Skip to content

Commit

Permalink
fix: Fixed how heos commands are parsed
Browse files Browse the repository at this point in the history
The system expects the message object to have a specific structure. The structure should that the
command property is an object with two properties. It was a string.
  • Loading branch information
juliuscc committed Jan 26, 2019
1 parent 1336a0c commit f64f51b
Show file tree
Hide file tree
Showing 2 changed files with 70 additions and 12 deletions.
39 changes: 30 additions & 9 deletions __tests__/listen/responseParser.ts
Original file line number Diff line number Diff line change
Expand Up @@ -6,7 +6,7 @@ describe('Heos response messages can be correctly parsed', () => {

const messageParser: ResponseParser = new ResponseParser(mockCallback)

messageParser.put('{"heos": {"command": "", "result": "", "message": ""}}\r\n')
messageParser.put('{"heos": {"command": "test/test", "result": "", "message": ""}}\r\n')

expect(mockCallback).toBeCalledTimes(1)
})
Expand All @@ -17,16 +17,18 @@ describe('Heos response messages can be correctly parsed', () => {
const messageParser: ResponseParser = new ResponseParser(mockCallback)

messageParser.put('{"he')
messageParser.put('os": {"command": "", "result": "", "message": ""}}\r\n')
messageParser.put('os": {"command": "test/test", "result": "", "message": ""}}\r\n')

expect(mockCallback).toBeCalledTimes(1)

messageParser.put(
'{"heos": {"command": "", "result": "", "message": ""}}\r\n{"heos": {"command": "", "result": "", "message": ""}}\r\n'
'{"heos": {"command": "test/test", "result": "", "message": ""}}\r\n{"heos": {"command": "test/test", "result": "", "message": ""}}\r\n'
)
expect(mockCallback).toBeCalledTimes(3)

messageParser.put('{"heos": {"command": "", "result": "", "message": ""}}\r\n{ "heos":')
messageParser.put(
'{"heos": {"command": "test/test", "result": "", "message": ""}}\r\n{ "heos":'
)
expect(mockCallback).toBeCalledTimes(4)
})

Expand All @@ -35,12 +37,15 @@ describe('Heos response messages can be correctly parsed', () => {

const messageParser: ResponseParser = new ResponseParser(mockCallback)

const mockObject = { heos: { command: '', result: '', message: '' } }
const mockObject = { heos: { command: 'test/test', result: '', message: '' } }
const expectedObject = {
heos: { command: { commandGroup: 'test', command: 'test' }, result: '', message: '' }
}

messageParser.put(JSON.stringify(mockObject) + '\r\n')

expect(mockCallback).toBeCalledTimes(1)
expect(mockCallback.mock.calls[0][0]).toEqual(mockObject)
expect(mockCallback.mock.calls[0][0]).toEqual(expectedObject)
})

test('The parser returns the message as a HeosResponse', () => {
Expand All @@ -60,7 +65,10 @@ describe('Heos response messages can be correctly parsed', () => {

expect(mockCallback.mock.calls[0][0]).toEqual({
heos: {
command: expect.any(String),
command: {
commandGroup: expect.any(String),
command: expect.any(String)
},
result: expect.any(String),
message: expect.any(String)
}
Expand Down Expand Up @@ -115,18 +123,31 @@ describe('Heos response messages can be correctly parsed', () => {
}
}

const expectedObject = {
heos: {
command: { commandGroup: 'event', command: 'sources_changed' }
}
}

const mockObject2 = {
heos: {
command: 'event/sources_changed',
message: 'test_message'
}
}

const expectedObject2 = {
heos: {
command: { commandGroup: 'event', command: 'sources_changed' },
message: 'test_message'
}
}

messageParser.put(JSON.stringify(mockObject) + '\r\n')
messageParser.put(JSON.stringify(mockObject2) + '\r\n')

expect(mockCallback).toBeCalledTimes(2)
expect(mockCallback.mock.calls[0][0]).toEqual(mockObject)
expect(mockCallback.mock.calls[1][0]).toEqual(mockObject2)
expect(mockCallback.mock.calls[0][0]).toEqual(expectedObject)
expect(mockCallback.mock.calls[1][0]).toEqual(expectedObject2)
})
})
43 changes: 40 additions & 3 deletions src/listen/responseParser.ts
Original file line number Diff line number Diff line change
@@ -1,7 +1,16 @@
import { HeosResponse, HeosEvent } from '../types'
import { parseHeosCommandString } from './heosCommand'

const messageDelimiter = '\r\n'

function isCorrectResponse(response: any): boolean {
return (
response.hasOwnProperty('heos') &&
response.heos.hasOwnProperty('command') &&
typeof response.heos.command === 'string'
)
}

function isHeosResponse(response: any): response is HeosResponse {
if (response.hasOwnProperty('heos')) {
const heos: any = response.heos
Expand All @@ -12,11 +21,21 @@ function isHeosResponse(response: any): response is HeosResponse {
heos.hasOwnProperty('message')
) {
if (
typeof heos.command === 'string' &&
typeof heos.command === 'object' &&
typeof heos.result === 'string' &&
typeof heos.message === 'string'
) {
return true
if (
heos.command.hasOwnProperty('commandGroup') &&
heos.command.hasOwnProperty('command')
) {
if (
typeof heos.command.commandGroup === 'string' &&
typeof heos.command.command === 'string'
) {
return true
}
}
}
}
}
Expand All @@ -28,7 +47,13 @@ function isHeosEvent(response: any): response is HeosEvent {
const heos: any = response.heos

if (heos.hasOwnProperty('command')) {
if (typeof heos.command === 'string') {
if (
typeof heos.command === 'object' &&
heos.command.hasOwnProperty('commandGroup') &&
heos.command.hasOwnProperty('command') &&
typeof heos.command.commandGroup === 'string' &&
typeof heos.command.command === 'string'
) {
if (heos.hasOwnProperty('message')) {
return typeof heos.message === 'string'
} else {
Expand Down Expand Up @@ -65,6 +90,18 @@ export class ResponseParser {
messages
.filter((row: string) => row.length > 0)
.map((message: string) => JSON.parse(message))
.map((response: any) => {
if (isCorrectResponse) {
return response
} else {
throw new TypeError()
}
})
.map(response => {
const command = parseHeosCommandString(response.heos.command)
response.heos.command = command
return response
})
.map((response: any) => {
if (isHeosResponse(response) || isHeosEvent(response)) {
return response
Expand Down

0 comments on commit f64f51b

Please sign in to comment.