[HTML5] Obsolete socket input buffering?


#1

Hi,

I noticed an issue with the way socket messages are processed on HTML5.
In socket_onMessage, it adds the new message data to __inputBuffer, then copy the whole content to __input, and reset its position.
The problem is that if the client application doesn’t read messages on every callback (e.g. on each frame instead), data can be lost.
I solved the problem by completely removing usage of __inputBuffer :

	private function socket_onMessage (msg:Dynamic):Void {
		
		#if (js && html5)
		if (Std.is (msg.data, String)) {
			
			__input.position = __input.length;
			var cachePosition = __input.position;
			__input.writeUTFBytes (msg.data);
			__input.position = cachePosition;
			
		} else {
			
			var newData:ByteArray = (msg.data:ArrayBuffer);
			newData.readBytes (__input, __input.length);
			
		}
		
		if (__input.bytesAvailable > 0) {
			
			dispatchEvent (new ProgressEvent (ProgressEvent.SOCKET_DATA, false, false, __input.bytesAvailable, 0));
			
		}
		#end
		
	}

Any ideas why this __inputBuffer variable is there ?


#2

I think this might be left over from an earlier implementation, before we rewrote how our HTML5 sockets work. Perhaps it was shared code with our native implementation at some point. Regardless, I think you’re right. I’ve just changed it to not use an additional __inputBuffer object, as you did, but I added a little extra to prevent storing too much data if the socket is open for a long time:

	private function socket_onMessage (msg:Dynamic):Void {
		
		#if (js && html5)
		if (__input.position == __input.length) {
			
			__input.clear ();
			
		}
		
		if (Std.is (msg.data, String)) {
			
			__input.position = __input.length;
			var cachePosition = __input.position;
			__input.writeUTFBytes (msg.data);
			__input.position = cachePosition;
			
		} else {
			
			var newData:ByteArray = (msg.data:ArrayBuffer);
			newData.readBytes (__input, __input.length);
			
		}
		
		if (__input.bytesAvailable > 0) {
			
			dispatchEvent (new ProgressEvent (ProgressEvent.SOCKET_DATA, false, false, __input.bytesAvailable, 0));
			
		}
		#end
		
	}

I think this should cover your use case


#3

Perfect! Thank you :slight_smile: