Files changed (33)
+Pylons brings a very broad but explicit :term:`Model-View-Controller` (:term:`MVC`) approach to the construction of web applications. It is specifically designed to give the application developer a high degree of flexibility when choosing ways of expressing business logic and application data; of managing the business logic and data; and of constructing a user interface (:term:`UI`) and/or an application programmer interface (:term:`API`) to afford and manage access to the model.
+Pylons was written by Ben Bangert, James Gardner and Phil Jenvey, they explain here why they chose this particular approach:
+ "The Pylons team are obsessed with reuse. Our vision is that in the near future Python web frameworks will all adopt the :term:`Web Server Gateway Interface` (or :term:`WSGI`) throughout their stack, making integration and reuse between frameworks extremely easy. Other frameworks don't necessarily share this vision to the same extent, preferring instead to keep their existing code base rather than opening it up to be replaced with standardized code.
+ There have been many other excellent developments in the Python web world recently such as :mod:`Paste` and :mod:`Myghty` and so, rather than duplicating the efforts of these teams by writing similar code for existing frameworks, we decided instead to put a new framework together using these existing projects with an emphasis on WSGI. We did this by working with the existing project teams and adding features to their code when possible rather than putting it all into the Pylons package.
+ While we designed Pylons to have all the functionality of :term:`Rails` (porting Rails components to Python as necessary) we also designed it to be much more flexible, thanks mainly to :term:`WSGI`. This allowed us to design Pylons so that your projects are highly reusable and easy to integrate with existing projects, or integrate existing projects into Pylons. You can use Pylons in the way that feels most natural to you, and in smaller or larger chunks."
+In summary, Pylons provides the connectivity for a wide set of relevant and useful components from which the web application developer can select those components that are considered best suited for the kind of application that is to be constructed.
+:term:`Model-View-Controller` is an architectural pattern used in software engineering. Its defining characteristic is that the modeling of the external world, the handling of user input and the feedback to the user are explicitly separated and handled by three types of object, each specialized for its task:
+ is a representation of the application data and the business rules used to manipulate the data. It manages the representation of the application domain, responding to requests for information about its state and responding to instructions to change state (c.f. Pylons :ref:`models`)
+ interprets the inputs from users or applications, commanding the model and/or the view to change as appropriate. Web applications often have several distinct controllers, each handling a different aspect of the application's behavior; a separate URL *dispatcher* maps incoming requests to the appropriate controller, as directed by a URL mapping scheme defined by the developer (c.f. Pylons :ref:`controllers`)
+ manages the presentation of the output and renders the model into a form suitable for interaction via a UI element (for human use) or an API function (for machine use). Multiple views can exist for a single model for different purposes (c.f. Pylons :ref:`views`)
+The explicit separation of these three tasks isolates the business logic and data from user interface considerations. By decoupling models and views, MVC helps to reduce the complexity in architectural design and to increase flexibility and reuse.
+It is becoming increasingly important for web app developers to be able to operate at an elevated level of abstraction. The choice of data store implementation is driven by the dictates of expressing the business model. Similarly, the selection of a template engine to render views of the data has to acknowledge both operational concerns and development requirements.
+Making an *informed* choice entails becoming informed about the candidates: understanding their different capabilities, their respective strengths and weaknesses. In this way, Pylons encourages the development of more sophisticated attitudes towards component elements. The old saying "If all you have is a hammer, then everything looks like a nail" simply doesn't hold true for Pylons developers with their well-equipped toolboxes.
+The benefits of adopting a MVC architecture for application development typically appear in the form of superior applications: they are more capable (more can be done), they are more robust (fewer errors are made), they are easier to maintain (the separation *really* helps), they are more readily scalable and extensible (again, the separation is a key factor) ... the list goes on.
+Pylons is similar in many ways to Ruby on Rails since it uses similar methodologies and includes direct ports of useful Rails components such as Routes and AJAX Helpers. By combining ideas from Mason, TurboGears and various Python frameworks with a highly extensible API, Pylons provides a framework that is:
+ Built on Mako, Routes and Paste, Pylons harnesses the full power of Mako for maximum performance. Although Pylons is still in development the core packages it uses are mature and Pylons is already being used in production systems.
+ Pylons implements the very best web development methodologies in straightforward pure-Python code. People new to Pylons are often surprised by how natural it is to use. If you already know Python you will feel right at home with Pylons, if not the Python Tutorial is an excellent starting point. Pylons plays nicely with other frameworks; you can even run TurboGears, Django and other WSGI applications from within a Pylons application making transition that bit easier. The web based interactive debugging makes even tough problems easy to resolve.
+ Pylons and its underlying components have been designed with great care to run on operating systems from Windows to MacOS to Linux on all types of computer from embedded devices to dedicated servers, in fact anywhere with a full Python 2.3 installation or above. Pylons can be deployed with its own server or integrated with other servers through WSGI / FastCGI / SCGI / CGI / mod_python and more. For example you can run Pylons applications on an Apache shared hosting account with ease.
+ Most Pylons functionality is implemented through extension packages distributed as eggs rather than as part of Pylons Core. This enables you to only include functionality you need in your application and avoid slowdown caused by unnecessary code. Even the Pylons Core APIs have been designed so that they can be tweaked, customized, extended or replaced with the minimum of effort, often just by modifying files in your application's config directory.
+ If your application needs extra functionality you can install a Pylons Extension of your own. Pylons Extensions already exist to add Internationalization, Auth facilities and Rails helpers. You can easily write and distribute your own Pylons Extensions using the Extension API. Pylons Extensions are also designed to be integrated with other web frameworks and this integration is actively encouraged.
+ Pylons' ease of use and sophisticated features mean that it is rapidly gaining support. Its extensible architecture is enabling more people to write new packages to extend the core functionality and its careful and flexible design mean that Pylons can rapidly evolve and grow as new methodologies and ideas take root.
+ Pylons makes it easy to expand on your knowledge of Python to master Pylons for web development. Using a MVC style dispatch, Python knowledge is used at various levels:
+ The Controller is just a basic Python class, called for each request. Customizing the response is as easy as overriding __call__ to make your webapp work how you want.
+Determine the encoding as specified by the browser via the Content-Type's ``charset parameter``, if one is set
+Return a list of specified mime-types that the browser's HTTP Accept header allows in the order provided.
+Inevitably, there will be occasions during your applications development or deployment where some task takes a significant amount of time to complete. When this occurs, the best way to speed things up is with :term:`caching`.
+Pylons comes with caching middleware enabled that is part of the same package that provides the session handling, `Beaker <http://beaker.groovie.org>`_. It supports backends in memory, the filesystem, and memcached.
+* Browser-side Caching - HTTP/1.1 supports the :term:`ETag` caching system that allows the browser to use its own cache instead of requiring the re-generation the entire page. ETag-based caching avoids repeated generation of content but if the browser has never seen the page it will still be generated. Therefore using ETag caching in conjunction with one of the other types of caching listed here will achieve optimal throughput and avoid resource-intensive operations.
+* Controllers - The `cache` object is available in controllers and templates for use in caching anything that can be pickled.
+* Templates - You can cache the results of an entire rendered template using the `3 cache keyword arguments to the render calls <http://pylonshq.com/docs/class-pylons.templating.Buffet.html#render>`_. These render commands can also be used inside templates.
+* Mako/Myghty Templates - Built-in caching options are available for both `Mako <http://www.makotemplates.org/docs/caching.html>`_ and `Myghty <http://www.myghty.org/docs/cache.myt>`_ template engines. They allow fine grained caching of only certain sections of the template, as well as caching of the entire template.
+The two primary concepts to keep in mind when caching is that caches have a *namespace* and can have *keys* under that namespace. Consider that for a single template, there might be multiple versions of the template you wish to keep a cache for. The keys in the namespace are the "version" and the name of the template is the "namespace". **Both of these values must be Python strings.**
+In templates, the cache "namespace" will be set to the name of the template being rendered automatically. Nothing else is required for caching, unless you wish to control how long the template is cached for, and have multiple versions of the template cached.
+see also Stephen Pierzchala's `Caching for Performance <http://web.archive.org/web/20060424171425/http://www.webperformance.org/caching/caching_for_performance.pdf>`_ (firstname.lastname@example.org)
+The `createfunc` option requires a callable object (function) which is then called by the cache anytime a value for the provided is not in the cache, or has expired in the cache. Since it is called with no arguments, the expensive function must not require any as well.
+The cache also supports removing values from the cache by their key, and clearing the cache should you wish to reset it.
+back to the browser. The `RFC specification for HTTP headers <http://www.w3.org/Protocols/rfc2616/rfc2616-sec14.html>`_ indicates that your
+Typically as a developer writing a Pylons application you will change the files in the ``config`` directory to change certain aspects of how your application behaves but any options you want the webmaster using your configuration file to be able to configure will be specified by the in a configuration file. This document describes how to use the webmaster configurable configuration file support in Pylons.
XXX: Write overview of configuration choices, difference between run-time/deplyment configuration, and application configuration (whats in the config/ dir)
+When you create a project using ``paster create -t pylons`` a sample configuration file called ``development.ini`` is automatically produced as one of the project files. This is an example of a configuration file and contains sensible options for development use in your project. For example when you are developing a Pylons application it is very useful to be able to see a debug report every time an error occurs so the development.ini file includes options to enable debug mode so these errors are shown.
+The ``--reload`` option is useful during development as the server will automatically reload each time a file is changed so that you can test the changes without having to manually restart the server.
+Say your application is called wiki, when a user comes to want to setup an application they will run the command:
+This command produces a different configuration file with sensible options for production use. In particular, the debug display is disables as the report might contain your usernames, passwords or other information you wouldn't want end users to see.
+You can find out how to control what is produced by the ``paster make-config`` by reading `Application Setup <Packaging+and+Deployment>`_.
+It is your responsibility as a developer to ensure that a sensible set of default configuration values exist when the webmaster uses the ``paster make-config`` command.
+You can create as many different configuration files as you like. Typically a developer might have a ``development.ini`` configuration file for testing, a ``production.ini`` file produced by the ``paster make-config`` command for testing the command produces sensible production output. You might also want a ``testing.ini`` configuration for doing some specific testing or any other number of configurations appropriate for your application. You can deploy your configuration in a variety of ways supported by paste deploy but typically you would serve your configuration like this:
+Configuration file format is described in great detail in the `Paste Deploy documentation <http://www.pythonpaste.org>`_.
+A number of error handling options can be specified in the config file. These are described in the `Error Handler <interactive_debugger.txt>`_ documentation but the important point to remember is that debug should always be set to ``false`` in production environments otherwise if an error occurs the visitor will be presented with the developer's interactive traceback which they could use to execute malicious code.
+Things break, and when they do, quickly pinpointing what went wrong and why makes a huge difference. By default, Pylons uses a customized version of `Ian Bicking's <http://blog.ianbicking.org/>`_ EvalException middleware that also includes full Mako/Myghty Traceback information.
+See the Enabling Debugging section of the `Getting Started <Getting+Started>`_ guide to enable the interactive debugging.
+Displays CGI, WSGI variables at the time of the exception, in addition to configuration information
+Since Mako and Myghty compile their templates to Python modules, it can be difficult to accurately figure out what line of the template resulted in the error. The `Template` tab provides the full Mako or Myghty traceback which contains accurate line numbers for your templates, and where the error originated from. If your exception was triggered before a template was rendered, no Template information will be available in this section.
+Using the interactive debugger can also be useful to gain a deeper insight into objects present only during the web request like the ``session`` and ``request`` objects.
+To trigger an error so that we can explore what's happening just raise an exception inside an action you're curious about. In this example, we'll raise an error in the action that's used to display the page you're reading this on. Here's what the docs controller looks like:
+Since we want to explore the ``session`` and ``request``, we'll need to bind them first. Here's what our action now looks like with the binding and raising an exception:
+Here's what exploring the Traceback from the above example looks like (Excerpt of the relevant portion):
+You can make all sorts of changes to how the debugging works. For example if you disable the ``debug`` variable in the config file Pylons will email you an error report instead of displaying it as long as you provide your email address at the top of the config file:
+This is very useful for a production site. Emails are sent via SMTP so you need to specify a valid SMTP server too.
+If you are using Pylons in a commercial company it is useful to be able to change the theme of the debugger so that if an error occurs, a page with your company logo appears. You might also decide to remove the Pylons logo if you use the debugger a lot so that there is more space to view the traceback.
+You can change the theme by creating a new template. For example, a very simple template might look like this:
+The values are automatically substituted by the error middleware. You can also add ``%(prefix)s`` which is replaced by the path to your application so you can include CSS files or images. For example if your application had a file called ``style.css`` in a directory called ``css`` within your ``public`` directory, you could add the following line to your template to ensure that the CSS file was always correctly found:
+If you want to retain the ability to switch between the different error displays you need a slightly more complicated example:
+In this case when you click on a link the relevant tab is displayed. As long as you keep the same IDs and class names, you can specify your own styles and create a theme like the one used by Pylons by default.
+Now that you have a template you need to use it in your application. In ``config/middleware.py`` change the following lines:
+All information from your configuration file is available in the ``pylons.config`` object. ``pylons.config`` also contains runtime configuration as defined in your project's ``config.environment`` module.
+``pylons.config`` behaves like a dictionary. For example you can obtain the location of the cache directory like this:
-XXX: Explanation of how the default route can map to any controller, how to add routes, link to Routes manual
+``PrefixMiddleware`` provides a way to manually override the root prefix (``SCRIPT_NAME``) of your application for certain situations.
+When running an application under a prefix (such as '``/james``') in FastCGI/apache, the ``SCRIPT_NAME`` environment variable is automatically set to to the appropriate value: '``/james``'. Pylons' URL generating functions such as ``url_for`` always take the ``SCRIPT_NAME`` value into account.
+One situation where ``PrefixMiddleware`` is required is when an application is accessed via a reverse proxy with a prefix. The application is accessed through the reverse proxy via the the URL prefix '``/james``', whereas the reverse proxy forwards those requests to the application at the prefix '``/``'.
+The reverse proxy, being an entirely separate web server, has no way of specifying the ``SCRIPT_NAME`` variable; it must be manually set by a ``PrefixMiddleware`` instance. Without setting ``SCRIPT_NAME``, ``url_for`` will generate URLs such as: '``/purchase_orders/1``', when it should be generating: '``/james/purchase_orders/1``'.
+To filter your application through a ``PrefixMiddleware`` instance, add the following to the '``[app:main]``' section of your .ini file:
+The name ``proxy-prefix`` simply acts as an identifier of the filter section; feel free to rename it.
+These .ini settings are equivalent to adding the following to the end of your application's ``config/middleware.py``, right before the ``return app`` line:
+Whereas the modification to ``config/middleware.py`` will setup an instance of ``PrefixMiddleware`` under every environment (.ini).
+ 16:20:20,440 DEBUG [helloworld.controllers.hello] Returning: Hello World! (content-type: text/plain)
+ 00:50:53,694 INFO [helloworld.controllers.hello] Returning: Hello World! (content-type: text/plain)
+ 00:50:53,695 INFO [wsgi] 192.168.1.111 - - [11/Aug/2007:20:09:33 -0700] "GET /hello HTTP/1.1" 404 - "-"
+module. Its format matches the standard Python :mod:`logging` module's `config file format <http://docs.python.org/lib/logging-config-fileformat.html>`_ . If a
+In the MVC paradigm the *controller* interprets the inputs, commanding the model and/or the view to change as appropriate.
+The controller is used to stitch together different pieces of the model and the view to fulfill a request. This places significant power into the developer’s hands.
+Presented with a number of reusable building blocks in the model and the view, the controller picks and chooses which blocks are needed to handle specific processing and display requirements.
+The controller interprets requests from the user and calls portions of the model and view as necessary to fulfill the request. So when the user clicks a Web link or submits an HTML form, the controller itself doesn’t output anything or perform any real processing. It takes the request and determines which model components to invoke and which formatting to apply to the resulting data.
+Pylons uses a class, where the superclass provides the WSGI interface and the subclass implements the application-specific controller logic.
+The Pylons WSGI Controller handles incoming web requests that are dispatched from the PylonsBaseWSGIApp.
+These requests result in a new instance of the WSGIController being created, which is then called with the dict options from the Routes match. The standard WSGI response is then returned with start_response called as per the WSGI spec.
+Since Pylons controllers are actually called with the WSGI interface, normal WSGI applications can also be Pylons ‘controllers’.
+It is possible for an application to add controllers without restarting the application. This requires telling Routes to re-scan the controllers directory.
+New controllers may be added from the command line with the paster command (recommended as that also creates the test harness file), or any other means of creating the controller file.
+For Routes to become aware of new controllers present in the controller directory, an internal flag is toggled to indicate that Routes should rescan the directory:
+On the next request, Routes will rescan the controllers directory and those routes that use the ``:controller`` dynamic part of the path will be able to match the new controller.
+WSGI runs deep through Pylons, and is present in many parts of the architecture. Since Pylons controllers are actually called with the WSGI interface, normal WSGI applications can also be Pylons 'controllers'.
+Optionally, if a full WSGI app should be mounted and handle the remainder of the URL, Routes can automatically move the right part of the URL into the :envvar:`SCRIPT_NAME`, so that the WSGI application can properly handle its :envvar:`PATH_INFO` part.
+When hooking up other WSGI applications, they will expect the part of the URL that was used to get to this controller to have been moved into :envvar:`SCRIPT_NAME`. :mod:`Routes` can properly adjust the environ if a :term:`map route` for this controller is added to the :file:`config/routing.py` file:
+By specifying the ``path_info`` dynamic path, Routes will put everything leading up to the ``path_info`` in the :envvar:`SCRIPT_NAME` and the rest will go in the :envvar:`PATH_INFO`.
+From a search engine point of view, it is important that every URL in your application has one canonical location. It's not true by default in your Pylons app but it is easy to fix.
+1. Routes has undocumented :data:`append_slash` option which adds a trailing '/' to every URL that it is asked to generate for you. So update :file:`routing.py` like this:
+2. In addition to generating correct URLs, you also want to redirect the user to the canonical page location if the '/' wasn't specified. One possible solution is to add the following code to :file:`YOURPROJ/lib/base.py`:
+In order to deploy this controller you will need at least a passing familiarity with XML-RPC itself. We will first review the basics of XML-RPC and then describe the workings of the ``Pylons XMLRPCController``. Finally, we will show an example of how to use the controller to implement a simple web service.
+After you've read this document, you may be interested in reading the companion document: "A blog publishing web service in XML-RPC" which takes the subject further, covering details of the MetaWeblog API (a popular XML-RPC service) and demonstrating how to construct some basic service methods to act as the core of a MetaWeblog blog publishing service.
+XML-RPC is a specification that describes a Remote Procedure Call (RPC) interface by which an application can use the Internet to execute a specified procedure call on a remote XML-RPC server. The name of the procedure to be called and any required parameter values are "marshalled" into XML. The XML forms the body of a POST request which is despatched via HTTP to the XML-RPC server. At the server, the procedure is executed, the returned value(s) is/are marshalled into XML and despatched back to the application. XML-RPC is designed to be as simple as possible, while allowing complex data structures to be transmitted, processed and returned.
+Pylons uses Python's xmlrpclib library to provide a specialised :class:`XMLRPCController` class that gives you the full range of these XML-RPC Introspection facilities for use in your service methods and provides the foundation for constructing a set of specialised service methods that provide a useful web service --- such as a blog publishing interface.
+This controller handles XML-RPC responses and complies with the `XML-RPC Specification <http://www.xmlrpc.com/spec>`_ as well as the `XML-RPC Introspection <http://scripts.incutio.com/xmlrpc/introspection.html>`_ specification.
+As part of its basic functionality an XML-RPC server provides three standard introspection procedures or "service methods" as they are called. The Pylons :class:`XMLRPCController` class provides these standard service methods ready-made for you:
+* :meth:`system.methodSignature` Returns an array of arrays for the valid signatures for a method. The first value of each array is the return value of the method. The result is an array to indicate multiple signatures a method may be capable of.
+By default, methods with names containing a dot are translated to use an underscore. For example, the ``system.methodHelp`` is handled by the method :meth:`system_methodHelp`.
+Methods in the XML-RPC controller will be called with the method given in the XML-RPC body. Methods may be annotated with a signature attribute to declare the valid arguments and return types.
+Since XML-RPC methods can take different sets of data, each set of valid arguments is its own list. The first value in the list is the type of the return argument. The rest of the arguments are the types of the data that must be passed in.
+In the last method in the example above, since the method can optionally take an integer value, both sets of valid parameter lists should be provided.
+(The `XML-RPC Home page <http://www.xmlrpc.com/>`_ and the `XML-RPC HOW-TO <http://www.faqs.org/docs/Linux-HOWTO/XML-RPC-HOWTO.html>`_ both provide further detail on the XML-RPC specification.)
+This simple service ``test.battingOrder`` accepts a positive integer < 51 as the parameter ``posn`` and returns a string containing the name of the US state occupying that ranking in the order of ratifying the constitution / joining the union.
+For developers using OS X, there's an `XML/RPC client <http://www.ditchnet.org/xmlrpc/>`_ that is an extremely useful diagnostic tool when developing XML-RPC (it's free ... but not entirely bug-free). Or, you can just use the Python interpreter:
+To debug XML-RPC servers from Python, create the client object using the optional verbose=1 parameter. You can then use the client as normal and watch as the XML-RPC request and response is displayed in the console.
+This document assumes that you have already installed a Pylons web application, and `created a configuration <Configuration+Files>`_ for it. Pylons applications use `PasteDeploy <http://pythonpaste.org/deploy/>`_ to start up your Pylons WSGI application, and can use the flup package to provide a Fast-CGI, SCGI, or AJP connection to it.
+`Fast-CGI <http://fastcgi.com/>`_ is a gateway to connect web severs like `Apache <http://httpd.apache.org/>`_ and `lighttpd <http://lighttpd.net/>`_ to a CGI-style application. Out of the box, Pylons applications can run with Fast-CGI in either a threaded or forking mode. (Threaded is the recommended choice)
+Setting a Pylons application to use Fast-CGI is very easy, and merely requires you to change the config line like so:
+Note that you will need to install the `flup <http://www.saddi.com/software/flup/dist/>`_ package, which can be
+The options in the config file are passed onto flup. The two common ways to run Fast CGI is either using a socket to listen for requests, or listening on a port/host which allows a webserver to send your requests to web applications on a different machine.
+If you want to listen on a host/port, the configuration cited in the first example will do the trick.
+For this example, we will assume you're using Apache 2, though Apache 1 configuration will be very similar. First, make sure that you have the Apache `mod_fastcgi <http://fastcgi.com/mod_fastcgi/docs/mod_fastcgi.html>`_ module installed in
+There will most likely be a section where you declare your FastCGI servers, and whether they're external:
+In our example we'll assume you're going to run a Pylons web application listening on a host/port. Changing ``-host`` to ``-socket`` will let you use a Pylons web application listening on a socket.
+The filename you give in the second option does not need to physically exist on the webserver, URIs that Apache resolve to this filename will be handled by the FastCGI application.
+The other important line to ensure that your Apache webserver has is to indicate that fcgi scripts should be handled with Fast-CGI:
+Finally, to configure your website to use the Fast CGI application you will need to indicate the script to be used:
+Other useful directives should be added as needed, for example, the ErrorLog directive, etc. This configuration will result in all requests being sent to your FastCGI application.
+As mentioned earlier eggs are a convenient format for packaging applications. You can create an egg for your project like this: