RandomGuyqwert
RandomGuyqwert

Reputation: 435

Handling POST requests using Pythons web.py

I have a very simple server. I use Python 2.7 with web.py.

Basically, my code looks like this:

urls = ("/endpoint", "Endpoint")

class Endpoint(object):
    def GET(self):
        return "End point"
    def POST(self):
        data = web.data()
        web.header('Content-Type', 'application/json')
        result = json.loads(data)
        logging.info("[Server] Endpoint POST with payload: " + json.dumps(result))
        return "Endpoint POST"

I tested this server by making POST requests like this:

echo '{"field": "test"}' | curl -d @- http://my.ip.number:port/endpoint

I tried server other methods of making POST requests. I also tried making get requests, both from the terminal and the browser.

In all cases, I get this very strange error.

Traceback (most recent call last):
  File "/usr/local/lib/python2.7/dist-packages/web.py-0.37-py2.7.egg/web/application.py", line 239, in process
    return self.handle()
  File "/usr/local/lib/python2.7/dist-packages/web.py-0.37-py2.7.egg/web/application.py", line 229, in handle
    fn, args = self._match(self.mapping, web.ctx.path)
  File "/usr/local/lib/python2.7/dist-packages/web.py-0.37-py2.7.egg/web/application.py", line 427, in _match
    for pat, what in mapping:
ValueError: need more than 1 value to unpack

Why is this error occurring and what can I do to prevent it?

Thanks!

EDIT 1:

After the traceback is displayed, I also get this:

192.168.46.1:51390 - - [16/Mar/2016 12:54:08] "HTTP/1.1 GET /favicon.ico" - 500 Internal Server Error

Neither the IP nor the port are the ones that I am using.

EDIT 2

#!/usr/bin/python
# -*- coding: utf-8 -*-

# Unicode
from __future__ import unicode_literals

import sys
reload(sys)
# -----

# Logging
import logging
logging.basicConfig(level=logging.INFO)
# -----

# Libs
import web
import json
# -----

urls = ("/", "Index",
        "/endpoint1", "EP1"
        "/endpoint2", "EP2")

class Index(object):
    # In the browser, this displays "Index", but also causes the error on the server side.
    def GET(self):
        return "Index"
    # Doesn't do anything, but causes the error
    def POST(self):
        data = web.data()
        web.header('Content-Type', 'application/json')
        result = json.loads(data)

        logging.info("[Server] Index " + json.dumps(result))
        return "Index POST"

class EP1(object):
    def GET(self):
        return "EP1"
    def POST(self):
        data = web.data()
        web.header('Content-Type', 'application/json')
        result = json.loads(data)

        logging.info("[Server] EP1 " + json.dumps(result))
        return "EP1 POST"


class EP2(object):
    def GET(self):
        return "EP2"
    def POST(self):
        data = web.data()
        web.header('Content-Type', 'application/json')
        result = json.loads(data)

        logging.info("[Server] EP2 " + json.dumps(result))
        return "EP2 POST"

if __name__ == "__main__":
    logging.info("[Server] Starting server.")
    app = web.application(urls, globals())
    app.run()

This is how my server looks like.

I start the server like this:

python server.py 0.0.0.0:7331

If I access the server's root endpoint from the browser, I get "Index" and the error still occurs. The other two endpoints don't return anything and cause the error.

Upvotes: 1

Views: 1555

Answers (1)

Sevanteri
Sevanteri

Reputation: 4058

You're missing a comma at second line here:

urls = ("/", "Index",
        "/endpoint1", "EP1"
        "/endpoint2", "EP2")

It should be like this:

urls = ("/", "Index",
        "/endpoint1", "EP1",
        "/endpoint2", "EP2")

What happens without the comma is that Python concatenates the two strings without a comma in between.

So with your code, urls was actually

("/", "Index", "/endpoint1", "EP1/endpoint2", "EP2")

Upvotes: 3

Related Questions