summaryrefslogtreecommitdiff
path: root/docs/narr/views.rst
diff options
context:
space:
mode:
authorChris McDonough <chrism@plope.com>2010-12-19 18:04:55 -0500
committerChris McDonough <chrism@plope.com>2010-12-19 18:04:55 -0500
commita59c789b2bb4a1de5f79537cc2f1022c97bb51f6 (patch)
treeb5052ade4fc0718c9d2ff05b4a51e6f59f85f912 /docs/narr/views.rst
parente8f14759a3cf00b78735ef7e7ae8949f68b29b2b (diff)
downloadpyramid-a59c789b2bb4a1de5f79537cc2f1022c97bb51f6.tar.gz
pyramid-a59c789b2bb4a1de5f79537cc2f1022c97bb51f6.tar.bz2
pyramid-a59c789b2bb4a1de5f79537cc2f1022c97bb51f6.zip
- Split off "Renderers" as its own chapter from "Views" chapter in narrative
documentation.
Diffstat (limited to 'docs/narr/views.rst')
-rw-r--r--docs/narr/views.rst1376
1 files changed, 380 insertions, 996 deletions
diff --git a/docs/narr/views.rst b/docs/narr/views.rst
index 85bc8a5b0..c66da636f 100644
--- a/docs/narr/views.rst
+++ b/docs/narr/views.rst
@@ -3,8 +3,8 @@
Views
=====
-The primary job of any :app:`Pyramid` application is is to find and invoke a
-:term:`view callable` when a :term:`request` reaches the application. View
+One of the primary jobs of :app:`Pyramid` is is to find and invoke a
+:term:`view callable` when a :term:`request` reaches your application. View
callables are bits of code which do something interesting in response to a
request made to your application.
@@ -19,15 +19,16 @@ request made to your application.
The chapter :ref:`resourcelocation_chapter` describes how, using information
from the :term:`request`, a :term:`context` resource is computed. But the
-context resource found isn't very useful unless those elements can eventually
-be mapped to a :term:`view callable`.
+context resource itself isn't very useful without an associated :term:`view
+callable`. A view callable returns a response to a user, often using the
+context resource to do so.
The job of actually locating and invoking the "best" :term:`view callable` is
the job of the :term:`view lookup` subsystem. The view lookup subsystem
-compares information supplied by :term:`resource location` against
-:term:`view configuration` statements made by the developer stored in the
-:term:`application registry` to choose the most appropriate view callable for
-a specific request.
+compares the resource supplied by :term:`resource location` and information
+in the :term:`request` against :term:`view configuration` statements made by
+the developer to choose the most appropriate view callable for a specific
+set of circumstances.
This chapter provides documentation detailing the process of creating
view callables, documentation about performing view configuration, and
@@ -40,16 +41,18 @@ No matter how a view callable is eventually found, all view callables
used by :app:`Pyramid` must be constructed in the same way, and
must return the same kind of return value.
-Most view callables accept a single argument named ``request``. This argument
-represents a :app:`Pyramid` :term:`Request` object. A request object
-encapsulates a WSGI environment as represented to :app:`Pyramid` by the
-upstream :term:`WSGI` server.
+Most view callables accept a single argument named ``request``. This
+argument represents a :app:`Pyramid` :term:`Request` object. A request
+object encapsulates a WSGI environment as represented to :app:`Pyramid` by
+the upstream :term:`WSGI` server.
-A view callable can return a :mod:`Pyramid` :term:`Response` object
-directly. It may return another arbitrary non-Response value,
-however, this return value must be converted into a :term:`Response`
-object by the :term:`renderer` associated with the :term:`view
-configuration` for the view.
+In general, a view callable must return a :mod:`Pyramid` :term:`Response`
+object.
+
+.. note:: The above statement, though it sounds definitive, isn't always
+ true. See :ref:`renderers_chapter` for information related to using a
+ :term:`renderer` to convert a non-Response view callable return value into
+ a Response object.
View callables can be functions, instances, or classes.
@@ -62,10 +65,10 @@ View callables can be functions, instances, or classes.
Defining a View Callable as a Function
~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
-The easiest way to define a view callable is to create a function that
+One of the easiest way to define a view callable is to create a function that
accepts a single argument named ``request``, and which returns a
-:term:`Response` object. For example, this is a "hello world" view
-callable implemented as a function:
+:term:`Response` object. For example, this is a "hello world" view callable
+implemented as a function:
.. code-block:: python
:linenos:
@@ -84,14 +87,13 @@ callable implemented as a function:
Defining a View Callable as a Class
~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
-A view callable may also be a class instead of a function. When a
-view callable is a class, the calling semantics are slightly different
-than when it is a function or another non-class callable. When a view
-callable is a class, the class' ``__init__`` is called with a
-``request`` parameter. As a result, an instance of the class is
-created. Subsequently, that instance's ``__call__`` method is invoked
-with no parameters. Views defined as classes must have the following
-traits:
+A view callable may also be represented by a Python class instead of a
+function. When a view callable is a class, the calling semantics are
+slightly different than when it is a function or another non-class callable.
+When a view callable is a class, the class' ``__init__`` is called with a
+``request`` parameter. As a result, an instance of the class is created.
+Subsequently, that instance's ``__call__`` method is invoked with no
+parameters. Views defined as classes must have the following traits:
- an ``__init__`` method that accepts a ``request`` argument.
@@ -112,13 +114,16 @@ For example:
def __call__(self):
return Response('hello')
-The request object passed to ``__init__`` is the same type of request
-object described in :ref:`function_as_view`.
+The request object passed to ``__init__`` is the same type of request object
+described in :ref:`function_as_view`.
-If you'd like to use a different attribute than ``__call__`` to
-represent the method expected to return a response, you can use an
-``attr`` value as part of view configuration. See
-:ref:`view_configuration_parameters`.
+If you'd like to use a different attribute than ``__call__`` to represent the
+method expected to return a response, you can use an ``attr`` value as part
+of the configuration for the view. See :ref:`view_configuration_parameters`.
+The same view callable class can be used in different view configuration
+statements with different ``attr`` values, each pointing at a different
+method of the class if you'd like the class to represent a collection of
+related view callables.
.. index::
single: view calling convention
@@ -220,8 +225,7 @@ response. :app:`Pyramid` provides a range of different "exception" classes
which can act as response objects too. For example, an instance of the class
:class:`pyramid.httpexceptions.HTTPFound` is also a valid response object (see
:ref:`http_redirect`). A view can actually return any object that has the
-following attributes (these attributes form the notional "Pyramid Response
-interface"):
+following attributes.
status
The HTTP status code (including the name) for the response as a string.
@@ -238,40 +242,7 @@ app_iter
world!</body></html>']`` or it can be a file-like object, or any
other sort of iterable.
-Furthermore, a view needn't *always* return a Response object. If a view
-happens to return something which does not implement the Pyramid Response
-interface, :app:`Pyramid` will attempt to use a :term:`renderer` to construct a
-response. For example:
-
-.. code-block:: python
- :linenos:
-
- from pyramid.response import Response
- from pyramid.view import view_config
-
- @view_config(renderer='json')
- def hello_world(request):
- return {'content':'Hello!'}
-
-The above example returns a *dictionary* from the view callable. A dictionary
-does not implement the Pyramid response interface, so you might believe that
-this example would fail. However, since a ``renderer`` is associated with the
-view callable through its :term:`view configuration` (in this case, using a
-``renderer`` argument passed to :func:`pyramid.view.view_config`), if the view
-does *not* return a Response object, the renderer will attempt to convert the
-result of the view to a response on the developer's behalf. Of course, if no
-renderer is associated with a view's configuration, returning anything except
-an object which implements the Response interface will result in an error.
-And, if a renderer *is* used, whatever is returned by the view must be
-compatible with the particular kind of renderer used, or an error may occur
-during view invocation. One exception exists: it is *always* OK to return a
-Response object, even when a ``renderer`` is configured. If a view callable
-returns a response object from a view that is configured with a renderer, the
-renderer is bypassed entirely.
-
-Various types of renderers exist, including serialization renderers
-and renderers which use templating systems. See also
-:ref:`views_which_use_a_renderer`.
+These attributes form the notional "Pyramid Response interface".
.. index::
single: view http redirect
@@ -282,8 +253,8 @@ and renderers which use templating systems. See also
Using a View Callable to Do an HTTP Redirect
~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
-You can issue an HTTP redirect from within a view by returning a
-particular kind of response.
+You can issue an HTTP redirect from within a view by returning a particular
+kind of response.
.. code-block:: python
:linenos:
@@ -293,11 +264,12 @@ particular kind of response.
def myview(request):
return HTTPFound(location='http://example.com')
-All exception types from the :mod:`pyramid.httpexceptions` module implement the
-:term:`Response` interface; any can be returned as the response from a view.
-See :mod:`pyramid.httpexceptions` for the documentation for the ``HTTPFound``
-exception; it also includes other response types that imply other HTTP response
-codes, such as ``HTTPUnauthorized`` for ``401 Unauthorized``.
+All exception types from the :mod:`pyramid.httpexceptions` module implement
+the :term:`Response` interface; any can be returned as the response from a
+view. See :mod:`pyramid.httpexceptions` for the documentation for the
+``HTTPFound`` exception; it also includes other response types that imply
+other HTTP response codes, such as ``HTTPUnauthorized`` for ``401
+Unauthorized``.
.. note::
@@ -313,567 +285,6 @@ codes, such as ``HTTPUnauthorized`` for ``401 Unauthorized``.
more details.
.. index::
- single: renderer
- single: view renderer
-
-.. _views_which_use_a_renderer:
-
-Writing View Callables Which Use a Renderer
-~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
-
-View callables needn't always return a Response object. Instead, they may
-return an arbitrary Python object, with the expectation that a :term:`renderer`
-will convert that object into a response instance on behalf of the developer.
-Some renderers use a templating system; other renderers use object
-serialization techniques.
-
-If you do not define a ``renderer`` attribute in :term:`view configuration` for
-an associated :term:`view callable`, no renderer is associated with the view.
-In such a configuration, an error is raised when a view callable does not
-return an object which implements the :term:`Response` interface, documented
-within :ref:`the_response`.
-
-View configuration can vary the renderer associated with a view callable via
-the ``renderer`` attribute. For example, this call to
-:meth:`pyramid.config.Configurator.add_view` associates the ``json``
-renderer with a view callable:
-
-.. code-block:: python
- :linenos:
-
- config.add_view('myproject.views.my_view', renderer='json')
-
-When this configuration is added to an application, the
-``myproject.views.my_view`` view callable will now use a ``json`` renderer,
-which renders view return values to a :term:`JSON` serialization.
-
-Other built-in renderers include renderers which use the
-:term:`Chameleon` templating language to render a dictionary to a
-response.
-
-If the :term:`view callable` associated with a :term:`view configuration`
-returns a Response object directly (an object with the attributes ``status``,
-``headerlist`` and ``app_iter``), any renderer associated with the view
-configuration is ignored, and the response is passed back to :app:`Pyramid`
-unmolested. For example, if your view callable returns an instance of the
-:class:`pyramid.httpexceptions.HTTPFound` class as a response, no renderer will
-be employed.
-
-.. code-block:: python
- :linenos:
-
- from pyramid.httpexceptions import HTTPFound
-
- def view(request):
- return HTTPFound(location='http://example.com') # renderer avoided
-
-Views which use a renderer can vary non-body response attributes (such
-as headers and the HTTP status code) by attaching properties to the
-request. See :ref:`response_request_attrs`.
-
-Additional renderers can be added to the system as necessary (see
-:ref:`adding_and_overriding_renderers`).
-
-.. index::
- single: renderers (built-in)
- single: built-in renderers
-
-.. _built_in_renderers:
-
-Built-In Renderers
-~~~~~~~~~~~~~~~~~~
-
-Several built-in renderers exist in :app:`Pyramid`. These
-renderers can be used in the ``renderer`` attribute of view
-configurations.
-
-.. index::
- pair: renderer; string
-
-``string``: String Renderer
-+++++++++++++++++++++++++++
-
-The ``string`` renderer is a renderer which renders a view callable
-result to a string. If a view callable returns a non-Response object,
-and the ``string`` renderer is associated in that view's
-configuration, the result will be to run the object through the Python
-``str`` function to generate a string. Note that if a Unicode object
-is returned by the view callable, it is not ``str()`` -ified.
-
-Here's an example of a view that returns a dictionary. If the
-``string`` renderer is specified in the configuration for this view,
-the view will render the returned dictionary to the ``str()``
-representation of the dictionary:
-
-.. code-block:: python
- :linenos:
-
- from pyramid.response import Response
- from pyramid.view import view_config
-
- @view_config(renderer='string')
- def hello_world(request):
- return {'content':'Hello!'}
-
-The body of the response returned by such a view will be a string
-representing the ``str()`` serialization of the return value:
-
-.. code-block:: python
- :linenos:
-
- {'content': 'Hello!'}
-
-Views which use the string renderer can vary non-body response
-attributes by attaching properties to the request. See
-:ref:`response_request_attrs`.
-
-.. index::
- pair: renderer; JSON
-
-``json``: JSON Renderer
-+++++++++++++++++++++++
-
-The ``json`` renderer renders view callable
-results to :term:`JSON`. It passes the return value through the
-``json.dumps`` standard library function, and wraps the result in a
-response object. It also sets the response content-type to
-``application/json``.
-
-Here's an example of a view that returns a dictionary. Since the
-``json`` renderer is specified in the configuration for this view, the
-view will render the returned dictionary to a JSON serialization:
-
-.. code-block:: python
- :linenos:
-
- from pyramid.response import Response
- from pyramid.view import view_config
-
- @view_config(renderer='json')
- def hello_world(request):
- return {'content':'Hello!'}
-
-The body of the response returned by such a view will be a string
-representing the JSON serialization of the return value:
-
-.. code-block:: python
- :linenos:
-
- '{"content": "Hello!"}'
-
-The return value needn't be a dictionary, but the return value must
-contain values serializable by :func:`json.dumps`.
-
-You can configure a view to use the JSON renderer by naming ``json`` as the
-``renderer`` argument of a view configuration, e.g. by using
-:meth:`pyramid.config.Configurator.add_view`:
-
-.. code-block:: python
- :linenos:
-
- config.add_view('myproject.views.hello_world',
- name='hello',
- context='myproject.resources.Hello',
- renderer='json')
-
-
-Views which use the JSON renderer can vary non-body response
-attributes by attaching properties to the request. See
-:ref:`response_request_attrs`.
-
-.. index::
- pair: renderer; chameleon
-
-.. _chameleon_template_renderers:
-
-``*.pt`` or ``*.txt``: Chameleon Template Renderers
-+++++++++++++++++++++++++++++++++++++++++++++++++++
-
-Two built-in renderers exist for :term:`Chameleon` templates.
-
-If the ``renderer`` attribute of a view configuration is an absolute path, a
-relative path or :term:`asset specification` which has a final path element
-with a filename extension of ``.pt``, the Chameleon ZPT renderer is used.
-See :ref:`chameleon_zpt_templates` for more information about ZPT templates.
-
-If the ``renderer`` attribute of a view configuration is an absolute path or
-a :term:`asset specification` which has a final path element with a filename
-extension of ``.txt``, the :term:`Chameleon` text renderer is used. See
-:ref:`chameleon_zpt_templates` for more information about Chameleon text
-templates.
-
-The behavior of these renderers is the same, except for the engine
-used to render the template.
-
-When a ``renderer`` attribute that names a template path or :term:`asset
-specification` (e.g. ``myproject:templates/foo.pt`` or
-``myproject:templates/foo.txt``) is used, the view must return a
-:term:`Response` object or a Python *dictionary*. If the view callable with
-an associated template returns a Python dictionary, the named template will
-be passed the dictionary as its keyword arguments, and the template renderer
-implementation will return the resulting rendered template in a response to
-the user. If the view callable returns anything but a Response object or a
-dictionary, an error will be raised.
-
-Before passing keywords to the template, the keyword arguments derived from
-the dictionary returned by the view are augmented. The callable object --
-whatever object was used to define the ``view`` -- will be automatically
-inserted into the set of keyword arguments passed to the template as the
-``view`` keyword. If the view callable was a class, the ``view`` keyword
-will be an instance of that class. Also inserted into the keywords passed to
-the template are ``renderer_name`` (the string used in the ``renderer``
-attribute of the directive), ``renderer_info`` (an object containing
-renderer-related information), ``context`` (the context resource of the view
-used to render the template), and ``request`` (the request passed to the view
-used to render the template).
-
-Here's an example view configuration which uses a Chameleon ZPT
-renderer:
-
-.. code-block:: python
- :linenos:
-
- # config is an instance of pyramid.config.Configurator
-
- config.add_view('myproject.views.hello_world',
- name='hello',
- context='myproject.resources.Hello',
- renderer='myproject:templates/foo.pt')
-
-Here's an example view configuration which uses a Chameleon text
-renderer:
-
-.. code-block:: python
- :linenos:
-
- config.add_view('myproject.views.hello_world',
- name='hello',
- context='myproject.resources.Hello',
- renderer='myproject:templates/foo.txt')
-
-Views which use a Chameleon renderer can vary response attributes by
-attaching properties to the request. See
-:ref:`response_request_attrs`.
-
-.. index::
- pair: renderer; mako
-
-.. _mako_template_renderers:
-
-``*.mak`` or ``*.mako``: Mako Template Renderer
-+++++++++++++++++++++++++++++++++++++++++++++++
-
-The ``Mako`` template renderer renders views using a Mako template.
-When used, the view must return a Response object or a Python *dictionary*.
-The dictionary items will then be used in the global template space. If the
-view callable returns anything but a Response object, or a dictionary, an error
-will be raised.
-
-When using a ``renderer`` argument to a :term:`view configuration` to specify
-a Mako template, the value of the ``renderer`` may be a path relative to the
-``mako.directories`` setting (e.g. ``some/template.mak``) or, alternately,
-it may be a :term:`asset specification`
-(e.g. ``apackage:templates/sometemplate.mak``). Mako templates may
-internally inherit other Mako templates using a relative filename or a
-:term:`asset specification` as desired.
-
-XXX Further explanation or link to mako inheritance info
-
-Here's an example view configuration which uses a relative path:
-
-.. code-block:: python
- :linenos:
-
- # config is an instance of pyramid.config.Configurator
-
- config.add_view('myproject.views.hello_world',
- name='hello',
- context='myproject.resources.Hello',
- renderer='foo.mak')
-
-It's important to note that in Mako's case, the 'relative' path name
-``foo.mak`` above is not relative to the package, but is relative to the
-directory (or directories) configured for Mako via the ``mako.directories``
-configuration file setting.
-
-The renderer can also be provided in :term:`asset specification`
-format. Here's an example view configuration which uses one:
-
-.. code-block:: python
- :linenos:
-
- config.add_view('myproject.views.hello_world',
- name='hello',
- context='myproject.resources.Hello',
- renderer='mypackage:templates/foo.mak')
-
-The above configuration will use the file named ``foo.mak`` in the
-``templates`` directory of the ``mypackage`` package.
-
-The ``Mako`` template renderer can take additional arguments beyond the
-standard ``reload_templates`` setting, see the :ref:`environment_chapter` for
-additional :ref:`mako_template_renderer_settings`.
-
-.. index::
- single: response headers (from a renderer)
- single: renderer response headers
-
-.. _response_request_attrs:
-
-Varying Attributes of Rendered Responses
-~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
-
-Before a response constructed by a :term:`renderer` is returned to
-:app:`Pyramid`, several attributes of the request are examined which
-have the potential to influence response behavior.
-
-View callables that don't directly return a response should set these
-attributes on the ``request`` object via ``setattr`` during their
-execution, to influence associated response attributes.
-
-``response_content_type``
- Defines the content-type of the resulting response,
- e.g. ``text/xml``.
-
-``response_headerlist``
- A sequence of tuples describing cookie values that should be set in
- the response, e.g. ``[('Set-Cookie', 'abc=123'), ('X-My-Header',
- 'foo')]``.
-
-``response_status``
- A WSGI-style status code (e.g. ``200 OK``) describing the status of
- the response.
-
-``response_charset``
- The character set (e.g. ``UTF-8``) of the response.
-
-``response_cache_for``
- A value in seconds which will influence ``Cache-Control`` and
- ``Expires`` headers in the returned response. The same can also be
- achieved by returning various values in the ``response_headerlist``,
- this is purely a convenience.
-
-For example, if you need to change the response status from within a
-view callable that uses a renderer, assign the ``response_status``
-attribute to the request before returning a result:
-
-.. code-block:: python
- :linenos:
-
- from pyramid.view import view_config
-
- @view_config(name='gone', renderer='templates/gone.pt')
- def myview(request):
- request.response_status = '404 Not Found'
- return {'URL':request.URL}
-
-For more information on attributes of the request, see the API
-documentation in :ref:`request_module`.
-
-.. index::
- single: renderer (adding)
-
-.. _adding_and_overriding_renderers:
-
-Adding and Overriding Renderers
-~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
-
-New templating systems and serializers can be associated with :app:`Pyramid`
-renderer names. To this end, configuration declarations can be made which
-override an existing :term:`renderer factory`, and which add a new renderer
-factory.
-
-Renderers can be registered imperatively using the
-:meth:`pyramid.config.Configurator.add_renderer` API.
-
-.. note:: The tasks described in this section can also be performed via
- :term:`declarative configuration`. See
- :ref:`zcml_adding_and_overriding_renderers`.
-
-For example, to add a renderer which renders views which have a
-``renderer`` attribute that is a path that ends in ``.jinja2``:
-
-.. code-block:: python
- :linenos:
-
- config.add_renderer('.jinja2', 'mypackage.MyJinja2Renderer')
-
-The first argument is the renderer name.
-
-The second argument is a reference to an implementation of a
-:term:`renderer factory` or a :term:`dotted Python name` referring
-to such an object.
-
-.. _adding_a_renderer:
-
-Adding a New Renderer
-+++++++++++++++++++++
-
-You may add a new renderer by creating and registering a :term:`renderer
-factory`.
-
-A renderer factory implementation is typically a class with the
-following interface:
-
-.. code-block:: python
- :linenos:
-
- class RendererFactory:
- def __init__(self, info):
- """ Constructor: ``info`` will be an object having the
- the following attributes: ``name`` (the renderer name), ``package``
- (the package that was 'current' at the time the renderer was
- registered), ``type`` (the renderer type name), ``registry``
- (the current application registry) and ``settings`` (the
- deployment settings dictionary).
- """
-
- def __call__(self, value, system):
- """ Call a the renderer implementation with the value and
- the system value passed in as arguments and return the
- result (a string or unicode object). The value is the
- return value of a view. The system value is a dictionary
- containing available system values (e.g. ``view``,
- ``context``, and ``request``). """
-
-The formal interface definition of the ``info`` object passed to a renderer
-factory constructor is available as :class:`pyramid.interfaces.IRendererInfo`.
-
-There are essentially two different kinds of renderer factories:
-
-- A renderer factory which expects to accept a :term:`asset
- specification`, or an absolute path, as the ``name`` attribute of the
- ``info`` object fed to its constructor. These renderer factories are
- registered with a ``name`` value that begins with a dot (``.``). These
- types of renderer factories usually relate to a file on the filesystem,
- such as a template.
-
-- A renderer factory which expects to accept a token that does not represent
- a filesystem path or a asset specification in the ``name``
- attribute of the ``info`` object fed to its constructor. These renderer
- factories are registered with a ``name`` value that does not begin with a
- dot. These renderer factories are typically object serializers.
-
-.. sidebar:: Asset Specifications
-
- A asset specification is a colon-delimited identifier for a
- :term:`asset`. The colon separates a Python :term:`package`
- name from a package subpath. For example, the asset
- specification ``my.package:static/baz.css`` identifies the file named
- ``baz.css`` in the ``static`` subdirectory of the ``my.package`` Python
- :term:`package`.
-
-Here's an example of the registration of a simple renderer factory via
-:meth:`pyramid.config.Configurator.add_renderer`:
-
-.. code-block:: python
- :linenos:
-
- # config is an instance of pyramid.config.Configurator
-
- config.add_renderer(name='amf', factory='my.package.MyAMFRenderer')
-
-Adding the above code to your application startup configuration will
-allow you to use the ``my.package.MyAMFRenderer`` renderer factory
-implementation in view configurations. Your application can use this
-renderer by specifying ``amf`` in the ``renderer`` attribute of a
-:term:`view configuration`:
-
-.. code-block:: python
- :linenos:
-
- from pyramid.view import view_config
-
- @view_config(renderer='amf')
- def myview(request):
- return {'Hello':'world'}
-
-At startup time, when a :term:`view configuration` is encountered, which
-has a ``name`` attribute that does not contain a dot, the full ``name``
-value is used to construct a renderer from the associated renderer
-factory. In this case, the view configuration will create an instance
-of an ``AMFRenderer`` for each view configuration which includes ``amf``
-as its renderer value. The ``name`` passed to the ``AMFRenderer``
-constructor will always be ``amf``.
-
-Here's an example of the registration of a more complicated renderer
-factory, which expects to be passed a filesystem path:
-
-.. code-block:: python
- :linenos:
-
- config.add_renderer(name='.jinja2',
- factory='my.package.MyJinja2Renderer')
-
-Adding the above code to your application startup will allow you to use the
-``my.package.MyJinja2Renderer`` renderer factory implementation in view
-configurations by referring to any ``renderer`` which *ends in* ``.jinja`` in
-the ``renderer`` attribute of a :term:`view configuration`:
-
-.. code-block:: python
- :linenos:
-
- from pyramid.view import view_config
-
- @view_config(renderer='templates/mytemplate.jinja2')
- def myview(request):
- return {'Hello':'world'}
-
-When a :term:`view configuration` is encountered at startup time, which
-has a ``name`` attribute that does contain a dot, the value of the name
-attribute is split on its final dot. The second element of the split is
-typically the filename extension. This extension is used to look up a
-renderer factory for the configured view. Then the value of
-``renderer`` is passed to the factory to create a renderer for the view.
-In this case, the view configuration will create an instance of a
-``Jinja2Renderer`` for each view configuration which includes anything
-ending with ``.jinja2`` in its ``renderer`` value. The ``name`` passed
-to the ``Jinja2Renderer`` constructor will be the full value that was
-set as ``renderer=`` in the view configuration.
-
-See also :ref:`renderer_directive` and
-:meth:`pyramid.config.Configurator.add_renderer`.
-
-Overriding an Existing Renderer
-+++++++++++++++++++++++++++++++
-
-You can associate more than one filename extension with the same existing
-renderer implementation as necessary if you need to use a different file
-extension for the same kinds of templates. For example, to associate the
-``.zpt`` extension with the Chameleon ZPT renderer factory, use the
-:meth:`pyramid.config.Configurator.add_renderer` method:
-
-.. code-block:: python
- :linenos:
-
- config.add_renderer('.zpt', 'pyramid.chameleon_zpt.renderer_factory')
-
-After you do this, :app:`Pyramid` will treat templates ending in both the
-``.pt`` and ``.zpt`` filename extensions as Chameleon ZPT templates.
-
-To override the default mapping in which files with a ``.pt`` extension are
-rendered via a Chameleon ZPT page template renderer, use a variation on the
-following in your application's startup code:
-
-.. code-block:: python
- :linenos:
-
- config.add_renderer('.pt', 'mypackage.pt_renderer')
-
-After you do this, the :term:`renderer factory` in
-``mypackage.pt_renderer`` will be used to render templates which end
-in ``.pt``, replacing the default Chameleon ZPT renderer.
-
-To associate a *default* renderer with *all* view configurations (even
-ones which do not possess a ``renderer`` attribute), pass ``None`` as
-the ``name`` attribute to the renderer tag:
-
-.. code-block:: python
- :linenos:
-
- config.add_renderer(None, 'mypackage.json_renderer_factory')
-
-.. index::
single: view exceptions
.. _special_exceptions_in_callables:
@@ -882,25 +293,25 @@ Using Special Exceptions In View Callables
~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
Usually when a Python exception is raised within a view callable,
-:app:`Pyramid` allows the exception to propagate all the way out to
-the :term:`WSGI` server which invoked the application.
+:app:`Pyramid` allows the exception to propagate all the way out to the
+:term:`WSGI` server which invoked the application.
-However, for convenience, two special exceptions exist which are
-always handled by :app:`Pyramid` itself. These are
-:exc:`pyramid.exceptions.NotFound` and
-:exc:`pyramid.exceptions.Forbidden`. Both are exception classes
-which accept a single positional constructor argument: a ``message``.
+However, for convenience, two special exceptions exist which are always
+handled by :app:`Pyramid` itself. These are
+:exc:`pyramid.exceptions.NotFound` and :exc:`pyramid.exceptions.Forbidden`.
+Both are exception classes which accept a single positional constructor
+argument: a ``message``.
-If :exc:`pyramid.exceptions.NotFound` is raised within view code,
-the result of the :term:`Not Found View` will be returned to the user
-agent which performed the request.
+If :exc:`pyramid.exceptions.NotFound` is raised within view code, the result
+of the :term:`Not Found View` will be returned to the user agent which
+performed the request.
-If :exc:`pyramid.exceptions.Forbidden` is raised within view code,
-the result of the :term:`Forbidden View` will be returned to the user
-agent which performed the request.
+If :exc:`pyramid.exceptions.Forbidden` is raised within view code, the result
+of the :term:`Forbidden View` will be returned to the user agent which
+performed the request.
-In all cases, the message provided to the exception constructor is
-made available to the view which :app:`Pyramid` invokes as
+In all cases, the message provided to the exception constructor is made
+available to the view which :app:`Pyramid` invokes as
``request.exception.args[0]``.
.. index::
@@ -911,18 +322,15 @@ made available to the view which :app:`Pyramid` invokes as
Exception Views
~~~~~~~~~~~~~~~~
-The machinery which allows the special
-:exc:`pyramid.exceptions.NotFound` and
-:exc:`pyramid.exceptions.Forbidden` exceptions to be caught by
-specialized views as described in
-:ref:`special_exceptions_in_callables` can also be used by application
-developers to convert arbitrary exceptions to responses.
+The machinery which allows the special :exc:`pyramid.exceptions.NotFound` and
+:exc:`pyramid.exceptions.Forbidden` exceptions to be caught by specialized
+views as described in :ref:`special_exceptions_in_callables` can also be used
+by application developers to convert arbitrary exceptions to responses.
-To register a view that should be called whenever a particular
-exception is raised from with :app:`Pyramid` view code, use the
-exception class or one of its superclasses as the ``context`` of a
-view configuration which points at a view callable you'd like to
-generate a response.
+To register a view that should be called whenever a particular exception is
+raised from with :app:`Pyramid` view code, use the exception class or one of
+its superclasses as the ``context`` of a view configuration which points at a
+view callable you'd like to generate a response.
For example, given the following exception class in a module named
``helloworld.exceptions``:
@@ -935,8 +343,8 @@ For example, given the following exception class in a module named
self.msg = msg
-You can wire a view callable to be called whenever any of your *other*
-code raises a ``hellworld.exceptions.ValidationFailure`` exception:
+You can wire a view callable to be called whenever any of your *other* code
+raises a ``hellworld.exceptions.ValidationFailure`` exception:
.. code-block:: python
:linenos:
@@ -949,11 +357,11 @@ code raises a ``hellworld.exceptions.ValidationFailure`` exception:
response.status_int = 500
return response
-Assuming that a :term:`scan` was run to pick up this view
-registration, this view callable will be invoked whenever a
-``helloworld.exceptions.ValidationError`` is raised by your
-application's view code. The same exception raised by a custom root
-factory or a custom traverser is also caught and hooked.
+Assuming that a :term:`scan` was run to pick up this view registration, this
+view callable will be invoked whenever a
+``helloworld.exceptions.ValidationError`` is raised by your application's
+view code. The same exception raised by a custom root factory or a custom
+traverser is also caught and hooked.
Other normal view predicates can also be used in combination with an
exception view registration:
@@ -969,11 +377,11 @@ exception view registration:
def notfound_view(request):
return HTTPNotFound()
-The above exception view names the ``route_name`` of ``home``, meaning
-that it will only be called when the route matched has a name of
-``home``. You can therefore have more than one exception view for any
-given exception in the system: the "most specific" one will be called
-when the set of request circumstances match the view registration.
+The above exception view names the ``route_name`` of ``home``, meaning that
+it will only be called when the route matched has a name of ``home``. You
+can therefore have more than one exception view for any given exception in
+the system: the "most specific" one will be called when the set of request
+circumstances match the view registration.
The only view predicate that cannot be used successfully when creating
an exception view configuration is ``name``. The name used to look up
@@ -999,43 +407,42 @@ Exception views can be configured with any view registration mechanism:
Handling Form Submissions in View Callables (Unicode and Character Set Issues)
~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
-Most web applications need to accept form submissions from web
-browsers and various other clients. In :app:`Pyramid`, form
-submission handling logic is always part of a :term:`view`. For a
-general overview of how to handle form submission data using the
-:term:`WebOb` API, see :ref:`webob_chapter` and `"Query and POST
-variables" within the WebOb documentation
+Most web applications need to accept form submissions from web browsers and
+various other clients. In :app:`Pyramid`, form submission handling logic is
+always part of a :term:`view`. For a general overview of how to handle form
+submission data using the :term:`WebOb` API, see :ref:`webob_chapter` and
+`"Query and POST variables" within the WebOb documentation
<http://pythonpaste.org/webob/reference.html#query-post-variables>`_.
-:app:`Pyramid` defers to WebOb for its request and response
-implementations, and handling form submission data is a property of
-the request implementation. Understanding WebOb's request API is the
-key to understanding how to process form submission data.
-
-There are some defaults that you need to be aware of when trying to
-handle form submission data in a :app:`Pyramid` view. Having high-order
-(i.e., non-ASCII) characters in data contained within form submissions
-is exceedingly common, and the UTF-8 encoding is the most common
-encoding used on the web for character data. Since Unicode values are
-much saner than working with and storing bytestrings, :app:`Pyramid`
-configures the :term:`WebOb` request machinery to attempt to decode form
-submission values into Unicode from UTF-8 implicitly.
-This implicit decoding happens when view code obtains form field values
-via the ``request.params``, ``request.GET``, or ``request.POST`` APIs
-(see :ref:`request_module` for details about these APIs).
+:app:`Pyramid` defers to WebOb for its request and response implementations,
+and handling form submission data is a property of the request
+implementation. Understanding WebOb's request API is the key to
+understanding how to process form submission data.
+
+There are some defaults that you need to be aware of when trying to handle
+form submission data in a :app:`Pyramid` view. Having high-order (i.e.,
+non-ASCII) characters in data contained within form submissions is
+exceedingly common, and the UTF-8 encoding is the most common encoding used
+on the web for character data. Since Unicode values are much saner than
+working with and storing bytestrings, :app:`Pyramid` configures the
+:term:`WebOb` request machinery to attempt to decode form submission values
+into Unicode from UTF-8 implicitly. This implicit decoding happens when view
+code obtains form field values via the ``request.params``, ``request.GET``,
+or ``request.POST`` APIs (see :ref:`request_module` for details about these
+APIs).
.. note::
+
Many people find the difference between Unicode and UTF-8 confusing.
Unicode is a standard for representing text that supports most of the
- world's writing systems. However, there are many ways that Unicode
- data can be encoded into bytes for transmittal and storage. UTF-8 is
- a specific encoding for Unicode, that is backwards-compatible with
- ASCII. This makes UTF-8 very convenient for encoding data where a
- large subset of that data is ASCII characters, which is largely true
- on the web. UTF-8 is also the standard character encoding for URLs.
+ world's writing systems. However, there are many ways that Unicode data
+ can be encoded into bytes for transit and storage. UTF-8 is a specific
+ encoding for Unicode, that is backwards-compatible with ASCII. This makes
+ UTF-8 very convenient for encoding data where a large subset of that data
+ is ASCII characters, which is largely true on the web. UTF-8 is also the
+ standard character encoding for URLs.
-As an example, let's assume that the following form page is served up to
-a browser client, and its ``action`` points at some :app:`Pyramid`
-view code:
+As an example, let's assume that the following form page is served up to a
+browser client, and its ``action`` points at some :app:`Pyramid` view code:
.. code-block:: xml
:linenos:
@@ -1055,10 +462,10 @@ view code:
</form>
</html>
-The ``myview`` view code in the :app:`Pyramid` application *must*
-expect that the values returned by ``request.params`` will be of type
-``unicode``, as opposed to type ``str``. The following will work to
-accept a form post from the above form:
+The ``myview`` view code in the :app:`Pyramid` application *must* expect that
+the values returned by ``request.params`` will be of type ``unicode``, as
+opposed to type ``str``. The following will work to accept a form post from
+the above form:
.. code-block:: python
:linenos:
@@ -1067,9 +474,8 @@ accept a form post from the above form:
firstname = request.params['firstname']
lastname = request.params['lastname']
-But the following ``myview`` view code *may not* work, as it tries to
-decode already-decoded (``unicode``) values obtained from
-``request.params``:
+But the following ``myview`` view code *may not* work, as it tries to decode
+already-decoded (``unicode``) values obtained from ``request.params``:
.. code-block:: python
:linenos:
@@ -1080,34 +486,33 @@ decode already-decoded (``unicode``) values obtained from
firstname = request.params['firstname'].decode('utf-8')
lastname = request.params['lastname'].decode('utf-8')
-For implicit decoding to work reliably, you should ensure that every
-form you render that posts to a :app:`Pyramid` view explicitly defines a
-charset encoding of UTF-8. This can be done via a response that has a
-``;charset=UTF-8`` in its ``Content-Type`` header; or, as in the form
-above, with a ``meta http-equiv`` tag that implies that the charset is
-UTF-8 within the HTML ``head`` of the page containing the form. This
-must be done explicitly because all known browser clients assume that
-they should encode form data in the same character set implied by
-``Content-Type`` value of the response containing the form when
-subsequently submitting that form. There is no other generally accepted
-way to tell browser clients which charset to use to encode form data.
-If you do not specify an encoding explicitly, the browser client will
-choose to encode form data in its default character set before
-submitting it, which may not be UTF-8 as the server expects. If a
-request containing form data encoded in a non-UTF8 charset is handled by
-your view code, eventually the request code accessed within your view
-will throw an error when it can't decode some high-order character
-encoded in another character set within form data, e.g., when
-``request.params['somename']`` is accessed.
+For implicit decoding to work reliably, you should ensure that every form you
+render that posts to a :app:`Pyramid` view explicitly defines a charset
+encoding of UTF-8. This can be done via a response that has a
+``;charset=UTF-8`` in its ``Content-Type`` header; or, as in the form above,
+with a ``meta http-equiv`` tag that implies that the charset is UTF-8 within
+the HTML ``head`` of the page containing the form. This must be done
+explicitly because all known browser clients assume that they should encode
+form data in the same character set implied by ``Content-Type`` value of the
+response containing the form when subsequently submitting that form. There is
+no other generally accepted way to tell browser clients which charset to use
+to encode form data. If you do not specify an encoding explicitly, the
+browser client will choose to encode form data in its default character set
+before submitting it, which may not be UTF-8 as the server expects. If a
+request containing form data encoded in a non-UTF8 charset is handled by your
+view code, eventually the request code accessed within your view will throw
+an error when it can't decode some high-order character encoded in another
+character set within form data, e.g., when ``request.params['somename']`` is
+accessed.
If you are using the :class:`pyramid.response.Response` class to generate a
response, or if you use the ``render_template_*`` templating APIs, the UTF-8
charset is set automatically as the default via the ``Content-Type`` header.
-If you return a ``Content-Type`` header without an explicit charset, a request
-will add a ``;charset=utf-8`` trailer to the ``Content-Type`` header value for
-you, for response content types that are textual (e.g. ``text/html``,
-``application/xml``, etc) as it is rendered. If you are using your own
-response object, you will need to ensure you do this yourself.
+If you return a ``Content-Type`` header without an explicit charset, a
+request will add a ``;charset=utf-8`` trailer to the ``Content-Type`` header
+value for you, for response content types that are textual
+(e.g. ``text/html``, ``application/xml``, etc) as it is rendered. If you are
+using your own response object, you will need to ensure you do this yourself.
.. note:: Only the *values* of request params obtained via
``request.params``, ``request.GET`` or ``request.POST`` are decoded
@@ -1124,23 +529,23 @@ View Configuration: Mapping a Resource Type to a View
A developer makes a :term:`view callable` available for use within a
:app:`Pyramid` application via :term:`view configuration`. A view
-configuration associates a view callable with a set of statements
-that determine the set of circumstances which must be true for the view
-callable to be invoked.
+configuration associates a view callable with a set of statements that
+determine the set of circumstances which must be true for the view callable
+to be invoked.
A view configuration statement is made about information present in the
:term:`context` resource and the :term:`request`.
View configuration is performed in one of these ways:
-- by running a :term:`scan` against application source code which has
- a :class:`pyramid.view.view_config` decorator attached to a Python
- object as per :class:`pyramid.view.view_config` and
+- by running a :term:`scan` against application source code which has a
+ :class:`pyramid.view.view_config` decorator attached to a Python object as
+ per :class:`pyramid.view.view_config` and
:ref:`mapping_views_using_a_decorator_section`.
-- by using the :meth:`pyramid.config.Configurator.add_view`
- method as per :meth:`pyramid.config.Configurator.add_view`
- and :ref:`mapping_views_using_imperative_config_section`.
+- by using the :meth:`pyramid.config.Configurator.add_view` method as per
+ :meth:`pyramid.config.Configurator.add_view` and
+ :ref:`mapping_views_using_imperative_config_section`.
Both of these mechanisms is completely equivalent to the other.
@@ -1150,8 +555,8 @@ Both of these mechanisms is completely equivalent to the other.
A view configuration might also be performed by virtue of :term:`route
configuration`. View configuration via route configuration is performed by
-using the :meth:`pyramid.config.Configurator.add_route` method to
-create a route with a ``view`` argument.
+using the :meth:`pyramid.config.Configurator.add_route` method to create a
+route with a ``view`` argument.
.. note:: ZCML users can use :ref:`route_directive` to perform the same task.
See also :ref:`zcml_route_configuration`.
@@ -1181,40 +586,41 @@ Non-Predicate Arguments
+++++++++++++++++++++++
``permission``
- The name of a :term:`permission` that the user must possess in order
- to invoke the :term:`view callable`. See
- :ref:`view_security_section` for more information about view
- security and permissions.
+ The name of a :term:`permission` that the user must possess in order to
+ invoke the :term:`view callable`. See :ref:`view_security_section` for
+ more information about view security and permissions.
- If ``permission`` is not supplied, no permission is registered for
- this view (it's accessible by any caller).
+ If ``permission`` is not supplied, no permission is registered for this
+ view (it's accessible by any caller).
``attr``
The view machinery defaults to using the ``__call__`` method of the
- :term:`view callable` (or the function itself, if the view callable
- is a function) to obtain a response. The ``attr`` value allows you
- to vary the method attribute used to obtain the response. For
- example, if your view was a class, and the class has a method named
- ``index`` and you wanted to use this method instead of the class'
- ``__call__`` method to return the response, you'd say
- ``attr="index"`` in the view configuration for the view. This is
- most useful when the view definition is a class.
-
- If ``attr`` is not supplied, ``None`` is used (implying the function
- itself if the view is a function, or the ``__call__`` callable
- attribute if the view is a class).
-
-``renderer`` This is either a single string term (e.g. ``json``) or a string
- implying a path or :term:`asset specification`
- (e.g. ``templates/views.pt``) naming a :term:`renderer` implementation. If
- the ``renderer`` value does not contain a dot (``.``), the specified string
- will be used to look up a renderer implementation, and that renderer
- implementation will be used to construct a response from the view return
- value. If the ``renderer`` value contains a dot (``.``), the specified
- term will be treated as a path, and the filename extension of the last
- element in the path will be used to look up the renderer implementation,
- which will be passed the full path. The renderer implementation will be
- used to construct a :term:`response` from the view return value.
+ :term:`view callable` (or the function itself, if the view callable is a
+ function) to obtain a response. The ``attr`` value allows you to vary the
+ method attribute used to obtain the response. For example, if your view
+ was a class, and the class has a method named ``index`` and you wanted to
+ use this method instead of the class' ``__call__`` method to return the
+ response, you'd say ``attr="index"`` in the view configuration for the
+ view. This is most useful when the view definition is a class.
+
+ If ``attr`` is not supplied, ``None`` is used (implying the function itself
+ if the view is a function, or the ``__call__`` callable attribute if the
+ view is a class).
+
+``renderer``
+ Denotes the :term:`renderer` implementation which will be used to construct
+ a :term:`response` from the associated view callable's return value. (see
+ also :ref:`renderers_chapter`).
+
+ This is either a single string term (e.g. ``json``) or a string implying a
+ path or :term:`asset specification` (e.g. ``templates/views.pt``) naming a
+ :term:`renderer` implementation. If the ``renderer`` value does not
+ contain a dot (``.``), the specified string will be used to look up a
+ renderer implementation, and that renderer implementation will be used to
+ construct a response from the view return value. If the ``renderer`` value
+ contains a dot (``.``), the specified term will be treated as a path, and
+ the filename extension of the last element in the path will be used to look
+ up the renderer implementation, which will be passed the full path.
When the renderer is a path, although a path is usually just a simple
relative pathname (e.g. ``templates/foo.pt``, implying that a template
@@ -1225,67 +631,63 @@ Non-Predicate Arguments
``some.dotted.package_name:relative/path``, making it possible to address
template assets which live in a separate package.
- The ``renderer`` attribute is optional. If it is not defined, the
- "null" renderer is assumed (no rendering is performed and the value
- is passed back to the upstream :app:`Pyramid` machinery
- unmolested). Note that if the view callable itself returns a
- :term:`response` (see :ref:`the_response`), the specified renderer
- implementation is never called.
+ The ``renderer`` attribute is optional. If it is not defined, the "null"
+ renderer is assumed (no rendering is performed and the value is passed back
+ to the upstream :app:`Pyramid` machinery unmolested). Note that if the
+ view callable itself returns a :term:`response` (see :ref:`the_response`),
+ the specified renderer implementation is never called.
``wrapper``
- The :term:`view name` of a different :term:`view configuration`
- which will receive the response body of this view as the
- ``request.wrapped_body`` attribute of its own :term:`request`, and
- the :term:`response` returned by this view as the
- ``request.wrapped_response`` attribute of its own request. Using a
- wrapper makes it possible to "chain" views together to form a
- composite response. The response of the outermost wrapper view will
- be returned to the user. The wrapper view will be found as any view
- is found: see :ref:`view_lookup`. The "best" wrapper view will be
- found based on the lookup ordering: "under the hood" this wrapper
- view is looked up via
+ The :term:`view name` of a different :term:`view configuration` which will
+ receive the response body of this view as the ``request.wrapped_body``
+ attribute of its own :term:`request`, and the :term:`response` returned by
+ this view as the ``request.wrapped_response`` attribute of its own request.
+ Using a wrapper makes it possible to "chain" views together to form a
+ composite response. The response of the outermost wrapper view will be
+ returned to the user. The wrapper view will be found as any view is found:
+ see :ref:`view_lookup`. The "best" wrapper view will be found based on the
+ lookup ordering: "under the hood" this wrapper view is looked up via
``pyramid.view.render_view_to_response(context, request,
- 'wrapper_viewname')``. The context and request of a wrapper view is
- the same context and request of the inner view.
+ 'wrapper_viewname')``. The context and request of a wrapper view is the
+ same context and request of the inner view.
If ``wrapper`` is not supplied, no wrapper view is used.
Predicate Arguments
+++++++++++++++++++
-These arguments modify view lookup behavior. In general, the more
-predicate arguments that are supplied, the more specific, and narrower
-the usage of the configured view.
+These arguments modify view lookup behavior. In general, the more predicate
+arguments that are supplied, the more specific, and narrower the usage of the
+configured view.
``name``
The :term:`view name` required to match this view callable. Read
:ref:`traversal_chapter` to understand the concept of a view name.
- If ``name`` is not supplied, the empty string is used (implying the
- default view).
+ If ``name`` is not supplied, the empty string is used (implying the default
+ view).
``context``
An object representing a Python class that the :term:`context` resource
must be an instance of *or* the :term:`interface` that the :term:`context`
- must provide in order for this view to be found and called. This predicate
- is true when the :term:`context` resource is an instance of the represented
- class or if the :term:`context` provides the represented interface; it is
- otherwise false.
+ resource must provide in order for this view to be found and called. This
+ predicate is true when the :term:`context` resource is an instance of the
+ represented class or if the :term:`context` resource provides the
+ represented interface; it is otherwise false.
If ``context`` is not supplied, the value ``None``, which matches any
resource, is used.
``route_name``
- If ``route_name`` is supplied, the view callable will be invoked
- only when the named route has matched.
+ If ``route_name`` is supplied, the view callable will be invoked only when
+ the named route has matched.
This value must match the ``name`` of a :term:`route configuration`
- declaration (see :ref:`urldispatch_chapter`) that must match before
- this view will be called. Note that the ``route`` configuration
- referred to by ``route_name`` will usually have a ``*traverse`` token
- in the value of its ``pattern``, representing a part of the path that
- will be used by :term:`traversal` against the result of the route's
- :term:`root factory`.
+ declaration (see :ref:`urldispatch_chapter`) that must match before this
+ view will be called. Note that the ``route`` configuration referred to by
+ ``route_name`` will usually have a ``*traverse`` token in the value of its
+ ``pattern``, representing a part of the path that will be used by
+ :term:`traversal` against the result of the route's :term:`root factory`.
If ``route_name`` is not supplied, the view callable will be have a chance
of being invoked if no other route was matched. This is when the
@@ -1293,127 +695,119 @@ the usage of the configured view.
it matched any configured route.
``request_type``
- This value should be an :term:`interface` that the :term:`request`
- must provide in order for this view to be found and called.
+ This value should be an :term:`interface` that the :term:`request` must
+ provide in order for this view to be found and called.
- If ``request_type`` is not supplied, the value ``None`` is used,
- implying any request type.
+ If ``request_type`` is not supplied, the value ``None`` is used, implying
+ any request type.
*This is an advanced feature, not often used by "civilians"*.
``request_method``
- This value can either be one of the strings ``GET``, ``POST``,
- ``PUT``, ``DELETE``, or ``HEAD`` representing an HTTP
- ``REQUEST_METHOD``. A view declaration with this argument ensures
- that the view will only be called when the request's ``method``
- attribute (aka the ``REQUEST_METHOD`` of the WSGI environment)
- string matches the supplied value.
+ This value can either be one of the strings ``GET``, ``POST``, ``PUT``,
+ ``DELETE``, or ``HEAD`` representing an HTTP ``REQUEST_METHOD``. A view
+ declaration with this argument ensures that the view will only be called
+ when the request's ``method`` attribute (aka the ``REQUEST_METHOD`` of the
+ WSGI environment) string matches the supplied value.
- If ``request_method`` is not supplied, the view will be invoked
- regardless of the ``REQUEST_METHOD`` of the :term:`WSGI`
- environment.
+ If ``request_method`` is not supplied, the view will be invoked regardless
+ of the ``REQUEST_METHOD`` of the :term:`WSGI` environment.
``request_param``
This value can be any string. A view declaration with this argument
- ensures that the view will only be called when the :term:`request`
- has a key in the ``request.params`` dictionary (an HTTP ``GET`` or
- ``POST`` variable) that has a name which matches the supplied value.
+ ensures that the view will only be called when the :term:`request` has a
+ key in the ``request.params`` dictionary (an HTTP ``GET`` or ``POST``
+ variable) that has a name which matches the supplied value.
If the value supplied has a ``=`` sign in it,
- e.g. ``request_params="foo=123"``, then the key (``foo``) must both
- exist in the ``request.params`` dictionary, *and* the value must
- match the right hand side of the expression (``123``) for the view
- to "match" the current request.
+ e.g. ``request_params="foo=123"``, then the key (``foo``) must both exist
+ in the ``request.params`` dictionary, *and* the value must match the right
+ hand side of the expression (``123``) for the view to "match" the current
+ request.
- If ``request_param`` is not supplied, the view will be invoked
- without consideration of keys and values in the ``request.params``
- dictionary.
+ If ``request_param`` is not supplied, the view will be invoked without
+ consideration of keys and values in the ``request.params`` dictionary.
``containment``
- This value should be a reference to a Python class or
- :term:`interface` that a parent object in the context resource's
- :term:`lineage` must provide in order for this view to be found and
- called. The resources in your resource tree must be "location-aware" to
- use this feature.
+ This value should be a reference to a Python class or :term:`interface`
+ that a parent object in the context resource's :term:`lineage` must provide
+ in order for this view to be found and called. The resources in your
+ resource tree must be "location-aware" to use this feature.
- If ``containment`` is not supplied, the interfaces and classes in
- the lineage are not considered when deciding whether or not to
- invoke the view callable.
+ If ``containment`` is not supplied, the interfaces and classes in the
+ lineage are not considered when deciding whether or not to invoke the view
+ callable.
- See :ref:`location_aware` for more information about
- location-awareness.
+ See :ref:`location_aware` for more information about location-awareness.
``xhr``
This value should be either ``True`` or ``False``. If this value is
- specified and is ``True``, the :term:`WSGI` environment must possess
- an ``HTTP_X_REQUESTED_WITH`` (aka ``X-Requested-With``) header that
- has the value ``XMLHttpRequest`` for the associated view callable to
- be found and called. This is useful for detecting AJAX requests
- issued from jQuery, Prototype and other Javascript libraries.
-
- If ``xhr`` is not specified, the ``HTTP_X_REQUESTED_WITH`` HTTP
- header is not taken into consideration when deciding whether or not
- to invoke the associated view callable.
+ specified and is ``True``, the :term:`WSGI` environment must possess an
+ ``HTTP_X_REQUESTED_WITH`` (aka ``X-Requested-With``) header that has the
+ value ``XMLHttpRequest`` for the associated view callable to be found and
+ called. This is useful for detecting AJAX requests issued from jQuery,
+ Prototype and other Javascript libraries.
+
+ If ``xhr`` is not specified, the ``HTTP_X_REQUESTED_WITH`` HTTP header is
+ not taken into consideration when deciding whether or not to invoke the
+ associated view callable.
``accept``
The value of this argument represents a match query for one or more
mimetypes in the ``Accept`` HTTP request header. If this value is
- specified, it must be in one of the following forms: a mimetype
- match token in the form ``text/plain``, a wildcard mimetype match
- token in the form ``text/*`` or a match-all wildcard mimetype match
- token in the form ``*/*``. If any of the forms matches the
- ``Accept`` header of the request, this predicate will be true.
+ specified, it must be in one of the following forms: a mimetype match token
+ in the form ``text/plain``, a wildcard mimetype match token in the form
+ ``text/*`` or a match-all wildcard mimetype match token in the form
+ ``*/*``. If any of the forms matches the ``Accept`` header of the request,
+ this predicate will be true.
- If ``accept`` is not specified, the ``HTTP_ACCEPT`` HTTP header is
- not taken into consideration when deciding whether or not to invoke
- the associated view callable.
+ If ``accept`` is not specified, the ``HTTP_ACCEPT`` HTTP header is not
+ taken into consideration when deciding whether or not to invoke the
+ associated view callable.
``header``
- This value represents an HTTP header name or a header name/value
- pair.
+ This value represents an HTTP header name or a header name/value pair.
If ``header`` is specified, it must be a header name or a
``headername:headervalue`` pair.
If ``header`` is specified without a value (a bare header name only,
- e.g. ``If-Modified-Since``), the view will only be invoked if the
- HTTP header exists with any value in the request.
+ e.g. ``If-Modified-Since``), the view will only be invoked if the HTTP
+ header exists with any value in the request.
If ``header`` is specified, and possesses a name/value pair
- (e.g. ``User-Agent:Mozilla/.*``), the view will only be invoked if
- the HTTP header exists *and* the HTTP header matches the value
- requested. When the ``headervalue`` contains a ``:`` (colon), it
- will be considered a name/value pair (e.g. ``User-Agent:Mozilla/.*``
- or ``Host:localhost``). The value portion should be a regular
- expression.
+ (e.g. ``User-Agent:Mozilla/.*``), the view will only be invoked if the HTTP
+ header exists *and* the HTTP header matches the value requested. When the
+ ``headervalue`` contains a ``:`` (colon), it will be considered a
+ name/value pair (e.g. ``User-Agent:Mozilla/.*`` or ``Host:localhost``).
+ The value portion should be a regular expression.
- Whether or not the value represents a header name or a header
- name/value pair, the case of the header name is not significant.
+ Whether or not the value represents a header name or a header name/value
+ pair, the case of the header name is not significant.
- If ``header`` is not specified, the composition, presence or absence
- of HTTP headers is not taken into consideration when deciding
- whether or not to invoke the associated view callable.
+ If ``header`` is not specified, the composition, presence or absence of
+ HTTP headers is not taken into consideration when deciding whether or not
+ to invoke the associated view callable.
``path_info``
- This value represents a regular expression pattern that will be
- tested against the ``PATH_INFO`` WSGI environment variable to decide
- whether or not to call the associated view callable. If the regex
- matches, this predicate will be ``True``.
+ This value represents a regular expression pattern that will be tested
+ against the ``PATH_INFO`` WSGI environment variable to decide whether or
+ not to call the associated view callable. If the regex matches, this
+ predicate will be ``True``.
- If ``path_info`` is not specified, the WSGI ``PATH_INFO`` is not
- taken into consideration when deciding whether or not to invoke the
- associated view callable.
+ If ``path_info`` is not specified, the WSGI ``PATH_INFO`` is not taken into
+ consideration when deciding whether or not to invoke the associated view
+ callable.
``custom_predicates``
- If ``custom_predicates`` is specified, it must be a sequence of
- references to custom predicate callables. Use custom predicates
- when no set of predefined predicates do what you need. Custom
- predicates can be combined with predefined predicates as necessary.
- Each custom predicate callable should accept two arguments:
- ``context`` and ``request`` and should return either ``True`` or
- ``False`` after doing arbitrary evaluation of the context resource and/or the
- request. If all callables return ``True``, the associated view
- callable will be considered viable for a given request.
+ If ``custom_predicates`` is specified, it must be a sequence of references
+ to custom predicate callables. Use custom predicates when no set of
+ predefined predicates do what you need. Custom predicates can be combined
+ with predefined predicates as necessary. Each custom predicate callable
+ should accept two arguments: ``context`` and ``request`` and should return
+ either ``True`` or ``False`` after doing arbitrary evaluation of the
+ context resource and/or the request. If all callables return ``True``, the
+ associated view callable will be considered viable for a given request.
If ``custom_predicates`` is not specified, no custom predicates are
used.
@@ -1427,32 +821,27 @@ View Configuration Using the ``@view_config`` Decorator
~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
For better locality of reference, you may use the
-:class:`pyramid.view.view_config` decorator to associate your view
-functions with URLs instead of using :term:`ZCML` or imperative
-configuration for the same purpose.
+:class:`pyramid.view.view_config` decorator to associate your view functions
+with URLs instead of using :term:`ZCML` or imperative configuration for the
+same purpose.
.. warning::
- Using this feature tends to slows down application startup
- slightly, as more work is performed at application startup to scan
- for view declarations. Additionally, if you use decorators, it
- means that other people will not be able to override your view
- declarations externally using ZCML: this is a common requirement if
- you're developing an extensible application (e.g. a framework).
- See :ref:`extending_chapter` for more information about building
- extensible applications.
+ Using this feature tends to slows down application startup slightly, as
+ more work is performed at application startup to scan for view
+ declarations.
Usage of the ``view_config`` decorator is a form of :term:`declarative
configuration`, like ZCML, but in decorator form.
:class:`pyramid.view.view_config` can be used to associate :term:`view
configuration` information -- as done via the equivalent imperative code or
ZCML -- with a function that acts as a :app:`Pyramid` view callable. All
-arguments to the :meth:`pyramid.config.Configurator.add_view` method
-(save for the ``view`` argument) are available in decorator form and mean
-precisely the same thing.
+arguments to the :meth:`pyramid.config.Configurator.add_view` method (save
+for the ``view`` argument) are available in decorator form and mean precisely
+the same thing.
-An example of the :class:`pyramid.view.view_config` decorator might
-reside in a :app:`Pyramid` application module ``views.py``:
+An example of the :class:`pyramid.view.view_config` decorator might reside in
+a :app:`Pyramid` application module ``views.py``:
.. ignore-next-block
.. code-block:: python
@@ -1460,12 +849,12 @@ reside in a :app:`Pyramid` application module ``views.py``:
from resources import MyResource
from pyramid.view import view_config
- from pyramid.chameleon_zpt import render_template_to_response
+ from pyramid.response import Response
@view_config(name='my_view', request_method='POST', context=MyResource,
- permission='read', renderer='templates/my.pt')
+ permission='read')
def my_view(request):
- return {'a':1}
+ return Response('OK')
Using this decorator as above replaces the need to add this imperative
configuration stanza:
@@ -1490,18 +879,17 @@ All arguments to ``view_config`` may be omitted. For example:
""" My view """
return Response()
-Such a registration as the one directly above implies that the view
-name will be ``my_view``, registered with a ``context`` argument that
-matches any resource type, using no permission, registered against
-requests with any request method, request type, request param,
-route name, or containment.
+Such a registration as the one directly above implies that the view name will
+be ``my_view``, registered with a ``context`` argument that matches any
+resource type, using no permission, registered against requests with any
+request method, request type, request param, route name, or containment.
-The mere existence of a ``@view_config`` decorator doesn't suffice to
-perform view configuration. All that the decorator does is "annotate"
-the function with your configuration declarations, it doesn't process
-them. To make :app:`Pyramid` process your
-:class:`pyramid.view.view_config` declarations, you *must* do use the
-``scan`` method of a :class:`pyramid.config.Configurator`:
+The mere existence of a ``@view_config`` decorator doesn't suffice to perform
+view configuration. All that the decorator does is "annotate" the function
+with your configuration declarations, it doesn't process them. To make
+:app:`Pyramid` process your :class:`pyramid.view.view_config` declarations,
+you *must* do use the ``scan`` method of a
+:class:`pyramid.config.Configurator`:
.. code-block:: python
:linenos:
@@ -1518,18 +906,17 @@ about what happens when code is scanned for configuration declarations
resulting from use of decorators like :class:`pyramid.view.view_config`.
See :ref:`configuration_module` for additional API arguments to the
-:meth:`pyramid.config.Configurator.scan` method. For example, the
-method allows you to supply a ``package`` argument to better control exactly
-*which* code will be scanned.
+:meth:`pyramid.config.Configurator.scan` method. For example, the method
+allows you to supply a ``package`` argument to better control exactly *which*
+code will be scanned.
``@view_config`` Placement
++++++++++++++++++++++++++
-A :class:`pyramid.view.view_config` decorator can be placed in various
-points in your application.
+A :class:`pyramid.view.view_config` decorator can be placed in various points
+in your application.
-If your view callable is a function, it may be used as a function
-decorator:
+If your view callable is a function, it may be used as a function decorator:
.. code-block:: python
:linenos:
@@ -1541,11 +928,10 @@ decorator:
def edit(request):
return Response('edited!')
-If your view callable is a class, the decorator can also be used as a
-class decorator in Python 2.6 and better (Python 2.5 and below do not
-support class decorators). All the arguments to the decorator are the
-same when applied against a class as when they are applied against a
-function. For example:
+If your view callable is a class, the decorator can also be used as a class
+decorator in Python 2.6 and better (Python 2.5 and below do not support class
+decorators). All the arguments to the decorator are the same when applied
+against a class as when they are applied against a function. For example:
.. code-block:: python
:linenos:
@@ -1561,9 +947,9 @@ function. For example:
def __call__(self):
return Response('hello')
-You can use the :class:`pyramid.view.view_config` decorator as a
-simple callable to manually decorate classes in Python 2.5 and below
-without the decorator syntactic sugar, if you wish:
+You can use the :class:`pyramid.view.view_config` decorator as a simple
+callable to manually decorate classes in Python 2.5 and below without the
+decorator syntactic sugar, if you wish:
.. code-block:: python
:linenos:
@@ -1580,9 +966,9 @@ without the decorator syntactic sugar, if you wish:
my_view = view_config()(MyView)
-More than one :class:`pyramid.view.view_config` decorator can be
-stacked on top of any number of others. Each decorator creates a
-separate view registration. For example:
+More than one :class:`pyramid.view.view_config` decorator can be stacked on
+top of any number of others. Each decorator creates a separate view
+registration. For example:
.. code-block:: python
:linenos:
@@ -1613,20 +999,17 @@ The decorator can also be used against class methods:
def amethod(self):
return Response('hello')
-When the decorator is used against a class method, a view is
-registered for the *class*, so the class constructor must accept an
-argument list in one of two forms: either it must accept a single
-argument ``request`` or it must accept two arguments, ``context,
-request``.
+When the decorator is used against a class method, a view is registered for
+the *class*, so the class constructor must accept an argument list in one of
+two forms: either it must accept a single argument ``request`` or it must
+accept two arguments, ``context, request``.
-The method which is decorated must return a :term:`response` or it
-must rely on a :term:`renderer` to generate one.
+The method which is decorated must return a :term:`response`.
-Using the decorator against a particular method of a class is
-equivalent to using the ``attr`` parameter in a decorator attached to
-the class itself. For example, the above registration implied by the
-decorator being used against the ``amethod`` method could be spelled
-equivalently as the below:
+Using the decorator against a particular method of a class is equivalent to
+using the ``attr`` parameter in a decorator attached to the class itself.
+For example, the above registration implied by the decorator being used
+against the ``amethod`` method could be spelled equivalently as the below:
.. code-block:: python
:linenos:
@@ -1650,11 +1033,10 @@ equivalently as the below:
View Configuration Using the ``add_view`` Method of a Configurator
~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
-The :meth:`pyramid.config.Configurator.add_view` method
-within :ref:`configuration_module` is used to configure a view
-imperatively. The arguments to this method are very similar to the
-arguments that you provide to the ``@view_config`` decorator. For
-example:
+The :meth:`pyramid.config.Configurator.add_view` method within
+:ref:`configuration_module` is used to configure a view imperatively. The
+arguments to this method are very similar to the arguments that you provide
+to the ``@view_config`` decorator. For example:
.. code-block:: python
:linenos:
@@ -1668,11 +1050,10 @@ example:
# pyramid.config.Configurator class
config.add_view(hello_world, name='hello.html')
-The first argument, ``view``, is required. It must either be a Python
-object which is the view itself or a :term:`dotted Python name` to
-such an object. All other arguments are optional. See
-:meth:`pyramid.config.Configurator.add_view` for more
-information.
+The first argument, ``view``, is required. It must either be a Python object
+which is the view itself or a :term:`dotted Python name` to such an object.
+All other arguments are optional. See
+:meth:`pyramid.config.Configurator.add_view` for more information.
.. index::
single: resource interfaces
@@ -1794,11 +1175,11 @@ configuration using :meth:`pyramid.config.Configurator.add_view`:
config.add_view('myproject.views.add_entry', name='add.html',
context='myproject.resources.IBlog', permission='add')
-When an :term:`authorization policy` is enabled, this view will be
-protected with the ``add`` permission. The view will *not be called* if
-the user does not possess the ``add`` permission relative to the current
-:term:`context`. Instead the :term:`forbidden view` result will be
-returned to the client as per :ref:`protecting_views`.
+When an :term:`authorization policy` is enabled, this view will be protected
+with the ``add`` permission. The view will *not be called* if the user does
+not possess the ``add`` permission relative to the current :term:`context`.
+Instead the :term:`forbidden view` result will be returned to the client as
+per :ref:`protecting_views`.
.. index::
single: view lookup
@@ -1819,27 +1200,24 @@ set of circumstances implied by the context and request.
Predicate attributes of view configuration can be thought of like
"narrowers". In general, the greater number of predicate attributes
-possessed by a view's configuration, the more specific the
-circumstances need to be before the registered view callable will be
-invoked.
+possessed by a view's configuration, the more specific the circumstances need
+to be before the registered view callable will be invoked.
-For any given request, a view with five predicates will always be
-found and evaluated before a view with two, for example. All
-predicates must match for the associated view to be called.
+For any given request, a view with five predicates will always be found and
+evaluated before a view with two, for example. All predicates must match for
+the associated view to be called.
-This does not mean however, that :app:`Pyramid` "stops looking"
-when it finds a view registration with predicates that don't match.
-If one set of view predicates does not match, the "next most specific"
-view (if any) view is consulted for predicates, and so on, until a
-view is found, or no view can be matched up with the request. The
-first view with a set of predicates all of which match the request
-environment will be invoked.
+This does not mean however, that :app:`Pyramid` "stops looking" when it finds
+a view registration with predicates that don't match. If one set of view
+predicates does not match, the "next most specific" view (if any) view is
+consulted for predicates, and so on, until a view is found, or no view can be
+matched up with the request. The first view with a set of predicates all of
+which match the request environment will be invoked.
-If no view can be found with predicates which allow it to be
-matched up with the request, :app:`Pyramid` will return an error to
-the user's browser, representing a "not found" (404) page. See
-:ref:`changing_the_notfound_view` for more information about changing
-the default notfound view.
+If no view can be found with predicates which allow it to be matched up with
+the request, :app:`Pyramid` will return an error to the user's browser,
+representing a "not found" (404) page. See :ref:`changing_the_notfound_view`
+for more information about changing the default notfound view.
.. index::
single: debugging not found errors
@@ -1850,12 +1228,18 @@ the default notfound view.
:exc:`NotFound` Errors
~~~~~~~~~~~~~~~~~~~~~~
-It's useful to be able to debug :exc:`NotFound` error responses when
-they occur unexpectedly due to an application registry
-misconfiguration. To debug these errors, use the
-``BFG_DEBUG_NOTFOUND`` environment variable or the ``debug_notfound``
-configuration file setting. Details of why a view was not found will
-be printed to ``stderr``, and the browser representation of the error
-will include the same information. See :ref:`environment_chapter` for
+It's useful to be able to debug :exc:`NotFound` error responses when they
+occur unexpectedly due to an application registry misconfiguration. To debug
+these errors, use the ``BFG_DEBUG_NOTFOUND`` environment variable or the
+``debug_notfound`` configuration file setting. Details of why a view was not
+found will be printed to ``stderr``, and the browser representation of the
+error will include the same information. See :ref:`environment_chapter` for
more information about how, and where to set these values.
+Further Information
+-------------------
+
+The chapter entitled :ref:`renderers_chapter` explains how to create
+functions (or instances/classes) which do not return a :term:`Response`
+object, yet which still can be used as view callables.
+