Working with POST Data from HTML Forms

Table of contents:

The previous lab showed how to take a request from a client and return a response containing static HTML. This lab shows how you could write code to control how each response is generated, and act on data submitted from an HTML form.

4.3.1. How Do I Do That?

Write functions that take a Request object and work with it to generate a response. Set up a dictionary to map each available path in your web site to a function that will handle requests for that path. Use the Request.args dictionary to access data submitted from an HTML form. Example 4-3 shows a web server that generates one page containing an HTML form, and another page that processes the form and displays the results.

Example 4-3. formhandler.py


from twisted.web import http



def renderHomePage(request):

 colors = 'red', 'blue', 'green'

 flavors = 'vanilla', 'chocolate', 'strawberry', 'coffee'

 request.write("""

 

Form Test

Your name:

What's your favorite color?

""") for color in colors: request.write( "%s
" % ( color, color.capitalize( ))) request.write("""

What kinds of ice cream do you like?

""") for flavor in flavors: request.write( "%s
" % ( flavor, flavor.capitalize( ))) request.write("""

""") request.finish( ) def handlePost(request): request.write("""Posted Form Datagg

Form Data

""") for key, values in request.args.items( ): request.write("

%s

" % key) request.write("

  • ") for value in values: request.write("
  • %s
  • " % value) request.write("

") request.write(""" """) request.finish( ) class FunctionHandledRequest(http.Request): pageHandlers = { '/': renderHomePage, '/posthandler': handlePost, } def process(self): self.setHeader('Content-Type', 'text/html') if self.pageHandlers.has_key(self.path): handler = self.pageHandlers[self.path] handler(self) else: self.setResponseCode(http.NOT_FOUND) self.write("

Not Found

Sorry, no such page.") self.finish( ) class MyHttp(http.HTTPChannel): requestFactory = FunctionHandledRequest class MyHttpFactory(http.HTTPFactory): protocol = MyHttp if __name__ == "_ _main_ _": from twisted.internet import reactor reactor.listenTCP(8000, MyHttpFactory( )) reactor.run( )

Run formhandler.py. It will start a web server on port 8000. Go to http://localhost:8000/ and fill out the form on the home page. Figure 4-4 shows the home page with some fields already filled in.

Figure 4-4. Filling out the form generated by formhandler.py

 

When you click the Submit button, your browser will send the form data to the page formhandler using an HTTP POST request. When it receives the form data, formhandler will show you the fields and values that were submitted, as shown in Figure 4-5.

Figure 4-5. Displaying data submitted from a form

 

4.3.2. How Does That Work?

Example 4-3 defines two different functions for handling requests, renderHomePage and handlePost. FunctionHandledRequest is a subclass of Request with an attribute called pageHandlers that maps paths to functions. The process method looks at the path this particular request is using and tries to find a matching path in pageHandlers. If a match is found, the FunctionHandledRequest passes itself to the matching function, which is free to process the request however it likes; if no match is found, it generates a 404 "Not Found" response.

The renderHomePage function is set as the handler for /, the root page of the site. It generates an HTML form that will submit data to the page /formhandler. The handler function for /formhandler is handlePost, which responds with a page listing the posted data. handlePost iterates through the keys and values in Request args, which is a dictionary representing all the form data sent with the request.

In this case, the form data is sent as the body of an HTTP POST request. When a request is sent using HTTP GET, Request.args will contain values taken from the query portion of the request URI. You can verify this behavior by changing the method attribute of the form generated by renderHomePage from post to get, restarting the server, and resubmitting the form.

 

An HTML form can have multiple fields with the same name. For example, the form in Example 4-3 lets you check off multiple checkboxes, all which have the name of a flavor. Unlike many other web frameworks, http.Request doesn't hide this from you: instead of a mapping each field name to a string, Request.args maps each field name to a list. If you know there's going to be one value for a particular field, just grab the first value from the list.

Getting Started

Building Simple Clients and Servers

Web Clients

Web Servers

Web Services and RPC

Authentication

Mail Clients

Mail Servers

NNTP Clients and Servers

SSH

Services, Processes, and Logging



Twisted Network Programming Essentials
Twisted Network Programming Essentials
ISBN: 0596100329
EAN: 2147483647
Year: 2004
Pages: 107
Authors: Abe Fettig

Flylib.com © 2008-2020.
If you may any questions please contact us: flylib@qtcs.net