Search code examples
postargumentstornado

tornado post request: missing argument


I'm using tornado to build a web server and now I'm creating a login module. Here is the code:

<body>
    <form id="uploadForm">
      <div class="form-group">
        <label for="exampleInputEmail1">Email address</label>
        <input name="name" type="email" class="form-control" id="exampleInputEmail1" placeholder="Email">
      </div>
      <div class="form-group">
        <label for="exampleInputPassword1">Password</label>
        <input name="password" type="password" class="form-control" id="exampleInputPassword1" placeholder="Password">
      </div>
      <button id="submit" type="button" class="btn btn-default">Submit</button>
    </form>
</body>
    <script src="../js/plugins/jquery-3.2.1.min.js?v=c9f5aeeca3"></script>
    <script src="../js/common/bootstrap.min.js?v=5869c96cc8"></script>
    <script>
        $(function(){
            $('#submit').on('click',function(){
                $.ajax({
                    url: 'http://www.example.com/login',
                    method: 'POST',
                    data: $('#uploadForm').serialize(),
                    contentType: false,
                    processData: false,
                    cache: false,
                    success: function(data) {
                        console.log(data);
                        if( data === 'ERROR'){
                            alert('login failed')
                        }else{
                            location.href = data;
                        }
                    },
                    error: function (jqXHR) {
                        alert('ERROR');
                    }
                });
            });
        });
    </script>

And the backend part:

class LoginHandler(tornado.web.RequestHandler):
    def post(self, path):
        try:
            print(self.request.body)
            name = self.get_body_argument("name")
        except Exception as e:
            print(e)

When I do a test, I can see that print(self.request.body) gives me the result: b'name=test&password=tttt' but after that I get an exception:

HTTP 400: Bad Request (Missing argument name)

name=test is just in the http body but why it tells me missing argument name?


Solution

  • Tornado only supports "application/x-www-form-urlencoded" and "multipart/form-data" as content type. So when we send a post request to the server, we must send the request with the right contentType. For example,

    $.ajax({
                url: 'http://www.example.com/login',
                method: 'POST',
                data: $('#uploadForm').serialize(),
                contentType: 'application/x-www-form-urlencoded',
                processData: false,
                ...
    

    Also, we can neglect the contentType in ajax as 'application/x-www-form-urlencoded' is set by default.