Websockets - Guaranteed full Messages? - html

When an "onmessage" event fires in the web socket protocol are you guaranteed the full message or is it more like a straight TCP connection where you buffer the data first and then try to extract packets.

There is protocol level support for fragmented messages and streaming. But this behavior is not represented in the current Javascript API, (reference). So yes, if you receive a message, it is indeed an entire message even if it was sent as many fragments.

Related

Parsing pcapng vs pcap file

ALL,
The documentation here talks about 2 different functions.
Is pcap_next() call for pcap while pcap_next_ex() is for pcapng format? Or both those functions can read both formats?
The page doesn't indicate it.
I have a code that parses pcap file and uses the former call, and I'm just wondering if it will be enough to just check for pcapng file and use the latter call instead.
TIA!!
Is pcap_next() call for pcap while pcap_next_ex() is for pcapng format?
No. pcap_next() is for applications that don't bother checking for errors, and pcap_next_ex() is for applications that do. To quote the RETURN VALUE section of the man page:
pcap_next_ex() returns 1 if the packet was read without problems, 0 if packets are being read from a live capture and the packet buffer timeout expired, PCAP_ERROR if an error occurred while reading the packet, and PCAP_ERROR_BREAK if packets are being read from a ``savefile'' and there are no more packets to read from the savefile. If PCAP_ERROR is returned, pcap_geterr(3PCAP) or pcap_perror(3PCAP) may be called with p as an argument to fetch or display the error text.
pcap_next() returns a pointer to the packet data on success, and returns NULL if an error occurred, or if no packets were read from a live capture (if, for example, they were discarded because they didn't pass the packet filter, or if, on platforms that support a packet buffer timeout that starts before any packets arrive, the timeout expires before any packets arrive, or if the file descriptor for the capture device is in non-blocking mode and no packets were available to be read), or if no more packets are available in a "savefile." Unfortunately, there is no way to determine whether an error occurred or not.
You should use pcap_next_ex().
Or both those functions can read both formats?
Yes. (pcap_next_ex() was added before libpcap could even read pcapng files.)
I have a code that parses pcap file and uses the former call, and I'm just wondering if it will be enough to just check for pcapng file and use the latter call instead.
It would be enough just to use pcap_next_ex() regardless of whether the file is a pcap or pcapng file.

technical inquiry - HTML transfer of image from server to browser

When an image is uploaded from the client's machine to the client (browser), it requires FileReader() API in html, thereafter a base64 encoded url (say) of the image is sent in chunks to the server, where it needs to be re-assembled. All of this is taken care by the developer.
However, when an image is sent from the server to the client, only the directory path of the image inside the server machine suffices, no chunking and encoding is required.
My questions are:
1. Does the server send the image in chunks to the html file. If it does not, how does sending full images not bottle server's network? What would happen in case of large video files?
2. In what form of binary data is the image sent to the client - base64url / ArrayBuffer / binarystring / text / etc.
3. If the server does send the image in chunks, who is doing the chunking and the re-assembly on the client thereafter?
Thanks.
HTML isn't really important here. What you care about are the transport protocols used - HTTP and TCP, most likely.
HTTP isn't chunked by default, though there are advanced headers that do allow that - those are mostly used to support seeking in large files (e.g. PDF, video). Technically, this isn't really chunking - it's just the infrastructure for allowing for partial downloads (i.e. "Give me data from byte 1024 to byte 2048.").
TCP is a stream-based protocol. From programmer point of view, that's all there is to it - no chunking. Technically, though, it will process your input data and send it as distinct packets that are reassembled in-order on the other side. This is a matter of practicality - it allows you to manage data latency, streaming, packet retransmission etc. TCP handles the specifics during connection negotiation - flow control, window sizing, congestion control...
That's not the end of it, though. All the other layers add their own bits - their own ways to package the payload and split it as necessary, their own ways to handle routing and filtering, their own ways to handle congestion...
Finally, just like HTTP natively supports downloads, it supports uploading data as well. Just send an HTTP request (usually POST or PUT) and write data in a format the server understands - anything from text through base-64 to raw binary data. The limiting factor in your case isn't the server, the browser or HTTP - it's JavaScript. The basic mechanism is still the same - a request followed by a response.
Now, to address your questions:
Server doesn't send images to the HTML file. HTML only contains an URL of the image[1], and when the browser sees an URL in the img tag, it will initiate a new, separate request just for the image data. It isn't fundamentally different from downloading a file from a link. As for the transfer itself, it follows pretty much exactly the same way as the original HTML document - HTTP headers, then the payload.
Usually, raw binary data. HTTP is a text-based protocol, but it's payload can be arbitrary. There's little reason to use Base-64 to transfer image data (though in the past, there have been HTTP and FTP servers that didn't support binary at all, so you had to use something like Base-64).
The HTTP server doesn't care (with the exception of "partial downloads" mentioned above). The underlying network protocols handle this.
[1] Nowadays, there's methods to embed images directly in the HTML text, but it's of varying practicality depending on the image size, caching requirements etc.

Supporting Server Sent Events with Netty HTTP2 implementation

I am using Netty 4.1-Beta6 version.
I want to support the use case where the HTTP2 server should be able to push events to the HTTP2 client on an existing connection - this could be an alarm or timer event from the cloud which needs to be propagated to the client.
I am thinking of using 'Server Sent Event' feature - is it possible to do this with HTTP2 in Netty, if so, how? Should I keep a http2 stream open by sending data frames with 'final frame' flag set to false? When I try this, what I observe is that the content gets buffered. The data frame doesn't reach the client as and when I write. I am using the DefaultHttp2Encoder. I tried setting the 'Transfer-Encoding' header to 'chunked' too.
Related question - does HTTP2 allows bi-directional data frames once the stream is in 'open' state? The idea is that the server should be able ask data from the client and client should be able to respond with the data in the same stream (reversal of client/server role once the stream is established). Is this possible?
Thanks in advance for the help.
I played with Netty bit more. Here is what I found for the 2 questions above.
Both the client and server can keep the stream in 'open' state by sending 'endOfStream' as false when they send the header/data frames. In order to avoid the buffering of data on the server side, I had to invoke flowController.writePendingBytes() followed by ChannelHandlerContext.flush()'.
I have uploaded my sample here - https://github.com/skssfo/http2
Yes, the client and the server can keep the stream open and send data frames independent of each other.
I am playing with Netty for the first time, it is very cool. Nice job Netty team!

HTTP GET from socket multiple events?

How do you know if a socket server or web server is done transmitting a HTTP GET request when using ProgressEvent.SOCKET_DATA ?
I doing my socket request with socket.writeUTFBytes('GET /index.php HTTP/1.1\r\n');
But the 'answer' is so big that i get multiple ProgressEvent.SOCKET_DATA. How do i know how much data it is supposed to transmit to me ? Or when it's done transmitting ?? Or even how many progressEvents i will get out of this request ? So far I'm using a timer that checks if the server is still transmitting but this isn't a very clean way of doing things..
How do i know how much data it is supposed to transmit to me? Or when it's done transmitting ??
By reading the Content-length header if that is sent by the server, or by waiting until the server closes the connection, or by reading until you've encountered a last-chunk (0<CRLF><CRLF>) if chunked transfer encoding is enabled, or any of the other indications that a full response has been received.
For simplicity, use a HTTPService or if that doesn't fit your needs, use a library that implements an HTTP client.
Or even how many progressEvents i will get out of this request ?
There is no way to tell.

websocket binary frame example

In Internet, I could not found any example for "websocket binary frame" communication using Javascript (as web client) and Java (as web server).
Can you anybody post few example for "websocket binary frame" communication ?
Kaazing WebSocket Gateway has had binary support for quite a while now. Moreover it also works in older browsers that don't support WebSocket natively. And there is support for clients other than JavaScript. So you can do binary over WebSocket using JavaScript, Flash/Flex, Silverlight, .Net, or Java. You can use any browser, the fallback emulation will work in older browsers.
The backend server can be Java or anything that listens on a TCP port.
Jetty has supported binary frames in WebSockets since at least version 7.5.2. Here is a Jetty example that includes binary frames: https://www.eclipse.org/jetty/documentation/9.4.x/jetty-websocket-api-send-message.html
From the server point of view, there is very little difference between sending and receiving binary data, it's just a single opcode change. When sending text, you are limited to UTF-8 encoded data. With binary you don't have that limit.
From the browser point of view, if the browser supports binary data (which really only very recent builds of Chrome support) then sending binary data involves sending an arraybuffer or blob using the send() method on the WebSocket object. Receiving binary data happens automatically if the server sends a binary frame. However, you can select between receiving blobs or arraybuffers by setting the binaryType property on your WebSocket object instance.
I just know how to unwrap the content sent from browser, here is my code:
socket.ondata = function(src,start,end) {
src = src.slice(start,end);
var maskKeys = [src[2],src[3],src[4],src[5]];
var dest = new Array();
for(var i=0;i<src.length-6;i++){
var mKey = maskKeys[i%4];
dest[i] = mKey ^ src[6+i];
}
console.log(new Buffer(dest).toString());
}
Found from here: http://songpengfei.iteye.com/blog/1178310
Link there is a zipped c source code, I change it to node. And now I'm study how to send data to the client.