Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Reading PUT data from piped cURL in Sinatra

I'm rewriting a small server backend in Sinatra, and currently the client talks to it via cURL calls such as echo "foo" | curl -X PUT -T - http://localhost:8090/. The problem is, in my put method in Sinatra, the request.body.read is always empty, even after I call rewind on it. Furthermore, the params hash is completely empty.

What's weird is that if I do curl -X PUT -d 'foo' http://localhost:8090/ instead it works. Also, in node.js I can read it fine using the request.on('data') and request.on('end') functions.

Is there any way to read the PUT body in Sinatra? I would like to avoid changing the client code if at all possible.

like image 300
Suan Avatar asked Dec 11 '25 17:12

Suan


1 Answers

I think the curl command from the client is misusing the -T flag. -T is for uploading a file, not sending data. Normally, when you don't provide a destination file name, -T will use the local file name for the upload. For example, curl -X PUT -T "bar.txt" http://localhost:8090/ will upload the local file bar.txt to the remote location http://localhost:8090/bar.txt. Since your client code pipes stdin instead of specifying a file, no local file name exists. And since your client code does not specify any destination file name, it will produce undefined results. I would consider it non-standard behavior for node.js to accept the contents of a file upload as data in the request body.

Your second example using the -d flag is the proper way to send data. I really think the best solution would be to change the client code, but you can still pipe stdin if you want to. Just use -d instead of -T, like so:

echo "foo" | curl -X PUT -d @- http://localhost:8090/
like image 108
wyattisimo Avatar answered Dec 14 '25 11:12

wyattisimo



Donate For Us

If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!