Python Web Framework Series – Pylons: Part 2 Controllers, Views and Testing
We last left off with Getting Started and having created our “pylonsforum” project and generated our first controller.
Source for home.py
``
from pylons import request, response, session, tmpl_context as c
from pylons.controllers.util import abort, redirect_to
from pylonsforum.lib.base import BaseController, render
log = logging.getLogger(__name__)
class HomeController(BaseController):
def index(self):
# Return a rendered template
#return render(‘/home.mako’)
# or, return a response
return ‘Hello World </div> </div>
Source for test_home.py
class TestHomeController(TestController):
def test_index(self):
response = self.app.get(url(controller=‘home’, action=‘index’))
# Test response… </div> </div>
Some Testing Setup
Now this is optional but these are some things I got out of the Pylons Book with test setup, mainly I wanted to refresh the test database on every go.
first open up test.ini in the top level of your project and change the [app:main] section to the following:
#use = config:development.ini
use = egg:pylonsforum
full_stack = true
cache_dir = % (here)s/data
beaker.session.key = pylonsforum
beaker.session.secret = somesecret</p>
sqlalchemy.url = sqlite:///%(here)s/test.db </div> </div>
Then open up websetup.py in the pylonsforum directory and change it to so:
import logging
from pylonsforum import model
import os.path</p>
from pylonsforum.config.environment import load_environment
log = logging.getLogger(__name__)
def setup_app(command, conf, vars):
load_environment(conf.global_conf, conf.local_conf)
# Load the models
from pylonsforum.model import meta
meta.metadata.bind = meta.engine
filename = os.path.split(conf.filename)[-1]
if filename == ‘test.ini’:
# Permanently drop any existing tables
log.info(“Dropping existing tables…”)
meta.metadata.drop_all(checkfirst=True)
# Continue as before
# Create the tables if they aren’t there already
meta.metadata.create_all(checkfirst=True)
log.info(“Successfully set up.”)
this will ensure a proper refresh of the database each time you run a test.
Testing
Now that we’re setup lets get onto testing (test first).
So far my study has found pylons to emphasize functional tests over unit tests. Hopefully, those with more experience will correct me. On the plus side nothing is stopping you from unit tests, and the functional test support is really nice giving you access to the response object including your view.
The response object there will let you examine the html returned based on the conditions you’ve set. lets not get to advanced yet and just change test_index to look for a specific page title so change the test_index test to the following
response = self.app.get(url(controller=‘home’, action=‘index’))
assert “
# Test response…
so what we have here is a test asserting that our web response is able to find “
nosetests --with-pylons=test.ini
will results in the following failed test result:
Controller and view review
Pylons has a return based controller/action behavior. So it can return a number of objects for now we can focus on raw text and rendering a view.
As you can see from the comments rendering a view is as simple as placing one in the template directory
edit home.py index action to look like so:
return render(‘index.mako’)
then create a file in the templates directory called index.mako that looks like so
</span>
</head>
</span>
<div id=“recentposts” style=“float: right” >
</span>subject</th> | </span>author</th> | </span>date submitted</th></tr></thead> </span> </span>jkruse</td> | </span>Re: Whats Up</td> | </span>06/01/2009</td></tr> | </span>rsvihla</td> | </span>Whats Up</td> | </span>06/01/2009</td></tr> | </span>thondo</td> | </span>Re: Looking for new work</td> | </span>05/25/2009</td></tr> | </span>jkruse</td> | </span>Re: Looking for new work</td> | </span>5/20/2009</td></tr> | </span>usmith</td> | </span>Looking for new work</td> | </span>05/01/2009</td></tr> | </tbody> </table> </div> </body> </div> </div>
Now that we’ve created our view and our action rendering said view, lets run our test again and see what we get:
In ClosingThis whirlwind tour of testing, views and controllers is at an end. Stay tuned for more in depth coverage of controllers and views in the next post. |
---|