summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorSteve Piercy <web@stevepiercy.com>2018-10-05 02:33:18 -0700
committerGitHub <noreply@github.com>2018-10-05 02:33:18 -0700
commit086198b5db7dcb86c2b4edbc5d3610dcade0332a (patch)
tree1af84e37e9ad7bdb445786a0345822dcdfd851f0
parent2fa1e218ea6b9a6d5c3f8193ea27d0fc44b8964a (diff)
parentf6becd23966248fb7fc4db218258be4364902f8f (diff)
downloadpyramid-086198b5db7dcb86c2b4edbc5d3610dcade0332a.tar.gz
pyramid-086198b5db7dcb86c2b4edbc5d3610dcade0332a.tar.bz2
pyramid-086198b5db7dcb86c2b4edbc5d3610dcade0332a.zip
Merge branch 'master' into one_cc
-rw-r--r--.github/ISSUE_TEMPLATE/bug_report.md31
-rw-r--r--.github/ISSUE_TEMPLATE/documentation.md29
-rw-r--r--.github/ISSUE_TEMPLATE/feature_request.md24
-rw-r--r--CHANGES.rst39
-rw-r--r--CONTRIBUTORS.txt1
-rw-r--r--COPYRIGHT.txt2
-rw-r--r--HACKING.txt88
-rw-r--r--MANIFEST.in2
-rw-r--r--TODO.txt7
-rw-r--r--contributing.md34
-rw-r--r--docs/api/config.rst1
-rw-r--r--docs/api/request.rst3
-rw-r--r--docs/api/session.rst8
-rw-r--r--docs/conf.py9
-rw-r--r--docs/glossary.rst6
-rw-r--r--docs/index.rst2
-rw-r--r--docs/narr/advconfig.rst1
-rw-r--r--docs/narr/introduction.rst4
-rw-r--r--docs/narr/project.rst24
-rw-r--r--docs/narr/sessions.rst83
-rw-r--r--docs/narr/subrequest.rst3
-rw-r--r--docs/narr/testing.rst4
-rw-r--r--docs/quick_tour.rst8
-rw-r--r--docs/quick_tutorial/databases.rst4
-rw-r--r--docs/quick_tutorial/forms.rst2
-rw-r--r--docs/quick_tutorial/functional_testing.rst2
-rw-r--r--docs/quick_tutorial/jinja2.rst2
-rw-r--r--docs/quick_tutorial/json.rst2
-rw-r--r--docs/quick_tutorial/logging.rst2
-rw-r--r--docs/quick_tutorial/more_view_classes.rst2
-rw-r--r--docs/quick_tutorial/request_response.rst2
-rw-r--r--docs/quick_tutorial/routing.rst2
-rw-r--r--docs/quick_tutorial/sessions.rst2
-rw-r--r--docs/quick_tutorial/static_assets.rst2
-rw-r--r--docs/quick_tutorial/templating.rst2
-rw-r--r--docs/quick_tutorial/unit_testing.rst4
-rw-r--r--docs/quick_tutorial/view_classes.rst2
-rw-r--r--docs/quick_tutorial/views.rst2
-rw-r--r--docs/tutorials/wiki/installation.rst30
-rw-r--r--docs/tutorials/wiki/tests.rst8
-rw-r--r--docs/tutorials/wiki2/definingviews.rst2
-rw-r--r--docs/tutorials/wiki2/installation.rst30
-rw-r--r--docs/tutorials/wiki2/tests.rst4
-rw-r--r--docs/typographical-conventions.rst2
-rw-r--r--pyramid/config/factories.py20
-rw-r--r--pyramid/interfaces.py8
-rw-r--r--pyramid/renderers.py10
-rw-r--r--pyramid/security.py28
-rw-r--r--pyramid/session.py59
-rw-r--r--pyramid/tests/test_config/test_factories.py60
-rw-r--r--pyramid/tests/test_renderers.py14
-rw-r--r--pyramid/tests/test_security.py7
-rw-r--r--setup.py4
53 files changed, 433 insertions, 300 deletions
diff --git a/.github/ISSUE_TEMPLATE/bug_report.md b/.github/ISSUE_TEMPLATE/bug_report.md
new file mode 100644
index 000000000..d6ab170f9
--- /dev/null
+++ b/.github/ISSUE_TEMPLATE/bug_report.md
@@ -0,0 +1,31 @@
+---
+name: Bug Report
+about: Create a report to help us improve
+
+---
+
+## Get Support
+To get help or technical support, see [Get Support](https://pylonsproject.org/community-support.html).
+
+## Bug Report
+
+Please [search the issue tracker](https://github.com/Pylons/pyramid/issues) for similar issues before submitting a new issue.
+
+**Describe the bug**
+A clear and concise description of the bug.
+
+**To Reproduce**
+Steps to reproduce the behavior:
+1. Go to '...'
+2. Click on '....'
+3. Scroll down to '....'
+4. See error
+
+**Expected behavior**
+A clear and concise description of what you expected to happen.
+
+**Screenshots**
+If applicable, add screenshots to help explain the issue.
+
+**Additional context**
+Add any other context about the issue here.
diff --git a/.github/ISSUE_TEMPLATE/documentation.md b/.github/ISSUE_TEMPLATE/documentation.md
new file mode 100644
index 000000000..1117a57aa
--- /dev/null
+++ b/.github/ISSUE_TEMPLATE/documentation.md
@@ -0,0 +1,29 @@
+---
+name: Documentation Suggestion
+about: Create an issue to improve our documentation
+
+---
+
+## Get Support
+To get help or technical support, see [Get Support](https://pylonsproject.org/community-support.html).
+
+## Documentation Suggestion
+
+Please [search the issue tracker](https://github.com/Pylons/pyramid/issues) for similar issues before submitting a new issue.
+
+**Describe the issue**
+A clear and concise description of the issue.
+
+**Include references**
+1. Go to the URL '...'
+2. Click on '....'
+3. Scroll down to '....'
+
+**Describe the improvement**
+A clear and concise description of your suggestion.
+
+**Screenshots**
+If applicable, add screenshots to help explain the issue.
+
+**Additional context**
+Add any other context about the issue here.
diff --git a/.github/ISSUE_TEMPLATE/feature_request.md b/.github/ISSUE_TEMPLATE/feature_request.md
new file mode 100644
index 000000000..f71d6b24e
--- /dev/null
+++ b/.github/ISSUE_TEMPLATE/feature_request.md
@@ -0,0 +1,24 @@
+---
+name: Feature Request
+about: Suggest an idea for this project
+
+---
+
+## Get Support
+To get help or technical support, see [Get Support](https://pylonsproject.org/community-support.html).
+
+## Feature Request
+
+Please [search the issue tracker](https://github.com/Pylons/pyramid/issues) for similar issues before submitting a new issue.
+
+**Is your feature request related to an issue? Please describe.**
+A clear and concise description of the issue. Example: "I'm always frustrated when [...]".
+
+**Describe the solution you'd like**
+A clear and concise description of what you want to happen.
+
+**Describe alternatives you've considered**
+A clear and concise description of any alternative solutions or features you've considered.
+
+**Additional context**
+Add any other context or screenshots about the feature request here.
diff --git a/CHANGES.rst b/CHANGES.rst
index d0dbbe5c0..4f0de298b 100644
--- a/CHANGES.rst
+++ b/CHANGES.rst
@@ -57,6 +57,15 @@ Features
- Add support for Python 3.7. Add testing on Python 3.8 with allowed failures.
See https://github.com/Pylons/pyramid/pull/3333
+- Added ``pyramid.session.JSONSerializer``. See "Upcoming Changes to ISession
+ in Pyramid 2.0" in the "Sessions" chapter of the documentation for more
+ information about this feature.
+ See https://github.com/Pylons/pyramid/pull/3353
+
+- Add a ``registry`` argument to ``pyramid.renderers.get_renderer``
+ to allow users to avoid threadlocals during renderer lookup.
+ See https://github.com/Pylons/pyramid/pull/3358
+
Bug Fixes
---------
@@ -79,6 +88,21 @@ Bug Fixes
Deprecations
------------
+- The ``pyramid.intefaces.ISession`` interface will move to require
+ JSON-serializable objects in Pyramid 2.0. See
+ "Upcoming Changes to ISession in Pyramid 2.0" in the "Sessions" chapter
+ of the documentation for more information about this change.
+ See https://github.com/Pylons/pyramid/pull/3353
+
+- The ``pyramid.session.signed_serialize`` and
+ ``pyramid.session.signed_deserialize`` functions will be removed in Pyramid
+ 2.0, along with the removal of
+ ``pyramid.session.UnencryptedCookieSessionFactoryConfig`` which was
+ deprecated in Pyramid 1.5. Please switch to using the
+ ``SignedCookieSessionFactory``, copying the code, or another session
+ implementation if you're still using these features.
+ See https://github.com/Pylons/pyramid/pull/3353
+
Backward Incompatibilities
--------------------------
@@ -107,9 +131,24 @@ Backward Incompatibilities
of previous ``pyramid.httpexceptions.HTTPFound``.
See https://github.com/Pylons/pyramid/pull/3328
+- Removed ``pyramid.config.Configurator.set_request_property`` which had been
+ deprecated since Pyramid 1.5. Instead use
+ ``pyramid.config.Configurator.add_request_method`` with ``reify=True`` or
+ ``property=True``.
+ See https://github.com/Pylons/pyramid/pull/3368
+
+- Removed the ``principal`` keyword argument from
+ ``pyramid.security.remember`` which had been deprecated since Pyramid 1.6
+ and replaced by the ``userid`` argument.
+ See https://github.com/Pylons/pyramid/pull/3369
+
Documentation Changes
---------------------
+- Ad support for Read The Docs Ethical Ads.
+ https://github.com/Pylons/pyramid/pull/3360
+ https://docs.readthedocs.io/en/latest/advertising/ethical-advertising.html
+
- Add support for alembic to the pyramid-cookiecutter-alchemy cookiecutter
and update the wiki2 tutorial to explain how it works.
See https://github.com/Pylons/pyramid/pull/3307 and
diff --git a/CONTRIBUTORS.txt b/CONTRIBUTORS.txt
index 0c18d600f..80b43c8ec 100644
--- a/CONTRIBUTORS.txt
+++ b/CONTRIBUTORS.txt
@@ -331,3 +331,4 @@ Contributors
- Kuzma Leshakov, 2018/09/07
+- Colin Dunklau, 2018/09/19
diff --git a/COPYRIGHT.txt b/COPYRIGHT.txt
index 645160fa5..6e23cb876 100644
--- a/COPYRIGHT.txt
+++ b/COPYRIGHT.txt
@@ -1,4 +1,4 @@
-Copyright (c) 2008-2011 Agendaless Consulting and Contributors.
+Copyright (c) 2008-2018 Agendaless Consulting and Contributors.
(http://www.agendaless.com), All Rights Reserved
Portions (c) Zope Foundation and contributors (http://www.zope.org/).
diff --git a/HACKING.txt b/HACKING.txt
index 3a7774781..132511e11 100644
--- a/HACKING.txt
+++ b/HACKING.txt
@@ -8,9 +8,13 @@ Using a Development Checkout
----------------------------
You'll have to create a development environment to hack on Pyramid, using a
-Pyramid checkout. You can either do this by hand, or if you have ``tox``
-installed (it's on PyPI), you can use ``tox`` to set up a working development
-environment. Each installation method is described below.
+Pyramid checkout. You can either do this by hand, or if you have `tox`
+installed, you can use it to set up a working development environment.
+
+tox docs: http://tox.readthedocs.org/en/latest/
+tox on PyPI: https://pypi.org/project/tox/
+
+Each installation method is described below.
By Hand
@@ -46,20 +50,20 @@ repo, from which you can submit a pull request.
$ cd ~/hack-on-pyramid
$ python3 -m venv env
- From here on in within these instructions, the ``~/hack-on-pyramid/env``
- virtual environment you created above will be referred to as ``$VENV``.
+ From here on in within these instructions, the `~/hack-on-pyramid/env`
+ virtual environment you created above will be referred to as `$VENV`.
To use the instructions in the steps that follow literally, use the
- ``export VENV=~/hack-on-pyramid/env`` command.
+ `export VENV=~/hack-on-pyramid/env` command.
- Install Pyramid from the checkout into the virtual environment, where the
- current working directory is the ``pyramid`` checkout directory. We will
+ current working directory is the `pyramid` checkout directory. We will
install Pyramid in editable (development) mode as well as its testing
requirements.
$ cd ~/hack-on-pyramid
$ $VENV/bin/pip install -e ".[testing,docs]"
-- Optionally create a new Pyramid project using ``pcreate``:
+- Optionally create a new Pyramid project using `pcreate`:
$ cd $VENV
$ bin/pcreate -s starter starter
@@ -70,13 +74,13 @@ repo, from which you can submit a pull request.
$ $VENV/bin/pip install -e .
-Using ``Tox``
-+++++++++++++
+Using `Tox`
++++++++++++
-Alternatively, if you already have ``tox`` installed, there is an easier
+Alternatively, if you already have `tox` installed, there is an easier
way to get going.
-- Create a new directory somewhere and ``cd`` to it:
+- Create a new directory somewhere and `cd` to it:
$ mkdir ~/hack-on-pyramid
$ cd ~/hack-on-pyramid
@@ -89,16 +93,15 @@ way to get going.
Since Pyramid is a framework and not an application, it can be convenient to
work against a sample application, preferably in its own virtual environment. A
-quick way to achieve this is to use `tox
-<http://tox.readthedocs.org/en/latest/>`_ with a custom configuration file
+quick way to achieve this is to use `tox` with a custom configuration file
that is part of the checkout:
$ tox -c hacking-tox.ini
-This will create a python-2.7 based virtual environment named ``env27``
-(Pyramid's ``.gitconfig` ignores all top-level folders that start with ``env``
+This will create a python-2.7 based virtual environment named `env27`
+(Pyramid's `.gitconfig` ignores all top-level folders that start with `env`
specifically in our use case), and inside that a simple pyramid application
-named ``hacking`` that you can then fire up like so:
+named `hacking` that you can then fire up like so:
$ cd env27/hacking
$ ../bin/pip install -e ".[testing,docs]"
@@ -111,7 +114,7 @@ Adding Features
In order to add a feature to Pyramid:
- The feature must be documented in both the API and narrative documentation
- (in ``docs/``).
+ (in `docs/`).
- The feature must work fully on the following CPython versions: 2.7, 3.4, 3.5,
3.6, and 3.7 on both UNIX and Windows.
@@ -127,7 +130,7 @@ In order to add a feature to Pyramid:
The above requirements are relaxed for scaffolding dependencies. If a scaffold
has an install-time dependency on something that doesn't work on a particular
platform, that caveat should be spelled out clearly in *its* documentation
-(within its ``docs/`` directory).
+(within its `docs/` directory).
Coding Style
@@ -147,11 +150,11 @@ Running Tests
- To run all tests for Pyramid on a single Python version from your development
virtual environment (See *Using a Development Checkout* above), run
- ``nosetests``:
+ `nosetests`:
$ $VENV/bin/nosetests
-- To run individual tests (i.e., during development), you can use ``nosetests``
+- To run individual tests (i.e., during development), you can use `nosetests`
syntax as follows:
# run a single test
@@ -160,14 +163,14 @@ Running Tests
# run all tests in a class
$ $VENV/bin/nosetests pyramid.tests.test_module:ClassName
- Optionally you can install a nose plugin, `nose-selecttests
- <https://pypi.org/project/nose-selecttests/>`_, and use a regular
- expression with the ``-t`` parameter to run tests.
+ Optionally you can install a nose plugin, `nose-selecttests`
+ ( https://pypi.org/project/nose-selecttests/ ), and use a regular
+ expression with the `-t` parameter to run tests.
# run a single test
$ $VENV/bin/nosetests -t test_mytestname
-- The ``tox.ini`` uses ``nose`` and ``coverage``. As such ``tox`` may be used
+- The `tox.ini` uses `nose` and `coverage`. As such `tox` may be used
to run groups of tests or only a specific version of Python. For example, the
following command will run tests on Python 2.7 only without coverage:
@@ -178,27 +181,26 @@ Running Tests
$ tox -e py2-cover,py3-cover,coverage
-- To run the full set of Pyramid tests on all platforms, install `tox
- <http://codespeak.net/~hpk/tox/>`_ into a system Python. The ``tox`` console
- script will be installed into the scripts location for that Python. While
- ``cd``'ed to the Pyramid checkout root directory (it contains ``tox.ini``),
- invoke the ``tox`` console script. This will read the ``tox.ini`` file and
- execute the tests on multiple Python versions and platforms. While it runs,
- it creates a virtual environment for each version/platform combination. For
- example:
+- To run the full set of Pyramid tests on all platforms, install `tox` into a
+ system Python. The `tox` console script will be installed into the scripts
+ location for that Python. While `cd`'ed to the Pyramid checkout root
+ directory (it contains `tox.ini`), invoke the `tox` console script. This
+ will read the `tox.ini` file and execute the tests on multiple Python
+ versions and platforms. While it runs, it creates a virtual environment
+ for each version/platform combination. For example:
$ sudo /usr/bin/pip install tox
$ cd ~/hack-on-pyramid/
$ /usr/bin/tox
-- The tests can also be run using `pytest <http://pytest.org/>`_. This is
+- The tests can also be run using `pytest` ( http://pytest.org/ ). This is
intended as a convenience for people who are more used to or fond of
- ``pytest``. Run the tests like so:
+ `pytest`. Run the tests like so:
$ $VENV/bin/pip install pytest
- $ $VENV/bin/py.test --strict pyramid/
+ $ $VENV/bin/pytest --strict pyramid/
- To run individual tests (i.e., during development), see "py.test usage -
+ To run individual tests (i.e., during development), see "pytest usage -
Specifying tests / selecting tests":
http://pytest.org/latest/usage.html#specifying-tests-selecting-tests
@@ -218,8 +220,8 @@ Test Coverage
-------------
- The codebase *must* have 100% test statement coverage after each commit. You
- can test coverage via ``./coverage.sh`` (which itself just executes ``tox
- -epy2-cover,py3-cover,coverage``).
+ can test coverage via `./coverage.sh` (which itself just executes `tox
+ -epy2-cover,py3-cover,coverage`).
Documentation Coverage and Building HTML Documentation
@@ -230,19 +232,19 @@ documentation in this package which references that API or behavior must be
changed to reflect the bug fix, ideally in the same commit that fixes the bug
or adds the feature. To build and review docs, use the following steps.
-1. In the main Pyramid checkout directory, run ``./builddocs.sh`` (which just
- turns around and runs ``tox -e docs``):
+1. In the main Pyramid checkout directory, run `./builddocs.sh` (which just
+ turns around and runs `tox -e docs`):
$ ./builddocs.sh
-2. Open the ``docs/_build/html/index.html`` file to see the resulting HTML
+2. Open the `docs/_build/html/index.html` file to see the resulting HTML
rendering.
Change Log
----------
-- Feature additions and bugfixes must be added to the ``CHANGES.rst``
+- Feature additions and bugfixes must be added to the `CHANGES.rst`
file in the prevailing style. Changelog entries should be long and
descriptive, not cryptic. Other developers should be able to know
what your changelog entry means.
diff --git a/MANIFEST.in b/MANIFEST.in
index 2e18ad5fe..c3391cbcc 100644
--- a/MANIFEST.in
+++ b/MANIFEST.in
@@ -8,9 +8,11 @@ include CONTRIBUTORS.txt LICENSE.txt COPYRIGHT.txt
include contributing.md RELEASING.txt
include tox.ini appveyor.yml .travis.yml rtd.txt
+graft .github
include HACKING.txt hacking-tox.ini
include builddocs.sh coverage.sh scaffoldtests.sh
include TODO.txt
global-exclude __pycache__ *.py[cod]
+global-exclude .DS_Store
diff --git a/TODO.txt b/TODO.txt
index a3ae9d8c0..318171931 100644
--- a/TODO.txt
+++ b/TODO.txt
@@ -111,13 +111,6 @@ Nice-to-Have
)
-Future
-------
-
-- 1.9: Remove set_request_property.
-- 1.9: Remove extra code enabling ``pyramid.security.remember(principal=...)``
- and force use of ``userid``.
-
Probably Bad Ideas
------------------
diff --git a/contributing.md b/contributing.md
index 3b960c1e1..40c42add7 100644
--- a/contributing.md
+++ b/contributing.md
@@ -1,28 +1,16 @@
-Contributing
-============
+# Contributing
-All projects under the Pylons Projects, including this one, follow the
-guidelines established at [How to
-Contribute](https://pylonsproject.org/community-how-to-contribute.html) and
-[Coding Style and
-Standards](https://pylonsproject.org/community-coding-style-standards.html).
+All projects under the Pylons Projects, including this one, follow the guidelines established at [How to Contribute](https://pylonsproject.org/community-how-to-contribute.html), [Coding Style and Standards](https://pylonsproject.org/community-coding-style-standards.html), and [Pylons Project Documentation Style Guide](https://docs.pylonsproject.org/projects/docs-style-guide/).
You can contribute to this project in several ways.
* [File an Issue on GitHub](https://github.com/Pylons/pyramid/issues)
-* Fork this project and create a branch with your suggested change. When ready,
- submit a pull request for consideration. [GitHub
- Flow](https://guides.github.com/introduction/flow/index.html) describes the
- workflow process and why it's a good practice. When submitting a pull
- request, sign
- [CONTRIBUTORS.txt](https://github.com/Pylons/pyramid/blob/master/CONTRIBUTORS.txt)
- if you have not yet done so.
-* Join the IRC channel #pyramid on irc.freenode.net.
-
-Git Branches
-------------
-Git branches and their purpose and status at the time of this writing are
-listed below.
+* Fork this project and create a branch with your suggested change. When ready, submit a pull request for consideration. [GitHub Flow](https://guides.github.com/introduction/flow/index.html) describes the workflow process and why it's a good practice. When submitting a pull request, sign [CONTRIBUTORS.txt](https://github.com/Pylons/pyramid/blob/master/CONTRIBUTORS.txt) if you have not yet done so.
+* Join the [IRC channel #pyramid on irc.freenode.net](https://webchat.freenode.net/?channels=pyramid).
+
+## Git Branches
+
+Git branches and their purpose and status at the time of this writing are listed below.
* [master](https://github.com/Pylons/pyramid/) - The branch on which further
development takes place. The default branch on GitHub.
@@ -34,16 +22,14 @@ listed below.
Older branches are not actively maintained. In general, two stable branches and
one or two development branches are actively maintained.
-Prerequisites
--------------
+## Prerequisites
Follow the instructions in HACKING.txt for your version or branch located in
the [root of the Pyramid repository](https://github.com/Pylons/pyramid/) to
install Pyramid and the tools needed to run its tests and build its
documentation.
-Building documentation for a Pylons Project project
----------------------------------------------------
+## Building documentation for a Pylons Project project
*Note:* These instructions might not work for Windows users. Suggestions to
improve the process for Windows users are welcome by submitting an issue or a
diff --git a/docs/api/config.rst b/docs/api/config.rst
index a785b64ad..b2cd53a68 100644
--- a/docs/api/config.rst
+++ b/docs/api/config.rst
@@ -44,7 +44,6 @@
:methodcategory:`Extending the Request Object`
.. automethod:: add_request_method
- .. automethod:: set_request_property
:methodcategory:`Using I18N`
diff --git a/docs/api/request.rst b/docs/api/request.rst
index b5700f4ab..0c169adaf 100644
--- a/docs/api/request.rst
+++ b/docs/api/request.rst
@@ -228,8 +228,7 @@
handed.
- sets request extensions (such as those added via
- :meth:`~pyramid.config.Configurator.add_request_method` or
- :meth:`~pyramid.config.Configurator.set_request_property`) on the
+ :meth:`~pyramid.config.Configurator.add_request_method`) on the
request it's passed.
- causes a :class:`~pyramid.events.NewRequest` event to be sent at the
diff --git a/docs/api/session.rst b/docs/api/session.rst
index 53bae7c52..d0cb112ec 100644
--- a/docs/api/session.rst
+++ b/docs/api/session.rst
@@ -5,15 +5,11 @@
.. automodule:: pyramid.session
- .. autofunction:: signed_serialize
-
- .. autofunction:: signed_deserialize
-
.. autofunction:: SignedCookieSessionFactory
- .. autofunction:: UnencryptedCookieSessionFactoryConfig
-
.. autofunction:: BaseCookieSessionFactory
.. autoclass:: PickleSerializer
+ .. autoclass:: JSONSerializer
+
diff --git a/docs/conf.py b/docs/conf.py
index 8fe7108ff..6e3d41240 100644
--- a/docs/conf.py
+++ b/docs/conf.py
@@ -161,6 +161,15 @@ html_theme_options = dict(
outdated='false',
)
+# Control display of sidebars
+html_sidebars = {'**': [
+ 'localtoc.html',
+ 'ethicalads.html',
+ 'relations.html',
+ 'sourcelink.html',
+ 'searchbox.html',
+]}
+
# The name for this set of Sphinx documents. If None, it defaults to
# "<project> v<release> documentation".
html_title = 'The Pyramid Web Framework v%s' % release
diff --git a/docs/glossary.rst b/docs/glossary.rst
index ae7d4cf42..8f94eeaca 100644
--- a/docs/glossary.rst
+++ b/docs/glossary.rst
@@ -343,7 +343,7 @@ Glossary
full-featured Python web framework.
Grok
- `A web framework based on Zope 3 <http://grok.zope.org>`_.
+ `A web framework based on Zope 3 <https://web.archive.org/web/20180615015013/http://grok.zope.org>`_.
Django
`A full-featured Python web framework <https://www.djangoproject.com/>`_.
@@ -853,7 +853,7 @@ Glossary
Localization
The process of displaying the user interface of an
internationalized application in a particular language or
- cultural context. Often shortened to "l10" (because the word
+ cultural context. Often shortened to "l10n" (because the word
"localization" is L, 10 letters, then N).
.. seealso::
@@ -1083,7 +1083,7 @@ Glossary
Green Unicorn
Aka ``gunicorn``, a fast :term:`WSGI` server that runs on Unix under
- Python 2.6+ or Python 3.1+. See http://gunicorn.org/ for detailed
+ Python 2.6+ or Python 3.1+. See https://gunicorn.org/ for detailed
information.
predicate factory
diff --git a/docs/index.rst b/docs/index.rst
index 76d23b4f4..19cff9414 100644
--- a/docs/index.rst
+++ b/docs/index.rst
@@ -66,7 +66,7 @@ Official tutorials provide a quick overview of :app:`Pyramid`'s features in more
Support and Development
=======================
-The `Pyramid website <https://trypyramid.com/resources.html>`_ is the main
+The `Pyramid website <https://trypyramid.com/documentation.html>`_ is the main
entry point to :app:`Pyramid` web framework resources for support and
development information.
diff --git a/docs/narr/advconfig.rst b/docs/narr/advconfig.rst
index 880e538f1..322741648 100644
--- a/docs/narr/advconfig.rst
+++ b/docs/narr/advconfig.rst
@@ -299,7 +299,6 @@ These are the methods of the configurator which provide conflict detection:
:meth:`~pyramid.config.Configurator.add_request_method`,
:meth:`~pyramid.config.Configurator.set_request_factory`,
:meth:`~pyramid.config.Configurator.set_session_factory`,
-:meth:`~pyramid.config.Configurator.set_request_property`,
:meth:`~pyramid.config.Configurator.set_root_factory`,
:meth:`~pyramid.config.Configurator.set_view_mapper`,
:meth:`~pyramid.config.Configurator.set_authentication_policy`,
diff --git a/docs/narr/introduction.rst b/docs/narr/introduction.rst
index cc1ecdbee..dada4e8bd 100644
--- a/docs/narr/introduction.rst
+++ b/docs/narr/introduction.rst
@@ -52,7 +52,7 @@ Modern
Tested
~~~~~~
-Untested code is broken by design. The :app:`Pyramid` community has a strong testing culture and our framework reflects that. Every release of :app:`Pyramid` has 100% statement coverage (as measured by `coverage <https://coverage.readthedocs.io/en/latest/>`_) and 95% decision/condition coverage. (as measured by `instrumental <https://instrumental.readthedocs.io/en/latest/intro.html>`_) It is automatically tested using `Travis <https://travis-ci.org/Pylons/pyramid>`_ and `Jenkins <http://jenkins.pylonsproject.org/job/pyramid/>`_ on supported versions of Python after each commit to its GitHub repository. `Official Pyramid add-ons <https://trypyramid.com/resources-extending-pyramid.html>`_ are held to a similar testing standard.
+Untested code is broken by design. The :app:`Pyramid` community has a strong testing culture and our framework reflects that. Every release of :app:`Pyramid` has 100% statement coverage (as measured by `coverage <https://coverage.readthedocs.io/en/latest/>`_) and 95% decision/condition coverage. (as measured by `instrumental <https://instrumental.readthedocs.io/en/latest/intro.html>`_) It is automatically tested using `Travis <https://travis-ci.org/Pylons/pyramid>`_ and `Jenkins <http://jenkins.pylonsproject.org/job/pyramid/>`_ on supported versions of Python after each commit to its GitHub repository. `Official Pyramid add-ons <https://trypyramid.com/extending-pyramid.html>`_ are held to a similar testing standard.
We still find bugs in :app:`Pyramid`, but we've noticed we find a lot fewer of them while working on projects with a solid testing regime.
@@ -173,7 +173,7 @@ Supported :app:`Pyramid` add-ons are held to the same demanding standards as the
.. seealso::
- See also https://trypyramid.com/resources-extending-pyramid.html
+ See also https://trypyramid.com/extending-pyramid.html
Write your views, *your* way
~~~~~~~~~~~~~~~~~~~~~~~~~~~~
diff --git a/docs/narr/project.rst b/docs/narr/project.rst
index 5560b02c0..84fd8e31f 100644
--- a/docs/narr/project.rst
+++ b/docs/narr/project.rst
@@ -242,26 +242,26 @@ On Windows:
%VENV%\Scripts\pip install -e ".[testing]"
Once the testing requirements are installed, then you can run the tests using
-the ``py.test`` command that was just installed in the ``bin`` directory of
+the ``pytest`` command that was just installed in the ``bin`` directory of
your virtual environment.
On Unix:
.. code-block:: bash
- $VENV/bin/py.test -q
+ $VENV/bin/pytest -q
On Windows:
.. code-block:: doscon
- %VENV%\Scripts\py.test -q
+ %VENV%\Scripts\pytest -q
Here's sample output from a test run on Unix:
.. code-block:: bash
- $VENV/bin/py.test -q
+ $VENV/bin/pytest -q
..
2 passed in 0.47 seconds
@@ -269,28 +269,28 @@ The tests themselves are found in the ``tests.py`` module in your ``cookiecutter
.. note::
- The ``-q`` option is passed to the ``py.test`` command to limit the output
+ The ``-q`` option is passed to the ``pytest`` command to limit the output
to a stream of dots. If you don't pass ``-q``, you'll see verbose test
result output (which normally isn't very useful).
Alternatively, if you'd like to see test coverage, pass the ``--cov`` option
-to ``py.test``:
+to ``pytest``:
.. code-block:: bash
- $VENV/bin/py.test --cov -q
+ $VENV/bin/pytest --cov -q
-Cookiecutters include configuration defaults for ``py.test`` and test coverage.
+Cookiecutters include configuration defaults for ``pytest`` and test coverage.
These configuration files are ``pytest.ini`` and ``.coveragerc``, located at
the root of your package. Without these defaults, we would need to specify the
path to the module on which we want to run tests and coverage.
.. code-block:: bash
- $VENV/bin/py.test --cov=myproject myproject/tests.py -q
+ $VENV/bin/pytest --cov=myproject myproject/tests.py -q
-.. seealso:: See py.test's documentation for :ref:`pytest:usage` or invoke
- ``py.test -h`` to see its full set of options.
+.. seealso:: See ``pytest``'s documentation for :ref:`pytest:usage` or invoke
+ ``pytest -h`` to see its full set of options.
.. index::
@@ -1047,7 +1047,7 @@ The ``tests.py`` module includes tests for your application.
:linenos:
This sample ``tests.py`` file has one unit test and one functional test defined
-within it. These tests are executed when you run ``py.test -q``. You may add
+within it. These tests are executed when you run ``pytest -q``. You may add
more tests here as you build your application. You are not required to write
tests to use :app:`Pyramid`. This file is simply provided for convenience and
example.
diff --git a/docs/narr/sessions.rst b/docs/narr/sessions.rst
index 2d80b1a63..ded7e87e3 100644
--- a/docs/narr/sessions.rst
+++ b/docs/narr/sessions.rst
@@ -59,25 +59,68 @@ using the :meth:`pyramid.config.Configurator.set_session_factory` method.
By default the :func:`~pyramid.session.SignedCookieSessionFactory`
implementation contains the following security concerns:
- - Session data is *unencrypted*. You should not use it when you keep
- sensitive information in the session object, as the information can be
- easily read by both users of your application and third parties who have
- access to your users' network traffic.
-
- - If you use this sessioning implementation, and you inadvertently create a
- cross-site scripting vulnerability in your application, because the
- session data is stored unencrypted in a cookie, it will also be easier for
- evildoers to obtain the current user's cross-site scripting token.
-
- - The default serialization method, while replaceable with something like
- JSON, is implemented using pickle which can lead to remote code execution
- if your secret key is compromised.
-
- In short, use a different session factory implementation (preferably one
- which keeps session data on the server) for anything but the most basic of
- applications where "session security doesn't matter", you are sure your
- application has no cross-site scripting vulnerabilities, and you are confident
- your secret key will not be exposed.
+ - Session data is *unencrypted* (but it is signed / authenticated).
+
+ This means an attacker cannot change the session data, but they can view it.
+ You should not use it when you keep sensitive information in the session object, as the information can be easily read by both users of your application and third parties who have access to your users' network traffic.
+
+ At the very least, use TLS and set ``secure=True`` to avoid arbitrary users on the network from viewing the session contents.
+
+ - If you use this sessioning implementation, and you inadvertently create a cross-site scripting vulnerability in your application, because the session data is stored unencrypted in a cookie, it will also be easier for evildoers to obtain the current user's cross-site scripting token.
+
+ Set ``httponly=True`` to mitigate this vulnerability by hiding the cookie from client-side JavaScript.
+
+ - The default serialization method, while replaceable with something like JSON, is implemented using pickle which can lead to remote code execution if your secret key is compromised.
+
+ To mitigate this, set ``serializer=pyramid.session.JSONSerializer()`` to use :class:`pyramid.session.JSONSerializer`. This option will be the default in :app:`Pyramid` 2.0.
+ See :ref:`pickle_session_deprecation` for more information about this change.
+
+ In short, use a different session factory implementation (preferably one which keeps session data on the server) for anything but the most basic of applications where "session security doesn't matter", you are sure your application has no cross-site scripting vulnerabilities, and you are confident your secret key will not be exposed.
+
+.. index::
+ triple: pickle deprecation; JSON-serializable; ISession interface
+
+.. _pickle_session_deprecation:
+
+Upcoming Changes to ISession in Pyramid 2.0
+-------------------------------------------
+
+In :app:`Pyramid` 2.0 the :class:`pyramid.interfaces.ISession` interface will be changing to require that session implementations only need to support JSON-serializable data types.
+This is a stricter contract than the current requirement that all objects be pickleable and it is being done for security purposes.
+This is a backward-incompatible change.
+Currently, if a client-side session implementation is compromised, it leaves the application vulnerable to remote code execution attacks using specially-crafted sessions that execute code when deserialized.
+
+For users with compatibility concerns, it's possible to craft a serializer that can handle both formats until you are satisfied that clients have had time to reasonably upgrade.
+Remember that sessions should be short-lived and thus the number of clients affected should be small (no longer than an auth token, at a maximum). An example serializer:
+
+.. code-block:: python
+ :linenos:
+
+ from pyramid.session import JSONSerializer
+ from pyramid.session import PickleSerializer
+ from pyramid.session import SignedCookieSessionFactory
+
+ class JSONSerializerWithPickleFallback(object):
+ def __init__(self):
+ self.json = JSONSerializer()
+ self.pickle = PickleSerializer()
+
+ def dumps(self, value):
+ # maybe catch serialization errors here and keep using pickle
+ # while finding spots in your app that are not storing
+ # JSON-serializable objects, falling back to pickle
+ return self.json.dumps(value)
+
+ def loads(self, value):
+ try:
+ return self.json.loads(value)
+ except ValueError:
+ return self.pickle.loads(value)
+
+ # somewhere in your configuration code
+ serializer = JSONSerializerWithPickleFallback()
+ session_factory = SignedCookieSessionFactory(..., serializer=serializer)
+ config.set_session_factory(session_factory)
.. index::
single: session object
@@ -139,7 +182,7 @@ Some gotchas:
that they are instances of basic types of objects, such as strings, lists,
dictionaries, tuples, integers, etc. If you place an object in a session
data key or value that is not pickleable, an error will be raised when the
- session is serialized.
+ session is serialized. Please also see :ref:`pickle_session_deprecation`.
- If you place a mutable value (for example, a list or a dictionary) in a
session object, and you subsequently mutate that value, you must call the
diff --git a/docs/narr/subrequest.rst b/docs/narr/subrequest.rst
index 9094c7d83..03f372446 100644
--- a/docs/narr/subrequest.rst
+++ b/docs/narr/subrequest.rst
@@ -232,8 +232,7 @@ unconditionally does the following:
callable) to the request object to which it is handed.
- It sets request extensions (such as those added via
- :meth:`~pyramid.config.Configurator.add_request_method` or
- :meth:`~pyramid.config.Configurator.set_request_property`) on the subrequest
+ :meth:`~pyramid.config.Configurator.add_request_method`) on the subrequest
object passed as ``request``.
- It causes a :class:`~pyramid.events.NewRequest` event to be sent at the
diff --git a/docs/narr/testing.rst b/docs/narr/testing.rst
index ad4ba2186..8048ca62c 100644
--- a/docs/narr/testing.rst
+++ b/docs/narr/testing.rst
@@ -275,7 +275,7 @@ without needing to invoke the actual application configuration implied by its
In the above example, we create a ``MyTest`` test case that inherits from
:class:`unittest.TestCase`. If it's in our :app:`Pyramid` application, it will
-be found when ``py.test`` is run. It has two test methods.
+be found when ``pytest`` is run. It has two test methods.
The first test method, ``test_view_fn_forbidden`` tests the ``view_fn`` when
the authentication policy forbids the current user the ``edit`` permission. Its
@@ -365,7 +365,7 @@ Functional tests test your literal application.
In Pyramid, functional tests are typically written using the :term:`WebTest`
package, which provides APIs for invoking HTTP(S) requests to your application.
-We also like ``py.test`` and ``pytest-cov`` to provide simple testing and
+We also like ``pytest`` and ``pytest-cov`` to provide simple testing and
coverage reports.
Regardless of which testing :term:`package` you use, be sure to add a
diff --git a/docs/quick_tour.rst b/docs/quick_tour.rst
index ce0fed275..05c2ed7f6 100644
--- a/docs/quick_tour.rst
+++ b/docs/quick_tour.rst
@@ -680,8 +680,8 @@ the relevant ``.ini`` configuration file.
:ref:`Quick Tutorial pyramid_debugtoolbar <qtut_debugtoolbar>` and
:ref:`pyramid_debugtoolbar <toolbar:overview>`
-Unit tests and ``py.test``
-==========================
+Unit tests and ``pytest``
+=========================
Yikes! We got this far and we haven't yet discussed tests. This is particularly
egregious, as Pyramid has had a deep commitment to full test coverage since
@@ -689,7 +689,7 @@ before its release.
Our ``pyramid-cookiecutter-starter`` cookiecutter generated a ``tests.py`` module with
one unit test and one functional test in it. It also configured ``setup.py`` with test requirements:
-``py.test`` as the test runner, ``WebTest`` for running view tests, and the
+``pytest`` as the test runner, ``WebTest`` for running view tests, and the
``pytest-cov`` tool which yells at us for code that isn't tested:
.. literalinclude:: quick_tour/package/setup.py
@@ -706,7 +706,7 @@ We already installed the test requirements when we ran the command ``$VENV/bin/p
.. code-block:: bash
- $VENV/bin/py.test --cov --cov-report=term-missing
+ $VENV/bin/pytest --cov --cov-report=term-missing
This yields the following output.
diff --git a/docs/quick_tutorial/databases.rst b/docs/quick_tutorial/databases.rst
index 2e656f565..dcf411d23 100644
--- a/docs/quick_tutorial/databases.rst
+++ b/docs/quick_tutorial/databases.rst
@@ -128,11 +128,11 @@ Steps
.. literalinclude:: databases/tutorial/tests.py
:linenos:
-#. Run the tests in your package using ``py.test``:
+#. Run the tests in your package using ``pytest``:
.. code-block:: bash
- $VENV/bin/py.test tutorial/tests.py -q
+ $VENV/bin/pytest tutorial/tests.py -q
..
2 passed in 1.41 seconds
diff --git a/docs/quick_tutorial/forms.rst b/docs/quick_tutorial/forms.rst
index be745764b..f064a4baf 100644
--- a/docs/quick_tutorial/forms.rst
+++ b/docs/quick_tutorial/forms.rst
@@ -91,7 +91,7 @@ Steps
.. code-block:: bash
- $VENV/bin/py.test tutorial/tests.py -q
+ $VENV/bin/pytest tutorial/tests.py -q
..
2 passed in 0.45 seconds
diff --git a/docs/quick_tutorial/functional_testing.rst b/docs/quick_tutorial/functional_testing.rst
index fa56b4589..7c4dcee26 100644
--- a/docs/quick_tutorial/functional_testing.rst
+++ b/docs/quick_tutorial/functional_testing.rst
@@ -53,7 +53,7 @@ Steps
.. code-block:: bash
- $VENV/bin/py.test tutorial/tests.py -q
+ $VENV/bin/pytest tutorial/tests.py -q
..
2 passed in 0.25 seconds
diff --git a/docs/quick_tutorial/jinja2.rst b/docs/quick_tutorial/jinja2.rst
index 87122a374..6c33e406e 100644
--- a/docs/quick_tutorial/jinja2.rst
+++ b/docs/quick_tutorial/jinja2.rst
@@ -50,7 +50,7 @@ Steps
.. code-block:: bash
- $VENV/bin/py.test tutorial/tests.py -q
+ $VENV/bin/pytest tutorial/tests.py -q
....
4 passed in 0.40 seconds
diff --git a/docs/quick_tutorial/json.rst b/docs/quick_tutorial/json.rst
index 98283424c..44d1de8cb 100644
--- a/docs/quick_tutorial/json.rst
+++ b/docs/quick_tutorial/json.rst
@@ -54,7 +54,7 @@ Steps
.. code-block:: bash
- $VENV/bin/py.test tutorial/tests.py -q
+ $VENV/bin/pytest tutorial/tests.py -q
.....
5 passed in 0.47 seconds
diff --git a/docs/quick_tutorial/logging.rst b/docs/quick_tutorial/logging.rst
index ccbb7970f..f4a368bfa 100644
--- a/docs/quick_tutorial/logging.rst
+++ b/docs/quick_tutorial/logging.rst
@@ -54,7 +54,7 @@ Steps
.. code-block:: bash
- $VENV/bin/py.test tutorial/tests.py -q
+ $VENV/bin/pytest tutorial/tests.py -q
....
4 passed in 0.41 seconds
diff --git a/docs/quick_tutorial/more_view_classes.rst b/docs/quick_tutorial/more_view_classes.rst
index 15452e9ae..684fb1c43 100644
--- a/docs/quick_tutorial/more_view_classes.rst
+++ b/docs/quick_tutorial/more_view_classes.rst
@@ -105,7 +105,7 @@ Steps
.. code-block:: bash
- $VENV/bin/py.test tutorial/tests.py -q
+ $VENV/bin/pytest tutorial/tests.py -q
..
2 passed in 0.40 seconds
diff --git a/docs/quick_tutorial/request_response.rst b/docs/quick_tutorial/request_response.rst
index 098753820..f7753f222 100644
--- a/docs/quick_tutorial/request_response.rst
+++ b/docs/quick_tutorial/request_response.rst
@@ -61,7 +61,7 @@ Steps
.. code-block:: bash
- $VENV/bin/py.test tutorial/tests.py -q
+ $VENV/bin/pytest tutorial/tests.py -q
.....
5 passed in 0.30 seconds
diff --git a/docs/quick_tutorial/routing.rst b/docs/quick_tutorial/routing.rst
index 0384892b2..a6538a75f 100644
--- a/docs/quick_tutorial/routing.rst
+++ b/docs/quick_tutorial/routing.rst
@@ -79,7 +79,7 @@ Steps
.. code-block:: bash
- $VENV/bin/py.test tutorial/tests.py -q
+ $VENV/bin/pytest tutorial/tests.py -q
..
2 passed in 0.39 seconds
diff --git a/docs/quick_tutorial/sessions.rst b/docs/quick_tutorial/sessions.rst
index d67a5063a..8a67d6a0f 100644
--- a/docs/quick_tutorial/sessions.rst
+++ b/docs/quick_tutorial/sessions.rst
@@ -60,7 +60,7 @@ Steps
.. code-block:: bash
- $VENV/bin/py.test tutorial/tests.py -q
+ $VENV/bin/pytest tutorial/tests.py -q
....
4 passed in 0.42 seconds
diff --git a/docs/quick_tutorial/static_assets.rst b/docs/quick_tutorial/static_assets.rst
index 7a6b5dac3..567328307 100644
--- a/docs/quick_tutorial/static_assets.rst
+++ b/docs/quick_tutorial/static_assets.rst
@@ -54,7 +54,7 @@ Steps
.. code-block:: bash
- $VENV/bin/py.test tutorial/tests.py -q
+ $VENV/bin/pytest tutorial/tests.py -q
....
5 passed in 0.50 seconds
diff --git a/docs/quick_tutorial/templating.rst b/docs/quick_tutorial/templating.rst
index 3fbef699c..4d4ccea4f 100644
--- a/docs/quick_tutorial/templating.rst
+++ b/docs/quick_tutorial/templating.rst
@@ -92,7 +92,7 @@ Steps
.. code-block:: bash
- $VENV/bin/py.test tutorial/tests.py -q
+ $VENV/bin/pytest tutorial/tests.py -q
....
4 passed in 0.46 seconds
diff --git a/docs/quick_tutorial/unit_testing.rst b/docs/quick_tutorial/unit_testing.rst
index 09e3ea197..48cffd0e1 100644
--- a/docs/quick_tutorial/unit_testing.rst
+++ b/docs/quick_tutorial/unit_testing.rst
@@ -62,7 +62,7 @@ Steps
.. code-block:: bash
- $VENV/bin/py.test tutorial/tests.py -q
+ $VENV/bin/pytest tutorial/tests.py -q
.
1 passed in 0.14 seconds
@@ -96,7 +96,7 @@ Extra credit
============
#. Change the test to assert that the response status code should be ``404``
- (meaning, not found). Run ``py.test`` again. Read the error report and see
+ (meaning, not found). Run ``pytest`` again. Read the error report and see
if you can decipher what it is telling you.
#. As a more realistic example, put the ``tests.py`` back as you found it, and
diff --git a/docs/quick_tutorial/view_classes.rst b/docs/quick_tutorial/view_classes.rst
index fc7ba5125..4b7b78140 100644
--- a/docs/quick_tutorial/view_classes.rst
+++ b/docs/quick_tutorial/view_classes.rst
@@ -61,7 +61,7 @@ Steps
.. code-block:: bash
- $VENV/bin/py.test tutorial/tests.py -q
+ $VENV/bin/pytest tutorial/tests.py -q
....
4 passed in 0.34 seconds
diff --git a/docs/quick_tutorial/views.rst b/docs/quick_tutorial/views.rst
index f7fa64719..45bc8518b 100644
--- a/docs/quick_tutorial/views.rst
+++ b/docs/quick_tutorial/views.rst
@@ -68,7 +68,7 @@ Steps
.. code-block:: bash
- $VENV/bin/py.test tutorial/tests.py -q
+ $VENV/bin/pytest tutorial/tests.py -q
....
4 passed in 0.28 seconds
diff --git a/docs/tutorials/wiki/installation.rst b/docs/tutorials/wiki/installation.rst
index 2502c47b6..d0037e584 100644
--- a/docs/tutorials/wiki/installation.rst
+++ b/docs/tutorials/wiki/installation.rst
@@ -205,22 +205,22 @@ Run the tests
After you've installed the project in development mode as well as the testing
requirements, you may run the tests for the project. The following commands
-provide options to py.test that specify the module for which its tests shall be
-run, and to run py.test in quiet mode.
+provide options to ``pytest`` that specify the module for which its tests shall be
+run, and to run ``pytest`` in quiet mode.
On Unix
^^^^^^^
.. code-block:: bash
- $VENV/bin/py.test -q
+ $VENV/bin/pytest -q
On Windows
^^^^^^^^^^
.. code-block:: doscon
- %VENV%\Scripts\py.test -q
+ %VENV%\Scripts\pytest -q
For a successful test run, you should see output that ends like this:
@@ -233,8 +233,8 @@ For a successful test run, you should see output that ends like this:
Expose test coverage information
--------------------------------
-You can run the ``py.test`` command to see test coverage information. This
-runs the tests in the same way that ``py.test`` does, but provides additional
+You can run the ``pytest`` command to see test coverage information. This
+runs the tests in the same way that ``pytest`` does, but provides additional
:term:`coverage` information, exposing which lines of your project are covered by the
tests.
@@ -246,14 +246,14 @@ On Unix
.. code-block:: bash
- $VENV/bin/py.test --cov --cov-report=term-missing
+ $VENV/bin/pytest --cov --cov-report=term-missing
On Windows
^^^^^^^^^^
.. code-block:: doscon
- %VENV%\Scripts\py.test --cov --cov-report=term-missing
+ %VENV%\Scripts\pytest --cov --cov-report=term-missing
If successful, you will see output something like this:
@@ -285,7 +285,7 @@ Our package doesn't quite have 100% test coverage.
Test and coverage cookiecutter defaults
---------------------------------------
-The Pyramid cookiecutter includes configuration defaults for ``py.test`` and
+The Pyramid cookiecutter includes configuration defaults for ``pytest`` and
test coverage. These configuration files are ``pytest.ini`` and
``.coveragerc``, located at the root of your package. Without these defaults,
we would need to specify the path to the module on which we want to run tests
@@ -296,22 +296,22 @@ On Unix
.. code-block:: bash
- $VENV/bin/py.test --cov=tutorial tutorial/tests.py -q
+ $VENV/bin/pytest --cov=tutorial tutorial/tests.py -q
On Windows
^^^^^^^^^^
.. code-block:: doscon
- %VENV%\Scripts\py.test --cov=tutorial tutorial\tests.py -q
+ %VENV%\Scripts\pytest --cov=tutorial tutorial\tests.py -q
-py.test follows :ref:`conventions for Python test discovery
+``pytest`` follows :ref:`conventions for Python test discovery
<pytest:test discovery>`, and the configuration defaults from the cookiecutter
-tell ``py.test`` where to find the module on which we want to run tests and
+tell ``pytest`` where to find the module on which we want to run tests and
coverage.
-.. seealso:: See py.test's documentation for :ref:`pytest:usage` or invoke
- ``py.test -h`` to see its full set of options.
+.. seealso:: See ``pytest``'s documentation for :ref:`pytest:usage` or invoke
+ ``pytest -h`` to see its full set of options.
.. _wiki-start-the-application:
diff --git a/docs/tutorials/wiki/tests.rst b/docs/tutorials/wiki/tests.rst
index 353813e91..fdd218add 100644
--- a/docs/tutorials/wiki/tests.rst
+++ b/docs/tutorials/wiki/tests.rst
@@ -52,22 +52,22 @@ follows:
Running the tests
=================
-We can run these tests by using ``py.test`` similarly to how we did in
+We can run these tests by using ``pytest`` similarly to how we did in
:ref:`running_tests`. Courtesy of the cookiecutter, our testing dependencies have
-already been satisfied and ``py.test`` and coverage have already been
+already been satisfied and ``pytest`` and coverage have already been
configured, so we can jump right to running tests.
On Unix:
.. code-block:: bash
- $VENV/bin/py.test -q
+ $VENV/bin/pytest -q
On Windows:
.. code-block:: doscon
- %VENV%\Scripts\py.test -q
+ %VENV%\Scripts\pytest -q
The expected result should look like the following:
diff --git a/docs/tutorials/wiki2/definingviews.rst b/docs/tutorials/wiki2/definingviews.rst
index b73338f52..d10d862f5 100644
--- a/docs/tutorials/wiki2/definingviews.rst
+++ b/docs/tutorials/wiki2/definingviews.rst
@@ -149,7 +149,7 @@ We'll describe each one briefly in the following sections.
.. note::
- There is nothing special about the filename ``default.py`` exept that it is a
+ There is nothing special about the filename ``default.py`` except that it is a
Python module. A project may have many view callables throughout its codebase
in arbitrarily named modules. Modules implementing view callables often have
``view`` in their name (or may live in a Python subpackage of your
diff --git a/docs/tutorials/wiki2/installation.rst b/docs/tutorials/wiki2/installation.rst
index e04aea68e..924927cd4 100644
--- a/docs/tutorials/wiki2/installation.rst
+++ b/docs/tutorials/wiki2/installation.rst
@@ -353,22 +353,22 @@ Run the tests
After you've installed the project in development mode as well as the testing
requirements, you may run the tests for the project. The following commands
-provide options to py.test that specify the module for which its tests shall be
-run, and to run py.test in quiet mode.
+provide options to ``pytest`` that specify the module for which its tests shall be
+run, and to run ``pytest`` in quiet mode.
On Unix
^^^^^^^
.. code-block:: bash
- $VENV/bin/py.test -q
+ $VENV/bin/pytest -q
On Windows
^^^^^^^^^^
.. code-block:: doscon
- %VENV%\Scripts\py.test -q
+ %VENV%\Scripts\pytest -q
For a successful test run, you should see output that ends like this:
@@ -381,8 +381,8 @@ For a successful test run, you should see output that ends like this:
Expose test coverage information
--------------------------------
-You can run the ``py.test`` command to see test coverage information. This
-runs the tests in the same way that ``py.test`` does, but provides additional
+You can run the ``pytest`` command to see test coverage information. This
+runs the tests in the same way that ``pytest`` does, but provides additional
:term:`coverage` information, exposing which lines of your project are covered by the
tests.
@@ -394,14 +394,14 @@ On Unix
.. code-block:: bash
- $VENV/bin/py.test --cov --cov-report=term-missing
+ $VENV/bin/pytest --cov --cov-report=term-missing
On Windows
^^^^^^^^^^
.. code-block:: doscon
- c:\tutorial> %VENV%\Scripts\py.test --cov --cov-report=term-missing
+ c:\tutorial> %VENV%\Scripts\pytest --cov --cov-report=term-missing
If successful, you will see output something like this:
@@ -440,7 +440,7 @@ Our package doesn't quite have 100% test coverage.
Test and coverage cookiecutter defaults
---------------------------------------
-Cookiecutters include configuration defaults for ``py.test`` and test coverage.
+Cookiecutters include configuration defaults for ``pytest`` and test coverage.
These configuration files are ``pytest.ini`` and ``.coveragerc``, located at
the root of your package. Without these defaults, we would need to specify the
path to the module on which we want to run tests and coverage.
@@ -450,22 +450,22 @@ On Unix
.. code-block:: bash
- $VENV/bin/py.test --cov=tutorial tutorial/tests.py -q
+ $VENV/bin/pytest --cov=tutorial tutorial/tests.py -q
On Windows
^^^^^^^^^^
.. code-block:: doscon
- %VENV%\Scripts\py.test --cov=tutorial tutorial\tests.py -q
+ %VENV%\Scripts\pytest --cov=tutorial tutorial\tests.py -q
-py.test follows :ref:`conventions for Python test discovery
+pytest follows :ref:`conventions for Python test discovery
<pytest:test discovery>`, and the configuration defaults from the cookiecutter
-tell ``py.test`` where to find the module on which we want to run tests and
+tell ``pytest`` where to find the module on which we want to run tests and
coverage.
-.. seealso:: See py.test's documentation for :ref:`pytest:usage` or invoke
- ``py.test -h`` to see its full set of options.
+.. seealso:: See ``pytest``'s documentation for :ref:`pytest:usage` or invoke
+ ``pytest -h`` to see its full set of options.
.. _wiki2-start-the-application:
diff --git a/docs/tutorials/wiki2/tests.rst b/docs/tutorials/wiki2/tests.rst
index a8c35aa51..941a50928 100644
--- a/docs/tutorials/wiki2/tests.rst
+++ b/docs/tutorials/wiki2/tests.rst
@@ -99,14 +99,14 @@ On Unix:
.. code-block:: bash
rm tutorial.sqlite
- $VENV/bin/py.test -q
+ $VENV/bin/pytest -q
On Windows:
.. code-block:: doscon
del tutorial.sqlite
- %VENV%\Scripts\py.test -q
+ %VENV%\Scripts\pytest -q
The expected result should look like the following:
diff --git a/docs/typographical-conventions.rst b/docs/typographical-conventions.rst
index 76fdf8ace..7f052cbc8 100644
--- a/docs/typographical-conventions.rst
+++ b/docs/typographical-conventions.rst
@@ -128,7 +128,7 @@ When a command that should be typed on one line is too long to fit on the displa
.. code-block:: bash
- $VENV/bin/py.test tutorial/tests.py --cov-report term-missing \
+ $VENV/bin/pytest tutorial/tests.py --cov-report term-missing \
--cov=tutorial -q
diff --git a/pyramid/config/factories.py b/pyramid/config/factories.py
index 7a5b589cf..52248269d 100644
--- a/pyramid/config/factories.py
+++ b/pyramid/config/factories.py
@@ -1,4 +1,3 @@
-from zope.deprecation import deprecated
from zope.interface import implementer
from pyramid.interfaces import (
@@ -216,25 +215,6 @@ class FactoriesConfiguratorMixin(object):
introspectables=(intr,))
@action_method
- def set_request_property(self, callable, name=None, reify=False):
- """ Add a property to the request object.
-
- .. deprecated:: 1.5
- :meth:`pyramid.config.Configurator.add_request_method` should be
- used instead. (This method was docs-deprecated in 1.4 and
- issues a real deprecation warning in 1.5).
-
- .. versionadded:: 1.3
- """
- self.add_request_method(
- callable, name=name, property=not reify, reify=reify)
-
- deprecated(
- set_request_property,
- 'set_request_propery() is deprecated as of Pyramid 1.5; use '
- 'add_request_method() with the property=True argument instead')
-
- @action_method
def set_execution_policy(self, policy):
"""
Override the :app:`Pyramid` :term:`execution policy` in the
diff --git a/pyramid/interfaces.py b/pyramid/interfaces.py
index bedfb60b3..551ab701e 100644
--- a/pyramid/interfaces.py
+++ b/pyramid/interfaces.py
@@ -960,6 +960,14 @@ class ISession(IDict):
Keys and values of a session must be pickleable.
+ .. warning::
+
+ In :app:`Pyramid` 2.0 the session will only be required to support
+ types that can be serialized using JSON. It's recommended to switch any
+ session implementations to support only JSON and to only store primitive
+ types in sessions. See :ref:`pickle_session_deprecation` for more
+ information about why this change is being made.
+
.. versionchanged:: 1.9
Sessions are no longer required to implement ``get_csrf_token`` and
diff --git a/pyramid/renderers.py b/pyramid/renderers.py
index 6019f50fb..d1c85b371 100644
--- a/pyramid/renderers.py
+++ b/pyramid/renderers.py
@@ -147,7 +147,7 @@ def render_to_response(renderer_name,
return result
-def get_renderer(renderer_name, package=None):
+def get_renderer(renderer_name, package=None, registry=None):
""" Return the renderer object for the renderer ``renderer_name``.
You may supply a relative asset spec as ``renderer_name``. If
@@ -157,10 +157,16 @@ def get_renderer(renderer_name, package=None):
asset specification ``renderer_name``. If ``package`` is ``None``
(the default), the package name of the *caller* of this function
will be used as the package.
+
+ You may directly supply an :term:`application registry` using the
+ ``registry`` argument, and it will be used to look up the renderer.
+ Otherwise, the current thread-local registry (obtained via
+ :func:`~pyramid.threadlocal.get_current_registry`) will be used.
"""
if package is None:
package = caller_package()
- helper = RendererHelper(name=renderer_name, package=package)
+ helper = RendererHelper(name=renderer_name, package=package,
+ registry=registry)
return helper.renderer
# concrete renderer factory implementations (also API)
diff --git a/pyramid/security.py b/pyramid/security.py
index 4e9672d6a..0bdca090b 100644
--- a/pyramid/security.py
+++ b/pyramid/security.py
@@ -17,8 +17,6 @@ Authenticated = 'system.Authenticated'
Allow = 'Allow'
Deny = 'Deny'
-_marker = object()
-
class AllPermissionsList(object):
""" Stand in 'permission list' to represent all permissions """
@@ -120,7 +118,7 @@ deprecated(
'"effective_principals" attribute of the Pyramid request instead.'
)
-def remember(request, userid=_marker, **kw):
+def remember(request, userid, **kw):
"""
Returns a sequence of header tuples (e.g. ``[('Set-Cookie', 'foo=abc')]``)
on this request's response.
@@ -143,24 +141,14 @@ def remember(request, userid=_marker, **kw):
always return an empty sequence. If used, the composition and
meaning of ``**kw`` must be agreed upon by the calling code and
the effective authentication policy.
-
- .. deprecated:: 1.6
- Renamed the ``principal`` argument to ``userid`` to clarify its
- purpose.
+
+ .. versionchanged:: 1.6
+ Deprecated the ``principal`` argument in favor of ``userid`` to clarify
+ its relationship to the authentication policy.
+
+ .. versionchanged:: 1.10
+ Removed the deprecated ``principal`` argument.
"""
- if userid is _marker:
- principal = kw.pop('principal', _marker)
- if principal is _marker:
- raise TypeError(
- 'remember() missing 1 required positional argument: '
- '\'userid\'')
- else:
- deprecated(
- 'principal',
- 'The "principal" argument was deprecated in Pyramid 1.6. '
- 'It will be removed in Pyramid 1.9. Use the "userid" '
- 'argument instead.')
- userid = principal
policy = _get_authentication_policy(request)
if policy is None:
return []
diff --git a/pyramid/session.py b/pyramid/session.py
index 97039a404..b953fa184 100644
--- a/pyramid/session.py
+++ b/pyramid/session.py
@@ -4,11 +4,15 @@ import hashlib
import hmac
import os
import time
+import warnings
from zope.deprecation import deprecated
from zope.interface import implementer
-from webob.cookies import SignedSerializer
+from webob.cookies import (
+ JSONSerializer,
+ SignedSerializer,
+)
from pyramid.compat import (
pickle,
@@ -60,6 +64,14 @@ def signed_serialize(data, secret):
cookieval = signed_serialize({'a':1}, 'secret')
response.set_cookie('signed_cookie', cookieval)
+
+ .. deprecated:: 1.10
+
+ This function will be removed in :app:`Pyramid` 2.0. It is using
+ pickle-based serialization, which is considered vulnerable to remote
+ code execution attacks and will no longer be used by the default
+ session factories at that time.
+
"""
pickled = pickle.dumps(data, pickle.HIGHEST_PROTOCOL)
try:
@@ -70,6 +82,13 @@ def signed_serialize(data, secret):
sig = hmac.new(secret, pickled, hashlib.sha1).hexdigest()
return sig + native_(base64.b64encode(pickled))
+deprecated(
+ 'signed_serialize',
+ 'This function will be removed in Pyramid 2.0. It is using pickle-based '
+ 'serialization, which is considered vulnerable to remote code execution '
+ 'attacks.',
+)
+
def signed_deserialize(serialized, secret, hmac=hmac):
""" Deserialize the value returned from ``signed_serialize``. If
the value cannot be deserialized for any reason, a
@@ -82,6 +101,13 @@ def signed_deserialize(serialized, secret, hmac=hmac):
cookieval = request.cookies['signed_cookie']
data = signed_deserialize(cookieval, 'secret')
+
+ .. deprecated:: 1.10
+
+ This function will be removed in :app:`Pyramid` 2.0. It is using
+ pickle-based serialization, which is considered vulnerable to remote
+ code execution attacks and will no longer be used by the default
+ session factories at that time.
"""
# hmac parameterized only for unit tests
try:
@@ -105,6 +131,13 @@ def signed_deserialize(serialized, secret, hmac=hmac):
return pickle.loads(pickled)
+deprecated(
+ 'signed_deserialize',
+ 'This function will be removed in Pyramid 2.0. It is using pickle-based '
+ 'serialization, which is considered vulnerable to remote code execution '
+ 'attacks.',
+)
+
class PickleSerializer(object):
""" A serializer that uses the pickle protocol to dump Python
@@ -131,6 +164,10 @@ class PickleSerializer(object):
"""Accept a Python object and return bytes."""
return pickle.dumps(appstruct, self.protocol)
+
+JSONSerializer = JSONSerializer # api
+
+
def BaseCookieSessionFactory(
serializer,
cookie_name='session',
@@ -145,8 +182,6 @@ def BaseCookieSessionFactory(
set_on_exception=True,
):
"""
- .. versionadded:: 1.5
-
Configure a :term:`session factory` which will provide cookie-based
sessions. The return value of this function is a :term:`session factory`,
which may be provided as the ``session_factory`` argument of a
@@ -508,6 +543,7 @@ deprecated(
'so existing user session data will be destroyed if you switch to it.'
)
+
def SignedCookieSessionFactory(
secret,
cookie_name='session',
@@ -618,14 +654,31 @@ def SignedCookieSessionFactory(
should be raised for malformed inputs. If a serializer is not passed,
the :class:`pyramid.session.PickleSerializer` serializer will be used.
+ .. warning::
+
+ In :app:`Pyramid` 2.0 the default ``serializer`` option will change to
+ use :class:`pyramid.session.JSONSerializer`. See
+ :ref:`pickle_session_deprecation` for more information about why this
+ change is being made.
+
.. versionadded: 1.5a3
.. versionchanged: 1.10
Added the ``samesite`` option and made the default ``Lax``.
+
"""
if serializer is None:
serializer = PickleSerializer()
+ warnings.warn(
+ 'The default pickle serializer is deprecated as of Pyramid 1.9 '
+ 'and it will be changed to use pyramid.session.JSONSerializer in '
+ 'version 2.0. Explicitly set the serializer to avoid future '
+ 'incompatibilities. See "Upcoming Changes to ISession in '
+ 'Pyramid 2.0" for more information about this change.',
+ DeprecationWarning,
+ stacklevel=1,
+ )
signed_serializer = SignedSerializer(
secret,
diff --git a/pyramid/tests/test_config/test_factories.py b/pyramid/tests/test_config/test_factories.py
index eb1f3534c..7e6ea0476 100644
--- a/pyramid/tests/test_config/test_factories.py
+++ b/pyramid/tests/test_config/test_factories.py
@@ -161,63 +161,3 @@ class TestFactoriesMixin(unittest.TestCase):
registry = config.registry
result = registry.queryUtility(IExecutionPolicy)
self.assertEqual(result, default_execution_policy)
-
-class TestDeprecatedFactoriesMixinMethods(unittest.TestCase):
- def setUp(self):
- from zope.deprecation import __show__
- __show__.off()
-
- def tearDown(self):
- from zope.deprecation import __show__
- __show__.on()
-
- def _makeOne(self, *arg, **kw):
- from pyramid.config import Configurator
- config = Configurator(*arg, **kw)
- return config
-
- def test_set_request_property_with_callable(self):
- from pyramid.interfaces import IRequestExtensions
- config = self._makeOne(autocommit=True)
- callable = lambda x: None
- config.set_request_property(callable, name='foo')
- exts = config.registry.getUtility(IRequestExtensions)
- self.assertTrue('foo' in exts.descriptors)
-
- def test_set_request_property_with_unnamed_callable(self):
- from pyramid.interfaces import IRequestExtensions
- config = self._makeOne(autocommit=True)
- def foo(self): pass
- config.set_request_property(foo, reify=True)
- exts = config.registry.getUtility(IRequestExtensions)
- self.assertTrue('foo' in exts.descriptors)
-
- def test_set_request_property_with_property(self):
- from pyramid.interfaces import IRequestExtensions
- config = self._makeOne(autocommit=True)
- callable = property(lambda x: None)
- config.set_request_property(callable, name='foo')
- exts = config.registry.getUtility(IRequestExtensions)
- self.assertTrue('foo' in exts.descriptors)
-
- def test_set_multiple_request_properties(self):
- from pyramid.interfaces import IRequestExtensions
- config = self._makeOne()
- def foo(self): pass
- bar = property(lambda x: None)
- config.set_request_property(foo, reify=True)
- config.set_request_property(bar, name='bar')
- config.commit()
- exts = config.registry.getUtility(IRequestExtensions)
- self.assertTrue('foo' in exts.descriptors)
- self.assertTrue('bar' in exts.descriptors)
-
- def test_set_multiple_request_properties_conflict(self):
- from pyramid.exceptions import ConfigurationConflictError
- config = self._makeOne()
- def foo(self): pass
- bar = property(lambda x: None)
- config.set_request_property(foo, name='bar', reify=True)
- config.set_request_property(bar, name='bar')
- self.assertRaises(ConfigurationConflictError, config.commit)
-
diff --git a/pyramid/tests/test_renderers.py b/pyramid/tests/test_renderers.py
index 86d8b582a..a2f7bf8c2 100644
--- a/pyramid/tests/test_renderers.py
+++ b/pyramid/tests/test_renderers.py
@@ -624,6 +624,20 @@ class Test_get_renderer(unittest.TestCase):
result = self._callFUT('abc/def.pt', package=pyramid.tests)
self.assertEqual(result, renderer)
+ def test_it_with_registry(self):
+ renderer = self.config.testing_add_renderer(
+ 'pyramid.tests:abc/def.pt')
+ result = self._callFUT('abc/def.pt', registry=self.config.registry)
+ self.assertEqual(result, renderer)
+
+ def test_it_with_isolated_registry(self):
+ from pyramid.config import Configurator
+ isolated_config = Configurator()
+ renderer = isolated_config.testing_add_renderer(
+ 'pyramid.tests:abc/def.pt')
+ result = self._callFUT('abc/def.pt', registry=isolated_config.registry)
+ self.assertEqual(result, renderer)
+
class TestJSONP(unittest.TestCase):
def _makeOne(self, param_name='callback'):
from pyramid.renderers import JSONP
diff --git a/pyramid/tests/test_security.py b/pyramid/tests/test_security.py
index 1da73ff73..e5399ecdf 100644
--- a/pyramid/tests/test_security.py
+++ b/pyramid/tests/test_security.py
@@ -183,13 +183,6 @@ class TestRemember(unittest.TestCase):
result = self._callFUT(request, 'me')
self.assertEqual(result, [('X-Pyramid-Test', 'me')])
- def test_with_deprecated_principal_arg(self):
- request = _makeRequest()
- registry = request.registry
- _registerAuthenticationPolicy(registry, 'yo')
- result = self._callFUT(request, principal='me')
- self.assertEqual(result, [('X-Pyramid-Test', 'me')])
-
def test_with_missing_arg(self):
request = _makeRequest()
registry = request.registry
diff --git a/setup.py b/setup.py
index 10ed3fa23..d3d453a0d 100644
--- a/setup.py
+++ b/setup.py
@@ -41,9 +41,9 @@ tests_require = [
docs_extras = [
- 'Sphinx >= 1.7.4',
+ 'Sphinx >= 1.8.1',
'docutils',
- 'pylons-sphinx-themes',
+ 'pylons-sphinx-themes >= 1.0.8',
'pylons_sphinx_latesturl',
'repoze.sphinx.autointerface',
'sphinxcontrib-autoprogram',