sockjs/sockjs-erlang

400 bad request on cowboy branch

simonmacmullen opened this issue · 17 comments

Taken from the comments on commit 95b8c7a, making into an issue to make things a bit clearer.

essen: Hello! Cowboy author here, got linked to this commit. Did you find out what was the issue and is there anything I can do to help?

simonmacmullen: Hi essen, thanks for commenting! No, I haven't had any further time to investigate this and try to strip down to a more minimal test case or (more likely) figure out what the hell I'm doing wrong.

If you feel really energetic you could try to run it yourself; in the qunit tests there are lots of failures due to Cowboy returning 400 before my code gets a look in. If not I'll try to strip things down and make this more replicable next week.

essen: Sounds like it could be Cowboy indeed. I'll look later today. Can you tell me what browser you used to run the qunit tests though?

simonmacmullen: Chromium 11.0.696.68 (84545) Ubuntu 10.04, but I just tested with FF6 and got the same.

If you do try:

  • I apologise for the rough nature of the build system and tests
  • There will be bugs in my code that cause some tests to fail. "xhr-streaming: echo2" is an example of a test that fails in the way we're talking about here.
  • I stuck some io:formats in cowboy_http_protocol and it seems like the buffer in the state record contains the tail of a request somehow that gets carried over into the next request in next_request/3. But I have no idea how that module is supposed to work.

Simon, I'm trying to reproduce that, but I'm not sure how to run the cowboy branch:

$ cd sockjs-erlang
$ git branch -f cowboy origin/cowboy
$ git checkout cowboy
$ make
$ make test
[...]
coffee -o tests/html/lib/ -c --bare tests/html/src/tests.coffee
make[1]: Leaving directory `/tmp/sockjs-erlang/deps/sockjs-client'
make -C deps/misultin
make[1]: Entering directory `/tmp/sockjs-erlang/deps/misultin'
make[1]: rebar: Command not found
make[1]: *** [compile] Error 127
make[1]: Leaving directory `/tmp/sockjs-erlang/deps/misultin'
make: *** [test-prep] Error 2

Well, you need to install rebar. And probably a few other things.

Gah, misclick.

Thanks, copying rebar to bin does solve the problem.

Right, steps to reproduce.

  1. make test on proper branch
  2. run tcpdump in the background, for example sudo tcpdump -ni any -s0 -A port 8080
  3. Open chrome and type: http://127.0.0.1:8080/tests-qunit.html?filter=xhr-streaming%3A%20echo2
  4. Look at tcpdump:
HTTP/1.1 408 Request Timeout
Connection: close
Content-Length: 0
Date: Fri, 30 Sep 2011 15:54:50 GMT
Server: Cowboy

For completeness: we don't use 408 at any point in our code.

I may be wrong, but it looks like there are multiple 408 responses on a single connection. Ouch.

No, that's not it majek!

Due to the somewhat limited nature of the test code (yes, yes, it's still very young) you have to use http://localhost:8080/tests-qunit.html?filter=xhr-streaming%3A%20echo2 (i.e. localhost not 127.0.0.1)

Then you should see:

  HTTP/1.1 400 Bad Request
  Connection: close
  Content-Length: 0
  Date: Fri, 30 Sep 2011 16:00:23 GMT
  Server: Cowboy

If you put io:format("Buffer: ~p~n", [Buffer]), at the beginning of cowboy_http_protocol:parse_request/1 you'll see it try to parse a malformed HTTP request that does not appear to be what tcpdump sees.

Right, in the localhost case I can see one connection getting

  • first 204
  • than 400

And second connection getting 408. Something is clearly wrong somewhere.

Posting to get notice on this issue. Will look this week-end.

Didn't have time this week-end, sorry. I'll ping when I managed to take a look.

So I've tried to run make test and found out I need to install npm and nodejs to run it. Is there no way around this? I don't really want Node.

Not at the moment I'm afraid. I'm aware this is very far from a minimal test case; I'll try to cut it down.

OK, try the branch cowboy-no-node-hack. It just contains all the stuff node builds checked in directly.

Sounds like you have the same issue as in ninenines/cowboy#64

Good for me as I now have a test case to run against. ;)

I'll keep you informed.

Thanks!

You return the wrong Req object. In sockjs_cowboy_handler line 11 you get Req2 and then you return Req1 line 19, should be Req2. After that the tests crash but you have a proper error.

Argh, now I feel like an idiot. Thanks!