I am using jetty-9.2.2 with CometD-3.0.1. I am seeing below warning in my setup. It comes ~4,5 times in a day.:
2014-08-28 08:50:53.712:WARN:oejh.HttpParser:qtp607635164-15194: badMessage:
400 Illegal character for HttpChannelOverHttp#5946f125{r=1,a=IDLE,uri=-}
There is no details that can be debugged from the warning message. I have already logged a request https://bugs.eclipse.org/bugs/show_bug.cgi?id=443049 to provide detailed warning.
Meanwhile I want to know what is causing this warning? Can I ignore this or some messages are lost because of this?
Change https to http in the url.
I had the same error, then found out it's because my application did not support https, so jetty cannot recognize the https encrypted request.
Update May 2017
For Jetty 9.3+ users, you might see a log message that makes this response code more clear.
See Header parse error after upgrade to Jetty 9.3 for details.
Original Answer
The Bad Message: 400 Illegal Character can occur during parsing of a bad HTTP Request.
That is the HTTP error response that the client sees.
Some (not all) situations in which it can occur.
The EOL is not "\r\n" (CR + LF) (HTTP spec requirement)
The HTTP Method token is either not recognized or has invalid whitespace after it
The HTTP Version is not recognized or has invalid characters
HTTP Header name does not follow spec
HTTP Header value does not follow spec
This message is common on public (internet facing) servers.
You have bad HTTP requests coming in. Why?
A legitimate HTTP client has a bug
A legitimate HTTP client is not following the HTTP spec
A non HTTP client attempted to connect to your server (such as attempting to use non-encrypted HTTP on a SSL/TLS/HTTPS port, or even something as odd as an SMTP/IMAP email client attempting to talk to your HTTP port)
A malicious client is attempting to probe your system for weaknesses
This error can be caused, as it was for me, by a silly little mistake.
When testing on my localhost Jetty instance, I received a very similar 400 Illegal Character message. Then I realized why. I had simply assumed application address on my local Jetty was:
https://localhost:8080
whereas the correct address was unsecured:
http://localhost:8080
No problems after that.
Jetty is cautious about detailed error messages that include user sent data, as these can be part of an attack - even if echo'd just to a terminal.
However, we can do better and log some sanitised data. Acting on the bugzilla
Well, I met this problem because I mistook the "http://" as "https://"
Related
I have created a new project using the template 'Building a SOAP WebService Test Plan' in jmeter (followed the steps in the tutorial from the apache jmeter website to set this up). The responses aren't being accepted and in the results log I am seeing the message:
1446205258738,20995,Soap Request,Non HTTP response code: org.apache.http.conn.HttpHostConnectException,Non HTTP response message: Connection to http://(server name).com refused,Number of Users 1-10,text,false,2273,1,1,0
It's making the connection to http rather than https which I think is why the connection is not being made. Is there anyway to change this? I've tried using the different implementations in the soap request but this hasn't worked, currently using HttpClient4.
Please see the http request details
HTTP REQUEST DETAILS
As per #Rage answer (who should answer in response not comment , I'll be happy to remove my answer if he does), just change :
Protocol [http] value to https
See:
As per your last comment, you modified to https and now you face another issue , getting a 404.
So most probably your Path or Server Name or IP are wrong, as the hoster or developer for the correct connection informations.
I'm using libcurl (c++) library to make a request to an IIS 7.5 server. The transaction is a common SOAP webservice
Everything is working fine, my requests send an "Expect 100-continue" flag, and the server responds with a 100-continue and inmediately after that a 200 ok code along with the web service response.
But from time to time, the client receives a 100-continue message and after that, another 100 code. This makes the client report an error, as it expects a final status code right after the server 100 code. I read in W3C HTTP1.1 protocol:
An origin server that sends a 100 (Continue) response MUST
ultimately send a final status code, once the request body is
received and processed, unless it terminates the transport
connection prematurely.
The word "ultimately" makes me loose the track. Is it possible/common that a server sends several 100 codes after a final status code?
If anyone has faced this issue before, can point me to any explanation on how to handle multiple 100 response codes with libcurl?
Thanks in advance
The current spec says this on 100-continue:
The 100 (Continue) status code indicates that the initial part of a
request has been received and has not yet been rejected by the server. The server intends to send a final response after the request has been fully received and acted upon.
When the request contains an Expect header field that includes a
100- continue expectation, the 100 response indicates that the server wishes to receive the request payload body, as described in
Section 5.1.1. The client ought to continue sending the request and discard the 100 response.
If the request did not contain an Expect header field containing the 100-continue expectation, the client can simply discard this interim response.
The way I read it, it is not supposed to be more than one 100-continue response header and that's why libcurl works like this. I've never seen this (multiple 100 responses) happen and I've been doing HTTP for a while (I am the main developer of curl). To change this behavior I would expect you'd need to patch libcurl slightly to allow for this to happen.
It is not related to CURLOPT_FAILONERROR.
I suspect it's because there is an unhandled error that is not handled by the client properly. Make sure you set the CURLOPT_FAILONERROR flag.
See this SO post for more information.
When I send a http request using a wrong server address like 127.0.0.1 as the server address of a URL, the libcurl returns CURLE_OK and get me the http code 0. However, I get http code 404 when I send the same request with IE. Does anyone know how can I get an error code rather than 0 with libcurl when sending request like that.
libcurl returns CURLE_OK when the transfer went fine. Getting a 404 from a HTTP server is considered a fine transfer. You can make >=4xx HTTP response codes cause a libcurl error by setting the CURLOPT_FAILONERROR option.
Alternatively, and this may be the nicer way, you extract the HTTP response code after the transfer, with for example curl_easy_getinfo() to figure out the HTTP response code to see what the HTTP server thought about the resource you requested.
Try using it to visit a site that's actually running a web server, and try to retrieve a file that doesn't exist. For example, http://www.google.com/404. Your browser is almost certainly not actually getting a 404 from visiting 127.0.0.1, even if it's telling you that's what it got.
I'm developing a RESTful application that integrates with other webservices.
My question is, which HTTP status should I return if my client posts data that is invalid for one of those webservices? For example, if it posts a name that is invalid for a webservice that my application uses, which of the 4** status codes should I return, considering it's a user input error?
Some considerations I've made, and why I'm not comfortable of using them:
400: The data is invalid, but not the request format itself
403: The server is not refusing to respond, although the data is invalid
406: The error is in a provided parameter, not in the "accept" header
412: The error has nothing to do with "If-Match" header
So, what would you use in this case?
Stick with 400, or have a look at 422 (which may be close to what you need).
In real life, HTTP status codes for REST and other web services can be vague and hard to clearly specify. Things also get interesting if your client is actually talking to a proxy server and that proxy sends back its own status. If there's a problem in your web service (perhaps below your app) you may just get 500.
In the past I would opt for returning 200 and using your own JSON-or-whatever structure for returning error information for your client.
I'm writing a Django 1.3 view method which requires TLS/SSL to be used. I want to entirely drop the connection if an HttpRequest is received without using TLS/SSL and NOT return any kind of response. This is for security reasons.
Currently I am returning a response like so:
def some_view(request):
if not request.is_secure():
return HttpResponse(status=426)
...
However, returning 426 - Upgrade Required poses a couple of problems:
It's part of a proposed standard from May 2000 (RFC 2817), and is not an official HTTP standard.
The HttpResponse is open to a man-in-the-middle (MITM) attack. As mentioned in the comments here, if the server returns any type of response to the client without a TLS/SSL connection first being established, a MITM could hijack the response, alter it to re-direct elsewhere, and deliver the malicious re-direct response to the client.
Having the server re-direct from a HTTP URI to a HTTPS URI is open to the same MITM attack as noted above.
So, how can you entirely drop a connection inside a Django 1.3 view method without returning any type of HttpResponse?
As I was saying in this answer, I'm generally against the use of automatic redirections from http:// to https:// for the reasons you're mentioning. I would certainly not recommend resorting only to bulk mod_rewrite-style redirections for securing a site.
However, in your case, by the time the request reaches the server, it's too late. If there is a MITM, he has done his attack (or part of it) before you got the request.
The best you can do by then is to reply without any useful content. In this case, a redirection (using 301 or 302 and the Location header) could be appropriate. However, it may hide problems if the user (or even you as a developer) ignores the warnings (in this case, the browser will follow the redirection and retry the request almost transparently).
Therefore, I would simply suggest returning a 404 status:
http://yoursite/ and https://yoursite/ are effectively two distinct sites. There is no reason to expect a 1:1 mapping of all resources from the URI spaces from one to the other (just in the same way as you could have a completely different hierarchy for ftp://yoursite/).
More importantly, this is a problem that should be treated upstream: the link that led your user to this resource using http:// should be considered as broken. Don't make it work automatically. Having a 404 status for a resource that shouldn't be there is fine. In addition, returning an error message when there is an error is good: it will force you (or at least remind you) as a developer that you need to fix the page/form/link that led to this problem.
Dropping the connection is just a bonus, if you can do this with this framework: it will only be really useful if it can be sent asynchronously by the server (before the client has finished sending the request), if the browser can read it asynchronously (in which case it should stop sending immediately when there is an error) and if the MITM attacker is passive (an active MITM could stop the response to go back through the client and make sure the client sends all the request by consuming it with its own "proxy", whether or not the server has dropped the connection). These conditions can happen, but fixing the problem at the source is still better anyway.
If you are using Nginx as your front-end proxy then you can use another non-standard HTTP status code 444 which closes the connection without sending any headers. http://wiki.nginx.org/HttpRewriteModule#return It would require that Nginx know enough about which urls to deny on HTTP.