java - websocket protocol error when server deflates payload -
i'm writing java websocket server , receives opening handshake message client (in chrome version 57.0.2987.133 (64-bit)) , responds complete handshake, both shown below.
received: / http/1.1
received: host: localhost:6789
received: connection: upgrade
received: pragma: no-cache
received: cache-control: no-cache
received: upgrade: websocket
received: origin: http://localhost:8080
received: sec-websocket-version: 13
received: user-agent: mozilla/5.0 (macintosh; intel mac os x 10_9_5) applewebkit/537.36 (khtml, gecko) chrome/57.0.2987.133 safari/537.36
received: accept-encoding: gzip, deflate, sdch, br
received: accept-language: en-us,en;q=0.8
received: sec-websocket-key: l1iiusgijbgmtpthwsebog==
received: sec-websocket-extensions: permessage-deflate; client_max_window_bitssending: http/1.1 101 switching protocols
sending: upgrade: websocket
sending: connection: upgrade
sending: sec-websocket-accept: l5hxndjgdmybwr5grcqmowknf3q=
sending: accept-encoding: gzip, deflate
sending: sec-websocket-extensions: permessage-deflate; client_no_context_takeover; server_no_context_takeover
now, client can send messages , without problem , code uncompresses them using java.util.zip.deflater and... if server responds header bytes 0x81 (fin, no compression, text) , 0x5 bytes 'hello' (as example) websocket client in javascript on chrome entirely happy when try compress response, client closes connection citing error code 1002 , text 'websocket protocol error'.
deflate
public void sendmessagedeflated(string rxmessage, outputstream streamout) { system.out.println("message client is: " + rxmessage); // , compress response , send out. deflater compressor = new deflater(deflater.deflated); try { int headerlength = 2; byte unzippedmsg[] = rxmessage.getbytes("utf-8"); compressor.setinput(unzippedmsg); compressor.finish(); byte zippedmsg[] = new byte[2048]; // nasty constant have now. int tocompresslength = unzippedmsg.length; int complength = compressor.deflate(zippedmsg, headerlength, zippedmsg.length - headerlength); compressor.end(); zippedmsg[0] = (byte)0xc1; // fin bit, compression plus opcode text message zippedmsg[1] = (byte)((byte)0x00 | (byte)complength); // no mask on return data. streamout.write(zippedmsg, 0, complength + headerlength); } catch ( ioexception ioex ) { // tbd system.out.println("ioexception: " + ioex.tostring()); } catch ( exception ex ) { // tbd system.out.println("ioexception: " + ex.tostring()); } } gzip
public void sendmessagegzipped(string rxmessage, outputstream streamout) { // message here... system.out.println("message client is: " + rxmessage); // , compress response , send out. try { int headerlength = 2; byte unzippedmsg[] = rxmessage.getbytes("utf-8"); int tocompresslength = unzippedmsg.length; bytearrayoutputstream baos = new bytearrayoutputstream(); gzipoutputstream gzipout = new gzipoutputstream(baos); gzipout.write(unzippedmsg, 0, tocompresslength); gzipout.close(); byte[] payload = baos.tobytearray(); byte header[] = new byte[32]; header[0] = (byte)0xc1; // fin bit plus opcode text message header[1] = (byte)((byte)0x00 | (byte)payload.length); // no mask on return data. streamout.write(header, 0, 2); streamout.write(payload); } catch ( ioexception ioex ) { // tbd system.out.println("ioexception: " + ioex.tostring()); } catch ( exception ex ) { // tbd system.out.println("ioexception: " + ex.tostring()); } } i've tried switching opcode binary thinking perhaps compressed text = binary didn't work. can't see i've done wrong or missed out. implementation not include sliding compression window spans messages. think response headers make clear. gratefully accepted.
i solved building client-side websocket code , seeing exception thrown when tried inflate message: "invalid stored block lengths". led me post: java decompressing array of bytes talks deflate being able compress zlib wrapper or without. change 1 line in processmessage2 example code above this...
deflater compressor = new deflater(deflater.deflated, true); ...which sets 'nowrap' true.
in headers chrome browser client claims support gzip. if working i'll come here , post answer too.
Comments
Post a Comment