Skip to content

This issue was moved to a discussion.

You can continue the conversation there. Go to discussion →

New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

SockJS framing #205

Closed
brycekahle opened this issue Oct 28, 2014 · 5 comments
Closed

SockJS framing #205

brycekahle opened this issue Oct 28, 2014 · 5 comments

Comments

@brycekahle
Copy link
Contributor

I want to start a discussion around SockJS protocol framing. Currently everything gets JSON encoded, even if it is already a string. This leads to double escaping of objects that were JSON stringified already (primus/primus#79). The WebSocket send method takes a string parameter, and it shouldn't be manipulating it more than necessary.

I could rectify just this part, but it would most likely be solved by having all messages be a JSON object. Because older browsers having missing/broken JSON.parse/stringify implementations, it requires us to use a polyfill (currently JSON3). This is slow on those same older browsers, and increases the size of the library quite significantly.

Ideally no framing would be necessary. We do need purpose frames like heartbeat, open, and close though. We could make those very specific strings, like say __sockjs_o__, and treat everything else like a user message. The only caveat is we need a way to send multiple messages in a single request/response for optimal use of polling transports. Those messages need to be delimited by something. Currently \n is used for some transports, JSON-encoded arrays for others. This doesn't cause issues with user content that contains newlines because they are escaped. But if extra escaping was stopped, then they would. Newlines (specifically \r\n) also has a special meaning for the SSE transport, so they have to be escaped there as well.

We could use specific unicode characters (US decimal 31 and RS decimal 30, http://en.wikipedia.org/wiki/C0_and_C1_control_codes#Field_separators) for delimiters, but that would prevent user messages from containing them. I think this is a much lower probability than a newline. This also lets us delimit at multiple levels. For example, between frame type and frame data by using US, and between multiple user messages by RS.

Thoughts?

@bclozel
Copy link

bclozel commented Nov 3, 2014

Interesting change indeed - I'd go with US and RS, but I'm wondering if that choice would be hard to handle on a day-to-day basis, with web debugging tools or trying to type those chars on a keyboard.

Also, where do you see this change? version 1.1? version 2.0?

Thanks,

@brycekahle
Copy link
Contributor Author

In my test code I've just been using String.fromCharCode, so there is no need to try and type them.

This change would definitely increment the major version number.

@thepian
Copy link

thepian commented Oct 30, 2015

I proposed something similar like this for the Caplin Liberator protocol a long time ago. It would be feasible for all projects I have seen.
I haven't seen them used ever but always wanted to use them for low level protocols. Traditionally control characters are reserved for protocols at this level, so in my book this is completely appropriate use.

@tmds
Copy link

tmds commented Jan 19, 2016

When revising the framing, perhaps the concept of a 'continuation frame'('fragmentation') can also be added.
And binary (#252).

@yanguoyu
Copy link

i think if this's a pure lib, you should't change send data even if data is not support.
maybe you can export hooks let users to change data

@sockjs sockjs locked and limited conversation to collaborators Aug 24, 2021

This issue was moved to a discussion.

You can continue the conversation there. Go to discussion →

Projects
None yet
Development

No branches or pull requests

5 participants