Improve patrole core documentation

Updates patrole's current documentation with improved formatting.
Also updates many sections to add more clarity and detail.

Change-Id: Idebe341e2fcb0ee04db979d41df9bef5395af1b5
This commit is contained in:
Felipe Monteiro 2017-04-19 21:11:46 +01:00
parent 3f4158d935
commit 7bc35dc0cc
6 changed files with 204 additions and 51 deletions

View File

@ -1,4 +1,6 @@
patrole Style Commandments
===============================================
Patrole Style Commandments
==========================
Read the OpenStack Style Commandments http://docs.openstack.org/developer/hacking/
Read the OpenStack Style Commandments: `<http://docs.openstack.org/developer/hacking/>`__
Also review Tempest's Style Commandments: `<https://docs.openstack.org/developer/tempest/HACKING.html>`__

View File

@ -1,10 +1,11 @@
=======
patrole
=======
========
Overview
========
Patrole is a tool for verifying that Role-Based Access Control is being enforced.
Patrole is a tool for verifying that Role-Based Access Control is being
correctly enforced.
Patrole allows users to run API tests using specified RBAC roles. This allows
Patrole allows users to run API tests using specified RBAC roles. This allows
deployments to verify that only intended roles have access to those APIs.
This is critical to ensure security, especially in large deployments with
custom roles.
@ -15,18 +16,144 @@ custom roles.
* Bugs: http://bugs.launchpad.net/patrole
Features
--------
Patrole offers RBAC testing for various OpenStack RBAC policies. It includes
========
Patrole offers RBAC testing for various OpenStack RBAC policies. It includes
a decorator that wraps around tests which verifies that when the test calls the
corresponding api endpoint, access is only granted for correct roles.
corresponding API endpoint, access is only granted for correct roles.
Currently, Patrole supports policies contained in code and in policy.json files.
If both exist, the policy actions in the policy.json are prioritized.
.. _test-flows:
Test Flows
----------
There are several possible test flows.
If the rbac_test_role is allowed to access the endpoint
- The test passes if no 403 forbidden or RbacActionFailed exception is raised.
If the ``rbac_test_role`` is allowed to access the endpoint:
If the rbac_test_role is not allowed to access the endpoint
- If the endpoint returns a 403 forbidden exception the test will pass
- If the endpoint returns something other than a 403 forbidden to indicate
that the role is not allowed, the test will raise an RbacActionFailed exception.
* The test passes if no 403 ``Forbidden`` or ``RbacActionFailed`` exception is raised.
If the ``rbac_test_role`` is not allowed to access the endpoint:
* If the endpoint returns a 403 `Forbidden` exception the test will pass.
* If the endpoint returns successfully, then the test will fail with an
``RbacOverPermission`` exception.
* If the endpoint returns something other than a 403 ``Forbidden`` to indicate
that the role is not allowed, the test will raise an ``RbacActionFailed`` exception.
.. note::
Certain services like Neutron *intentionally* raise a 404 instead of a 403
for security concerns. Patrole accomodates this behavior by anticipating
a 404 instead of a 403, if specified through a special argument. For more
information about Neutron's policy enforcement, see:
`<https://docs.openstack.org/developer/neutron/devref/policy.html#request-authorization>`__.
How It Works
============
Patrole leverages oslo_policy (OpenStack's policy enforcement engine) to
determine whether a given role is allowed to perform a policy action given a
specific rule and OpenStack service. This is done before test execution inside
the ``rbac_rule_validation.action`` decorator. Then, inside the test, the API
that does policy enforcement for the same rule is called. The outcome is
compared against the result from oslo_policy and a pass or fail is determined
as outlined above: :ref:`test-flows`.
.. note::
Currently, Patrole does not support checking multiple rules against a single
API call. Even though some APIs enforce multiple rules (some indirectly),
it is increasingly difficult to maintain the tests if multiple policy
actions are expected to be called.
Test Execution Workflow
-----------------------
The workflow is as follows:
#. Each test uses the ``rbac_rule_validation.action`` decorator, like below: ::
@rbac_rule_validation.action(
service="nova",
rule="os_compute_api:servers:stop")
@decorators.idempotent_id('ab4a17d2-166f-4a6d-9944-f17baa576cf2')
def test_stop_server(self):
# Set the primary credential's role to "rbac_test_role".
self.rbac_utils.switch_role(self, toggle_rbac_role=True)
# Call the API that enforces the policy action specified by "rule".
self._test_stop_server()
The ``service`` attribute accepts an OpenStack service and the ``rule`` attribute
accepts a valid OpenStack policy action, like "os_compute_api:servers:stop".
#. The ``rbac_rule_validation.action`` decorator passes these attributes,
along with user_id and project_id information derived from the primary
Tempest credential (``self.os.credentials.user_id`` and ``self.os.credentials.project_id``),
to the ``rbac_policy_parser``.
#. The logic in ``rbac_policy_parser`` then passes all this information along
and the role in ``CONF.rbac.rbac_test_role`` to oslo_policy to determine whether
the ``rbac_test_role`` is authorized to perform the policy action for the given
service.
#. After all of the logic above has executed inside the rbac decorator, the
test is executed. The test then sets up test-level resources, if necessary,
with **admin** credentials implicitly. This is accomplished through
``rbac_utils.switch_role(toggle_rbac_role=False)``: ::
@classmethod
def setup_clients(cls):
super(BaseV2ComputeRbacTest, cls).setup_clients()
cls.auth_provider = cls.os.auth_provider
cls.rbac_utils = rbac_utils()
cls.rbac_utils.switch_role(cls, toggle_rbac_role=False)
This code has *already* executed when the test class is instantiated, because
it is located in the base rbac test class. Whenever ``cls.rbac_utils.switch_role``
is called, one of two behaviors are possible:
#. The primary credential's role is changed to admin if ``toggle_rbac_role=False``
#. The primary credential's role is changed to ``rbac_test_role`` if
``toggle_rbac_role=True``
Thus, at the *beginning* of every test and during ``resource_setup`` and
``resource_cleanup``, the primary credential has the admin role.
#. After preliminary test-level setup is performed, like creating a server, a
second call to ``self.rbac_utils.switch_role`` is done: ::
self.rbac_utils.switch_role(cls, toggle_rbac_role=True)
Now the primary credential has the role specified by ``rbac_test_role``.
#. The API endpoint in which policy enforcement of "os_compute_api:servers:stop"
is performed can now be called.
.. note:
To determine whether a policy action is enforced, refer to the relevant
controller code to make sure that the policy action is indeed enforced.
#. Now that a call is made to "stop_server" with the primary credentials having
the role specified by ``rbac_test_role``, either the nova contoller will allow
or disallow the action to be performed. Since the "stop_server" policy action in
nova is defined as "base.RULE_ADMIN_OR_OWNER", the API will most likely
return a successful status code. For more information about this policy action,
see `<https://github.com/openstack/nova/blob/master/nova/policies/servers.py>`__.
#. As mentioned above, the result from the API call and the result from oslo_policy
are compared for consistency.
#. Finally, after the test has executed, but before ``tearDown`` or ``resource_cleanup``
is called, ``self.rbac_utils.switch_role(cls, toggle_rbac_role=False)`` is
called, so that the primary credential yet again has admin permissions for
test clean up. This call is always performed in the "finally" block inside
the ``rbac_rule_validation`` decorator.
.. warning::
Failure to call ``self.rbac_utils.switch_role(cls, toggle_rbac_role=True)``
inside a test with the ``rbac_rule_validation`` decorator applied results
in a ``RbacResourceSetupFailed`` being raised, causing the test to fail.

View File

@ -3,7 +3,7 @@
You can adapt this file completely to your liking, but it should at least
contain the root `toctree` directive.
Welcome to patrole's documentation!
Patrole - an OpenStack Tempest Plugin for RBAC Testing
========================================================
Contents:
@ -22,4 +22,3 @@ Indices and tables
* :ref:`genindex`
* :ref:`modindex`
* :ref:`search`

View File

@ -3,24 +3,24 @@ Installation
============
Installation Information
########################
========================
At the command line::
$ pip install patrole
$ sudo pip install patrole
Or, if you have virtualenvwrapper installed::
$ mkvirtualenv patrole
$ pip install patrole
$ sudo pip install patrole
Or to install from the source::
$ navigate to patrole directory
$ pip install -e .
$ sudo pip install -e .
Configuration Information
#########################
=========================
tempest.conf
++++++++++++
@ -28,25 +28,25 @@ tempest.conf
To run the RBAC tempest api test, you have to make the following changes to
the tempest.conf file.
#. [auth] section updates ::
#. ``auth`` section updates ::
# Allows test cases to create/destroy projects and users. This option
# requires that OpenStack Identity API admin credentials are known. If
# false, isolated test cases and parallel execution, can still be
# achieved configuring a list of test accounts (boolean value)
use_dynamic_credentials = True
# Allows test cases to create/destroy projects and users. This option
# requires that OpenStack Identity API admin credentials are known. If
# false, isolated test cases and parallel execution, can still be
# achieved configuring a list of test accounts (boolean value)
use_dynamic_credentials = True
#. [rbac] section updates ::
#. ``rbac`` section updates ::
# The role that you want the RBAC tests to use for RBAC testing
# This needs to be edited to run the test as a different role.
rbac_test_role = _member_
# The role that you want the RBAC tests to use for RBAC testing
# This needs to be edited to run the test as a different role.
rbac_test_role = _member_
# Enables RBAC Tempest tests if set to True. Otherwise, they are
# skipped.
enable_rbac = True
# Enables RBAC Tempest tests if set to True. Otherwise, they are
# skipped.
enable_rbac = True
# If set to true, tests throw a RbacParsingException for policies
# not found in the policy.json. Otherwise, they throw a
# skipException.
strict_policy_check = False
# If set to true, tests throw a RbacParsingException for policies
# not found in the policy.json. Otherwise, they throw a
# skipException.
strict_policy_check = False

View File

@ -1,10 +1,36 @@
..
========
Usage
========
To use run patrole tests in Tempest::
Running Patrole Tests in Tempest
================================
If patrole is installed correctly tests are run like any others.
If Patrole is installed correctly, then the API tests can be executed
from inside the tempest root directory as follows: ::
To change the role that the patrole tests are being run as edit rbac_role
in the rbac section of tempest.conf.
tox -eall-plugin -- patrole_tempest_plugin.tests.api
To execute patrole tests for a specific module, run: ::
tox -eall-plugin -- patrole_tempest_plugin.tests.api.compute
To change the role that the patrole tests are being run as, edit
``rbac_test_role`` in the ``rbac`` section of tempest.conf: ::
[rbac]
rbac_test_role = Member
...
.. note::
The ``rbac_test_role`` is service-specific. Member, for example,
is an arbitrary role, but by convention is used to designate the default
non-admin role in the system. Most patrole tests should be run with
**admin** and **Member** roles. However, some services, like Heat, take
advantage of a role called **heat_stack_user**, as it appears frequently
in Heat's policy.json.
For more information about the Member role,
please see: `<https://ask.openstack.org/en/question/4759/member-vs-_member_/>`__.

View File

@ -1,6 +1,5 @@
===============================================
Tempest Integration of patrole
===============================================
This directory contains Tempest tests to cover the patrole project.
==============================
Tempest Integration of Patrole
==============================
This directory contains Tempest tests to cover the Patrole project.