summaryrefslogtreecommitdiff
path: root/docs
diff options
context:
space:
mode:
Diffstat (limited to 'docs')
-rw-r--r--docs/narr/threadlocals.rst176
-rw-r--r--docs/narr/views.rst2
-rw-r--r--docs/whatsnew-1.1.rst2
3 files changed, 95 insertions, 85 deletions
diff --git a/docs/narr/threadlocals.rst b/docs/narr/threadlocals.rst
index b97d9e4f2..9eef3e233 100644
--- a/docs/narr/threadlocals.rst
+++ b/docs/narr/threadlocals.rst
@@ -3,14 +3,14 @@
Thread Locals
=============
-A thread local variable is a variable that appears to be a "global"
-variable to an application which uses it. However, unlike a true
-global variable, one thread or process serving the application may
-receive a different value than another thread or process when that
+A :term:`thread local` variable is a variable that appears to be a
+"global" variable to an application which uses it. However, unlike a
+true global variable, one thread or process serving the application
+may receive a different value than another thread or process when that
variable is "thread local".
-When a request is processed, :mod:`repoze.bfg` makes two "thread
-local" variables available to the application: a "registry" and a
+When a request is processed, :mod:`repoze.bfg` makes two :term:`thread
+local` variables available to the application: a "registry" and a
"request".
Why and How :mod:`repoze.bfg` Uses Thread Local Variables
@@ -27,20 +27,21 @@ bad idea, at least if code readability counts as an important concern.
For historical reasons, however, thread local variables are indeed
consulted by various :mod:`repoze.bfg` API functions. For example,
the implementation of the :mod:`repoze.bfg.security` function named
-``authenticated_userid`` retrieves the thread local :term:`application
-registry` as a matter of course to find a :term:`authentication
-policy`. It uses the ``repoze.bfg.threadlocal.get_current_registry``
-function to retrieve the registry, from which it looks up the
+:func:`repoze.bfg.security.authenticated_userid` retrieves the thread
+local :term:`application registry` as a matter of course to find a
+:term:`authentication policy`. It uses the
+:func:`repoze.bfg.threadlocal.get_current_registry` function to
+retrieve the application registry, from which it looks up the
authentication policy; it then uses the authentication policy to
retrieve the authenticated user id. This is how :mod:`repoze.bfg`
allows arbitrary authentication policies to be "plugged in".
When they need to do so, :mod:`repoze.bfg` internals use two API
functions to retrieve the :term:`request` and :term:`application
-registry`: ``repoze.bfg.threadlocal.get_current_request`` and
-``repoze.bfg.threadlocal.get_current_registry``. The former returns
-the "current" request; the latter returns the "current" registry.
-Both ``get_current_*`` functions retrieve an object from a
+registry`: :func:`repoze.bfg.threadlocal.get_current_request` and
+:func:`repoze.bfg.threadlocal.get_current_registry`. The former
+returns the "current" request; the latter returns the "current"
+registry. Both ``get_current_*`` functions retrieve an object from a
thread-local data structure. These API functions are documented in
:ref:`threadlocal_module`.
@@ -48,15 +49,15 @@ These values are thread locals rather than true globals because one
Python process may be handling multiple simultaneous requests or even
multiple :mod:`repoze.bfg` applications. If they were true globals,
:mod:`repoze.bfg` could not handle multiple simultaneous requests or
-allow more than one BFG application instance to exist in a single
-Python process.
+allow more than one :mod:`repoze.bfg` application instance to exist in
+a single Python process.
Because one :mod:`repoze.bfg` application is permitted to call
*another* :mod:`repoze.bfg` application from its own :term:`view` code
-(perhaps as a :term:`WSGI` app with help from the ``wsgiapp2``
-decorator in :ref:`wsgi_module`), these variables are managed in a
-*stack* during normal system operations. The stack instance itself is
-a `threading.local
+(perhaps as a :term:`WSGI` app with help from the
+:func:`repoze.bfg.wsgi.wsgiapp2` decorator), these variables are
+managed in a *stack* during normal system operations. The stack
+instance itself is a `threading.local
<http://docs.python.org/library/threading.html#threading.local>`_.
During normal operations, the thread locals stack is managed by a
@@ -69,10 +70,11 @@ defined entirely by the behavior of a repoze.bfg :term:`Router`.
However, during unit testing, no Router code is ever invoked, and the
definition of "current" is defined by the boundary between calls to
-the ``begin`` and ``end`` methods of a :term:`Configurator` (or,
-pre-1.2a6, between calls to the ``repoze.bfg.testing.setUp`` and
-``repoze.bfg.testing.tearDown`` functions). These functions push and
-pop the threadlocal stack when the system is under test. See
+the :meth:`repoze.bfg.configuration.Configurator.begin` and
+:meth:`repoze.bfg.configuration.Configurator.end` methods (or between
+calls to the :func:`repoze.bfg.testing.setUp` and
+:func:`repoze.bfg.testing.tearDown` functions). These functions push
+and pop the threadlocal stack when the system is under test. See
:ref:`test_setup_and_teardown` for the definitions of these functions.
Scripts which use :mod:`repoze.bfg` machinery but never actually start
@@ -80,71 +82,79 @@ a WSGI server or receive requests via HTTP such as scripts which use
the :mod:`repoze.bfg.scripting`` API will never cause any Router code
to be executed. However, the :mod:`repoze.bfg.scripting` APIs also
push some values on to the thread locals stack as a matter of course.
-Such scripts should expect the ``get_current_request`` function to
-always return ``None``, and should expect the ``get_current_registry``
-function to return exactly the same :term:`application registry` for
-every request.
+Such scripts should expect the
+:func:`repoze.bfg.threadlocal.get_current_request` function to always
+return ``None``, and should expect the
+:func:`repoze.bfg.threadlocal.get_current_registry` function to return
+exactly the same :term:`application registry` for every request.
Why You Shouldn't Abuse Thread Locals
-------------------------------------
-You probably should almost never use the ``get_current_request`` or
-``get_current_registry`` functions, except perhaps in tests. In
-particular, it's almost always a mistake to use
-``get_current_request`` or ``get_current_registry`` in application
+You probably should almost never use the
+:func:`repoze.bfg.threadlocal.get_current_request` or
+:func:`repoze.bfg.threadlocal.get_current_registry` functions, except
+perhaps in tests. In particular, it's almost always a mistake to use
+:func:`repoze.bfg.threadlocal.get_current_request` or
+:func:`repoze.bfg.threadlocal.get_current_registry` in application
code because its usage makes it possible to write code that can be
neither easily tested nor scripted. Inappropriate usage is defined as
follows:
-- ``get_current_request`` should never be called within :term:`view`
- code, or code called by view code. View code already has access to
- the request (it's passed in).
-
-- ``get_current_request`` should never be called in :term:`model`
- code. Model code should never require any access to the request; if
- your model code requires access to a request object, you've almost
- certainly factored something wrong, and you should change your code
- rather than using this function.
-
-- The ``get_current_request`` function should never be called because
- it's "easier" or "more elegant" to think about calling it than to
- pass a request through a series of function calls when creating some
- API design. Your application should instead almost certainly pass
- data derived from the request around rather than relying on being
- able to call this function to obtain the request in places that
- actually have no business knowing about it. Parameters are *meant*
- to be passed around as function arguments, this is why they exist.
- Don't try to "save typing" or create "nicer APIs" by using this
- function in the place where a request is required; this will only
- lead to sadness later.
-
-- Neither ``get_current_request`` nor ``get_current_registry`` should
- ever be called within application-specific forks of third-party
- library code. The library you've forked almost certainly has
- nothing to do with :mod:`repoze.bfg`, and making it dependent on
- repoze.bfg (rather than making your :mod:`repoze.bfg` application
- depend upon it) means you're forming a dependency in the wrong
- direction.
-
-Use of the ``get_current_request`` function in application code *is*
-still useful in very limited circumstances. As a rule of thumb, usage
-of ``get_current_request`` is useful **within code which is meant to
-eventually be removed**. For instance, you may find yourself wanting
-to deprecate some API that expects to be passed a request object in
-favor of one that does not expect to be passed a request object. But
-you need to keep implementations of the old API working for some
-period of time while you deprecate the older API. So you write a
-"facade" implementation of the new API which calls into the code which
-implements the older API. Since the new API does not require the
-request, your facade implementation doesn't have local access to the
-request when it needs to pass it into the older API implementation.
-After some period of time, the older implementation code is disused
-and the hack that uses ``get_current_request`` is removed. This would
-be an appropriate place to use the ``get_current_request`` function.
-
-Use of the ``get_current_registry`` function should be limited to
-testing scenarios. The registry made current by use of a
-Configurator's ``begin`` method during a test (or pre-1.2a6, via
-``repoze.bfg.testing.setUp``) when you do not pass one in is available
-to you via this API.
+- :func:`repoze.bfg.threadlocal.get_current_request` should never be
+ called within the body of a :term:`view callable`, or within code
+ called by a view callable. View callables already have access to
+ the request (it's passed in to each as ``request``).
+
+- :func:`repoze.bfg.threadlocal.get_current_request` should never be
+ called in :term:`model` code. Model code should never require any
+ access to the request; if your model code requires access to a
+ request object, you've almost certainly factored something wrong,
+ and you should change your code rather than using this function.
+
+- :func:`repoze.bfg.threadlocal.get_current_request` function should
+ never be called because it's "easier" or "more elegant" to think
+ about calling it than to pass a request through a series of function
+ calls when creating some API design. Your application should
+ instead almost certainly pass data derived from the request around
+ rather than relying on being able to call this function to obtain
+ the request in places that actually have no business knowing about
+ it. Parameters are *meant* to be passed around as function
+ arguments, this is why they exist. Don't try to "save typing" or
+ create "nicer APIs" by using this function in the place where a
+ request is required; this will only lead to sadness later.
+
+- Neither :func:`repoze.bfg.threadlocal.get_current_request` nor
+ :func:`repoze.bfg.threadlocal.get_current_registry` should ever be
+ called within application-specific forks of third-party library
+ code. The library you've forked almost certainly has nothing to do
+ with :mod:`repoze.bfg`, and making it dependent on repoze.bfg
+ (rather than making your :mod:`repoze.bfg` application depend upon
+ it) means you're forming a dependency in the wrong direction.
+
+Use of the :func:`repoze.bfg.threadlocal.get_current_request` function
+in application code *is* still useful in very limited circumstances.
+As a rule of thumb, usage of
+:func:`repoze.bfg.threadlocal.get_current_request` is useful **within
+code which is meant to eventually be removed**. For instance, you may
+find yourself wanting to deprecate some API that expects to be passed
+a request object in favor of one that does not expect to be passed a
+request object. But you need to keep implementations of the old API
+working for some period of time while you deprecate the older API. So
+you write a "facade" implementation of the new API which calls into
+the code which implements the older API. Since the new API does not
+require the request, your facade implementation doesn't have local
+access to the request when it needs to pass it into the older API
+implementation. After some period of time, the older implementation
+code is disused and the hack that uses
+:func:`repoze.bfg.threadlocal.get_current_request` is removed. This
+would be an appropriate place to use the
+:func:`repoze.bfg.threadlocal.get_current_request` function.
+
+Use of the :func:`repoze.bfg.threadlocal.get_current_registry`
+function should be limited to testing scenarios. The registry made
+current by use of the
+:meth:`repoze.bfg.configuration.Configurator.begin` method during a
+test (or via :func:`repoze.bfg.testing.setUp`) when you do not pass
+one in is available to you via this API.
diff --git a/docs/narr/views.rst b/docs/narr/views.rst
index 5c512c902..8fda32240 100644
--- a/docs/narr/views.rst
+++ b/docs/narr/views.rst
@@ -224,7 +224,7 @@ the ``renderer`` attribute. For example, this ZCML associates the
There is 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. See :ref:`built_in_renders` for
+render a dictionary to a response. See :ref:`built_in_renderers` for
the available built-in renderers.
If the ``view`` callable associated with a ``view`` directive returns
diff --git a/docs/whatsnew-1.1.rst b/docs/whatsnew-1.1.rst
index 1847bfc1c..fa2af3e94 100644
--- a/docs/whatsnew-1.1.rst
+++ b/docs/whatsnew-1.1.rst
@@ -278,7 +278,7 @@ language to render a dictionary to a response. For example:
def my_view(context, request):
return {'abc':123}
-See :ref:`built_in_renders` for the available built-in renderers.
+See :ref:`built_in_renderers` for the available built-in renderers.
If the ``view`` callable associated with a ``view`` directive returns
a Response object (an object with the attributes ``status``,