Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

How to make a chunked request via nginx

It seems that nginx does not support chunked requests well. But I'm trying to get a more definitive (and current) answer. I have a client making a SOAP request to a server from a Java client which sets the header Transfer-Encoding: chunked. All works well when I connect directly to my application on Tomcat.

But when I put nginx between them, then things break.

To add a few details: I'm working with CloudFoundry. I'm using the Micro Cloud Foundry to confirm that things work as expected in the absence of nginx. But my requirement is to use cloudfoundry.com, so I don't have the ability to bypass nginx there.

This question and answer says that this is perhaps my only workaround: http://wiki.nginx.org/NginxHttpChunkinModule. But that workaround isn't available, since I cannot modify the configuration on cloudfoundry.com.

This question looks similar too, but it actually covers the reverse of this requirement. It covers chunked responses rather than chunked requests.

So how about any changes on the client to work around this? Is it possible to send both Transfer-Encoding: chunked and Content-Length: 123 as headers? This area is new to me, but it seems from projects like Apache HttpComponents that one would set either the length or chunking but not both. The point of chunking is that you don't need to know the length when the request starts. Could I tell my client to use HTTP/1.0 and play nice with nginx without chunking? Are there other workaround ideas that I'm forgetting?

like image 286
mdahlman Avatar asked Dec 16 '11 00:12

mdahlman


People also ask

What is a chunked request?

Chunking is a technique that HTTP servers use to improve responsiveness. Chunking can help you avoid situations where the server needs to obtain dynamic content from an external source and delays sending the response to the client until receiving all of the content so the server can calculate a Content-Length header.

What is chunked header?

chunked. Data is sent in a series of chunks. The Content-Length header is omitted in this case and at the beginning of each chunk you need to add the length of the current chunk in hexadecimal format, followed by ' \r\n ' and then the chunk itself, followed by another ' \r\n '.


1 Answers

I have gathered up answers to all parts of this question.

Base nginx does not support chunked requests (as Alexander confirmed!). Nginx can support chunked request by using NginXHttpCunkinModule (as my question mentions). Better: this module graduated from beta status to production quality more than 18 months ago. Best: I spoke with some members of the CloudFoundry engineering team at a recent meetup; they confirm that it's planned to add this module to their version of nginx. Problem solved. (Well, it's fully solved in the long term. But we don't have an exact date for when to expect this.)

Therefore a short-term solution would be nice as well. I found one.

Answering my question directed to Alexander: It's not possible to send "Content-Length" with chunked messages. That's really the point of chunked messages: you start sending them before you have the full content, so you cannot possibly know the length yet. So his idea to avoid chunked requests is correct. But to be more practical I would say, "Use HTTP/1.0 rather than HTTP/1.1." This has the effect of not sending chunked messages. We were able to patch our client temporarily to test this idea out. It worked. But we do not plan to roll out a public patch. It seems counterproductive to make everyone use a ten year old protocol (and a 10 year old unsupported client library!) to solve the problem for this one situation.

Instead I'll use the hacked client when needed, I'll email out if others find a need for it, and we'll wait for CloudFoundry up update to HttpChunkin and HTTP/1.1.

like image 150
mdahlman Avatar answered Sep 27 '22 19:09

mdahlman