Not waiting for all data from socket before parsing message
See original GitHub issueSteps:
- ??? I’m not sure what I did to get into this state (maybe have a bunch of gcm notifications queued?), but I’m consistently in it
- Get multiple socket data events per gcm notification
Expected: Able to parse notifications
Actual: index out of range errors from protobuf
I think this is also the cause of #9
When you get into this state, if you add a console.log in socket.on('data' like so:
console.log('got data', buffer.length)
Than for the first push notification you’ll see the following:
got data 1
got data 88
got data 105
got data 514
got data 695
For subsequent push notifications you’ll see the following:
got data 1026
got data 189
Note that the first push notification always starts with a buffer of length 1.
When you’re in this state NotificationSchema.decode(buffer) always fails with messages like:
Error: invalid wire type 7 at offset 9
at BufferReader.Reader.skipType (/Users/islam/Projects/superhuman/desktop-electron/node_modules/protobufjs/src/reader.js:375:19)
at BufferReader.Reader.skipType (/Users/islam/Projects/superhuman/desktop-electron/node_modules/protobufjs/src/reader.js:366:22)
at Type.DataMessageStanza$decode [as decode] (eval at Codegen (/Users/islam/Projects/superhuman/desktop-electron/node_modules/@protobufjs/codegen/index.js:50:33), <anonymous>:67:5)
at Type.decode_setup [as decode] (/Users/islam/Projects/superhuman/desktop-electron/node_modules/protobufjs/src/type.js:502:25)
at onMessageReceived (/Users/islam/Projects/superhuman/desktop-electron/node_modules/push-receiver/src/client/socket/index.js:125:34)
at Timeout.setTimeout [as _onTimeout] (/Users/islam/Projects/superhuman/desktop-electron/node_modules/push-receiver/src/client/socket/index.js:105:9)
at ontimeout (timers.js:475:11)
at tryOnTimeout (timers.js:310:5)
at Timer.listOnTimeout (timers.js:270:5)
This is because socket.on('data' is not waiting for all the data to arrive before parsing it. I was able to demonstrate this by making a hack fix:
function listen(socket, NotificationSchema, keys, persistentIds) {
let buf = null
let timeout = null
socket.on('data', (buffer) => {
if (buf) {
buf = Buffer.concat([buf, buffer])
} else {
buf = buffer
}
if (!timeout) {
timeout = setTimeout(() => {
onMessageReceived(buf, NotificationSchema, keys, persistentIds)
buf = null
timeout = null
}, 1000)
}
});
}
This works but isn’t the right fix since it’s race-condition prone.
Issue Analytics
- State:
- Created 6 years ago
- Comments:12 (11 by maintainers)

Top Related StackOverflow Question
@MatthieuLemoine / @yurynix FYI I started on this and I should have something usable in the next day or two. I’m copying the implementation from chromium (with a few slight simplifications) so hopefully it’s mostly correct.
Also - @MatthieuLemoine would you be opposed to restructuring this library to use more classes? Ideally each connection can be isolated.
Fixed in v2.0.0