From aba92673238984f98a42005bd7f27940c72cc419 Mon Sep 17 00:00:00 2001 From: Samriddhi Jain Date: Wed, 31 May 2017 20:01:23 +0530 Subject: [PATCH] Added keystone admin guides to documentation Currently the identity administrator guide docs are a part of general OpenStack-manuals. Migrating those docs to keystone documentation so that they can be reviewed effectively by keystone developers too. Partial-Bug #1694460 Depends-On: Ia750cb049c0f53a234ea70ce1f2bbbb7a2aa9454 Change-Id: Id121ae1dd5bce993b4ad1219b592527ef0047063 --- .../admin/identity-auth-token-middleware.rst | 74 +++ doc/source/admin/identity-caching-layer.rst | 128 +++++ .../admin/identity-certificates-for-pki.rst | 237 +++++++++ doc/source/admin/identity-concepts.rst | 354 ++++++++++++++ .../admin/identity-domain-specific-config.rst | 69 +++ .../identity-external-authentication.rst | 41 ++ .../admin/identity-fernet-token-faq.rst | 345 +++++++++++++ .../admin/identity-integrate-with-ldap.rst | 453 ++++++++++++++++++ .../identity-keystone-usage-and-features.rst | 83 ++++ doc/source/admin/identity-management.rst | 31 ++ .../admin/identity-security-compliance.rst | 167 +++++++ .../admin/identity-service-api-protection.rst | 128 +++++ doc/source/admin/identity-token-binding.rst | 64 +++ doc/source/admin/identity-tokens.rst | 108 +++++ doc/source/admin/identity-troubleshoot.rst | 199 ++++++++ doc/source/admin/identity-use-trusts.rst | 56 +++ doc/source/index.rst | 8 + 17 files changed, 2545 insertions(+) create mode 100644 doc/source/admin/identity-auth-token-middleware.rst create mode 100644 doc/source/admin/identity-caching-layer.rst create mode 100644 doc/source/admin/identity-certificates-for-pki.rst create mode 100644 doc/source/admin/identity-concepts.rst create mode 100644 doc/source/admin/identity-domain-specific-config.rst create mode 100644 doc/source/admin/identity-external-authentication.rst create mode 100644 doc/source/admin/identity-fernet-token-faq.rst create mode 100644 doc/source/admin/identity-integrate-with-ldap.rst create mode 100644 doc/source/admin/identity-keystone-usage-and-features.rst create mode 100644 doc/source/admin/identity-management.rst create mode 100644 doc/source/admin/identity-security-compliance.rst create mode 100644 doc/source/admin/identity-service-api-protection.rst create mode 100644 doc/source/admin/identity-token-binding.rst create mode 100644 doc/source/admin/identity-tokens.rst create mode 100644 doc/source/admin/identity-troubleshoot.rst create mode 100644 doc/source/admin/identity-use-trusts.rst diff --git a/doc/source/admin/identity-auth-token-middleware.rst b/doc/source/admin/identity-auth-token-middleware.rst new file mode 100644 index 0000000000..291d4f777b --- /dev/null +++ b/doc/source/admin/identity-auth-token-middleware.rst @@ -0,0 +1,74 @@ +Authentication middleware with user name and password +~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ + +You can also configure Identity authentication middleware using the +``admin_user`` and ``admin_password`` options. + +.. note:: + + The ``admin_token`` option is deprecated and no longer used for + configuring auth_token middleware. + +For services that have a separate paste-deploy ``.ini`` file, you can +configure the authentication middleware in the ``[keystone_authtoken]`` +section of the main configuration file, such as ``nova.conf``. In +Compute, for example, you can remove the middleware parameters from +``api-paste.ini``, as follows: + +.. code-block:: ini + + [filter:authtoken] + paste.filter_factory = keystonemiddleware.auth_token:filter_factory + + +And set the following values in ``nova.conf`` as follows: + +.. code-block:: ini + + [DEFAULT] + # ... + auth_strategy=keystone + + [keystone_authtoken] + auth_uri = http://controller:5000/v2.0 + identity_uri = http://controller:35357 + admin_user = admin + admin_password = SuperSekretPassword + admin_tenant_name = service + +.. note:: + + The middleware parameters in the paste config take priority. You + must remove them to use the values in the ``[keystone_authtoken]`` + section. + +.. note:: + + Comment out any ``auth_host``, ``auth_port``, and + ``auth_protocol`` options because the ``identity_uri`` option + replaces them. + +This sample paste config filter makes use of the ``admin_user`` and +``admin_password`` options: + +.. code-block:: ini + + [filter:authtoken] + paste.filter_factory = keystonemiddleware.auth_token:filter_factory + auth_uri = http://controller:5000/v2.0 + identity_uri = http://controller:35357 + auth_token = 012345SECRET99TOKEN012345 + admin_user = admin + admin_password = keystone123 + +.. note:: + + Using this option requires an admin project/role relationship. The + admin user is granted access to the admin role on the admin project. + +.. note:: + + Comment out any ``auth_host``, ``auth_port``, and + ``auth_protocol`` options because the ``identity_uri`` option + replaces them. + diff --git a/doc/source/admin/identity-caching-layer.rst b/doc/source/admin/identity-caching-layer.rst new file mode 100644 index 0000000000..7fb62b1c19 --- /dev/null +++ b/doc/source/admin/identity-caching-layer.rst @@ -0,0 +1,128 @@ +.. :orphan: + +Caching layer +~~~~~~~~~~~~~ + +OpenStack Identity supports a caching layer that is above the +configurable subsystems (for example, token). OpenStack Identity uses the +`oslo.cache `__ +library which allows flexible cache back ends. The majority of the +caching configuration options are set in the ``[cache]`` section of the +``/etc/keystone/keystone.conf`` file. However, each section that has +the capability to be cached usually has a caching boolean value that +toggles caching. + +So to enable only the token back end caching, set the values as follows: + +.. code-block:: ini + + [cache] + enabled=true + + [catalog] + caching=false + + [domain_config] + caching=false + + [federation] + caching=false + + [resource] + caching=false + + [revoke] + caching=false + + [role] + caching=false + + [token] + caching=true + +.. note:: + + Since the Newton release, the default setting is enabled for subsystem + caching and the global toggle. As a result, all subsystems that support + caching are doing this by default. + +Caching for tokens and tokens validation +---------------------------------------- + +All types of tokens benefit from caching, including Fernet tokens. Although +Fernet tokens do not need to be persisted, they should still be cached for +optimal token validation performance. + +The token system has a separate ``cache_time`` configuration option, +that can be set to a value above or below the global ``expiration_time`` +default, allowing for different caching behavior from the other systems +in OpenStack Identity. This option is set in the ``[token]`` section of +the configuration file. + +The token revocation list cache time is handled by the configuration +option ``revocation_cache_time`` in the ``[token]`` section. The +revocation list is refreshed whenever a token is revoked. It typically +sees significantly more requests than specific token retrievals or token +validation calls. + +Here is a list of actions that are affected by the cached time: getting +a new token, revoking tokens, validating tokens, checking v2 tokens, and +checking v3 tokens. + +The delete token API calls invalidate the cache for the tokens being +acted upon, as well as invalidating the cache for the revoked token list +and the validate/check token calls. + +Token caching is configurable independently of the ``revocation_list`` +caching. Lifted expiration checks from the token drivers to the token +manager. This ensures that cached tokens will still raise a +``TokenNotFound`` flag when expired. + +For cache consistency, all token IDs are transformed into the short +token hash at the provider and token driver level. Some methods have +access to the full ID (PKI Tokens), and some methods do not. Cache +invalidation is inconsistent without token ID normalization. + +Caching for non-token resources +------------------------------- + +Various other keystone components have a separate ``cache_time`` configuration +option, that can be set to a value above or below the global +``expiration_time`` default, allowing for different caching behavior +from the other systems in Identity service. This option can be set in various +sections (for example, ``[role]`` and ``[resource]``) of the configuration +file. +The create, update, and delete actions for domains, projects and roles +will perform proper invalidations of the cached methods listed above. + +For more information about the different back ends (and configuration +options), see: + +- `dogpile.cache.memory `__ + +- `dogpile.cache.memcached `__ + + .. note:: + + The memory back end is not suitable for use in a production + environment. + +- `dogpile.cache.redis `__ + +- `dogpile.cache.dbm `__ + +Configure the Memcached back end example +---------------------------------------- + +The following example shows how to configure the memcached back end: + +.. code-block:: ini + + [cache] + + enabled = true + backend = dogpile.cache.memcached + backend_argument = url:127.0.0.1:11211 + +You need to specify the URL to reach the ``memcached`` instance with the +``backend_argument`` parameter. diff --git a/doc/source/admin/identity-certificates-for-pki.rst b/doc/source/admin/identity-certificates-for-pki.rst new file mode 100644 index 0000000000..2c518cc63e --- /dev/null +++ b/doc/source/admin/identity-certificates-for-pki.rst @@ -0,0 +1,237 @@ +==================== +Certificates for PKI +==================== + +PKI stands for Public Key Infrastructure. Tokens are documents, +cryptographically signed using the X509 standard. In order to work +correctly token generation requires a public/private key pair. The +public key must be signed in an X509 certificate, and the certificate +used to sign it must be available as a Certificate Authority (CA) +certificate. These files can be generated either using the +:command:`keystone-manage` utility, or externally generated. The files need to +be in the locations specified by the top level Identity service +configuration file ``/etc/keystone/keystone.conf`` as specified in the +above section. Additionally, the private key should only be readable by +the system user that will run the Identity service. + + +.. warning:: + + The certificates can be world readable, but the private key cannot + be. The private key should only be readable by the account that is + going to sign tokens. When generating files with the + :command:`keystone-manage pki_setup` command, your best option is to run + as the pki user. If you run :command:`keystone-manage` as root, you can + append ``--keystone-user`` and ``--keystone-group`` parameters + to set the user name and group keystone is going to run under. + +The values that specify where to read the certificates are under the +``[signing]`` section of the configuration file. The configuration +values are: + +- ``certfile`` + Location of certificate used to verify tokens. Default is + ``/etc/keystone/ssl/certs/signing_cert.pem``. + +- ``keyfile`` + Location of private key used to sign tokens. Default is + ``/etc/keystone/ssl/private/signing_key.pem``. + +- ``ca_certs`` + Location of certificate for the authority that issued + the above certificate. Default is + ``/etc/keystone/ssl/certs/ca.pem``. + +- ``ca_key`` + Location of the private key used by the CA. Default is + ``/etc/keystone/ssl/private/cakey.pem``. + +- ``key_size`` + Default is ``2048``. + +- ``valid_days`` + Default is ``3650``. + +- ``cert_subject`` + Certificate subject (auto generated certificate) for token signing. + Default is ``/C=US/ST=Unset/L=Unset/O=Unset/CN=www.example.com``. + +When generating certificates with the :command:`keystone-manage pki_setup` +command, the ``ca_key``, ``key_size``, and ``valid_days`` configuration +options are used. + +If the :command:`keystone-manage pki_setup` command is not used to generate +certificates, or you are providing your own certificates, these values +do not need to be set. + +If ``provider=keystone.token.providers.uuid.Provider`` in the +``[token]`` section of the keystone configuration file, a typical token +looks like ``53f7f6ef0cc344b5be706bcc8b1479e1``. If +``provider=keystone.token.providers.pki.Provider``, a typical token is a +much longer string, such as:: + + MIIKtgYJKoZIhvcNAQcCoIIKpzCCCqMCAQExCTAHBgUrDgMCGjCCCY8GCSqGSIb3DQEHAaCCCYAEggl8eyJhY2Nlc3MiOiB7InRva2VuIjogeyJpc3N1ZWRfYXQiOiAiMjAxMy0wNS0z + MFQxNTo1MjowNi43MzMxOTgiLCAiZXhwaXJlcyI6ICIyMDEzLTA1LTMxVDE1OjUyOjA2WiIsICJpZCI6ICJwbGFjZWhvbGRlciIsICJ0ZW5hbnQiOiB7ImRlc2NyaXB0aW9uIjogbnVs + bCwgImVuYWJsZWQiOiB0cnVlLCAiaWQiOiAiYzJjNTliNGQzZDI4NGQ4ZmEwOWYxNjljYjE4MDBlMDYiLCAibmFtZSI6ICJkZW1vIn19LCAic2VydmljZUNhdGFsb2ciOiBbeyJlbmRw + b2ludHMiOiBbeyJhZG1pblVSTCI6ICJodHRwOi8vMTkyLjE2OC4yNy4xMDA6ODc3NC92Mi9jMmM1OWI0ZDNkMjg0ZDhmYTA5ZjE2OWNiMTgwMGUwNiIsICJyZWdpb24iOiAiUmVnaW9u + T25lIiwgImludGVybmFsVVJMIjogImh0dHA6Ly8xOTIuMTY4LjI3LjEwMDo4Nzc0L3YyL2MyYzU5YjRkM2QyODRkOGZhMDlmMTY5Y2IxODAwZTA2IiwgImlkIjogIjFmYjMzYmM5M2Y5 + ODRhNGNhZTk3MmViNzcwOTgzZTJlIiwgInB1YmxpY1VSTCI6ICJodHRwOi8vMTkyLjE2OC4yNy4xMDA6ODc3NC92Mi9jMmM1OWI0ZDNkMjg0ZDhmYTA5ZjE2OWNiMTgwMGUwNiJ9XSwg + ImVuZHBvaW50c19saW5rcyI6IFtdLCAidHlwZSI6ICJjb21wdXRlIiwgIm5hbWUiOiAibm92YSJ9LCB7ImVuZHBvaW50cyI6IFt7ImFkbWluVVJMIjogImh0dHA6Ly8xOTIuMTY4LjI3 + LjEwMDozMzMzIiwgInJlZ2lvbiI6ICJSZWdpb25PbmUiLCAiaW50ZXJuYWxVUkwiOiAiaHR0cDovLzE5Mi4xNjguMjcuMTAwOjMzMzMiLCAiaWQiOiAiN2JjMThjYzk1NWFiNDNkYjhm + MGU2YWNlNDU4NjZmMzAiLCAicHVibGljVVJMIjogImh0dHA6Ly8xOTIuMTY4LjI3LjEwMDozMzMzIn1dLCAiZW5kcG9pbnRzX2xpbmtzIjogW10sICJ0eXBlIjogInMzIiwgIm5hbWUi + OiAiczMifSwgeyJlbmRwb2ludHMiOiBbeyJhZG1pblVSTCI6ICJodHRwOi8vMTkyLjE2OC4yNy4xMDA6OTI5MiIsICJyZWdpb24iOiAiUmVnaW9uT25lIiwgImludGVybmFsVVJMIjog + Imh0dHA6Ly8xOTIuMTY4LjI3LjEwMDo5MjkyIiwgImlkIjogIjczODQzNTJhNTQ0MjQ1NzVhM2NkOTVkN2E0YzNjZGY1IiwgInB1YmxpY1VSTCI6ICJodHRwOi8vMTkyLjE2OC4yNy4x + MDA6OTI5MiJ9XSwgImVuZHBvaW50c19saW5rcyI6IFtdLCAidHlwZSI6ICJpbWFnZSIsICJuYW1lIjogImdsYW5jZSJ9LCB7ImVuZHBvaW50cyI6IFt7ImFkbWluVVJMIjogImh0dHA6 + Ly8xOTIuMTY4LjI3LjEwMDo4Nzc2L3YxL2MyYzU5YjRkM2QyODRkOGZhMDlmMTY5Y2IxODAwZTA2IiwgInJlZ2lvbiI6ICJSZWdpb25PbmUiLCAiaW50ZXJuYWxVUkwiOiAiaHR0cDov + LzE5Mi4xNjguMjcuMTAwOjg3NzYvdjEvYzJjNTliNGQzZDI4NGQ4ZmEwOWYxNjljYjE4MDBlMDYiLCAiaWQiOiAiMzQ3ZWQ2ZThjMjkxNGU1MGFlMmJiNjA2YWQxNDdjNTQiLCAicHVi + bGljVVJMIjogImh0dHA6Ly8xOTIuMTY4LjI3LjEwMDo4Nzc2L3YxL2MyYzU5YjRkM2QyODRkOGZhMDlmMTY5Y2IxODAwZTA2In1dLCAiZW5kcG9pbnRzX2xpbmtzIjogW10sICJ0eXBl + IjogInZvbHVtZSIsICJuYW1lIjogImNpbmRlciJ9LCB7ImVuZHBvaW50cyI6IFt7ImFkbWluVVJMIjogImh0dHA6Ly8xOTIuMTY4LjI3LjEwMDo4NzczL3NlcnZpY2VzL0FkbWluIiwg + InJlZ2lvbiI6ICJSZWdpb25PbmUiLCAiaW50ZXJuYWxVUkwiOiAiaHR0cDovLzE5Mi4xNjguMjcuMTAwOjg3NzMvc2VydmljZXMvQ2xvdWQiLCAiaWQiOiAiMmIwZGMyYjNlY2U4NGJj + YWE1NDAzMDMzNzI5YzY3MjIiLCAicHVibGljVVJMIjogImh0dHA6Ly8xOTIuMTY4LjI3LjEwMDo4NzczL3NlcnZpY2VzL0Nsb3VkIn1dLCAiZW5kcG9pbnRzX2xpbmtzIjogW10sICJ0 + eXBlIjogImVjMiIsICJuYW1lIjogImVjMiJ9LCB7ImVuZHBvaW50cyI6IFt7ImFkbWluVVJMIjogImh0dHA6Ly8xOTIuMTY4LjI3LjEwMDozNTM1Ny92Mi4wIiwgInJlZ2lvbiI6ICJS + ZWdpb25PbmUiLCAiaW50ZXJuYWxVUkwiOiAiaHR0cDovLzE5Mi4xNjguMjcuMTAwOjUwMDAvdjIuMCIsICJpZCI6ICJiNTY2Y2JlZjA2NjQ0ZmY2OWMyOTMxNzY2Yjc5MTIyOSIsICJw + dWJsaWNVUkwiOiAiaHR0cDovLzE5Mi4xNjguMjcuMTAwOjUwMDAvdjIuMCJ9XSwgImVuZHBvaW50c19saW5rcyI6IFtdLCAidHlwZSI6ICJpZGVudGl0eSIsICJuYW1lIjogImtleXN0 + b25lIn1dLCAidXNlciI6IHsidXNlcm5hbWUiOiAiZGVtbyIsICJyb2xlc19saW5rcyI6IFtdLCAiaWQiOiAiZTVhMTM3NGE4YTRmNDI4NWIzYWQ3MzQ1MWU2MDY4YjEiLCAicm9sZXMi + OiBbeyJuYW1lIjogImFub3RoZXJyb2xlIn0sIHsibmFtZSI6ICJNZW1iZXIifV0sICJuYW1lIjogImRlbW8ifSwgIm1ldGFkYXRhIjogeyJpc19hZG1pbiI6IDAsICJyb2xlcyI6IFsi + YWRiODM3NDVkYzQzNGJhMzk5ODllNjBjOTIzYWZhMjgiLCAiMzM2ZTFiNjE1N2Y3NGFmZGJhNWUwYTYwMWUwNjM5MmYiXX19fTGB-zCB-AIBATBcMFcxCzAJBgNVBAYTAlVTMQ4wDAYD + VQQIEwVVbnNldDEOMAwGA1UEBxMFVW5zZXQxDjAMBgNVBAoTBVVuc2V0MRgwFgYDVQQDEw93d3cuZXhhbXBsZS5jb20CAQEwBwYFKw4DAhowDQYJKoZIhvcNAQEBBQAEgYCAHLpsEs2R + nouriuiCgFayIqCssK3SVdhOMINiuJtqv0sE-wBDFiEj-Prcudqlz-n+6q7VgV4mwMPszz39-rwp+P5l4AjrJasUm7FrO-4l02tPLaaZXU1gBQ1jUG5e5aL5jPDP08HbCWuX6wr-QQQB + SrWY8lF3HrTcJT23sZIleg== + +Sign certificate issued by external CA +~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ + +You can use a signing certificate issued by an external CA instead of +generated by :command:`keystone-manage`. However, a certificate issued by an +external CA must satisfy the following conditions: + +- All certificate and key files must be in Privacy Enhanced Mail (PEM) + format + +- Private key files must not be protected by a password + +When using a signing certificate issued by an external CA, you do not +need to specify ``key_size``, ``valid_days``, and ``ca_password`` as +they will be ignored. + +The basic workflow for using a signing certificate issued by an external +CA involves: + +#. Request Signing Certificate from External CA + +#. Convert certificate and private key to PEM if needed + +#. Install External Signing Certificate + +Request a signing certificate from an external CA +~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ + +One way to request a signing certificate from an external CA is to first +generate a PKCS #10 Certificate Request Syntax (CRS) using OpenSSL CLI. + +Create a certificate request configuration file. For example, create the +``cert_req.conf`` file, as follows: + +.. code-block:: ini + + [ req ] + default_bits = 4096 + default_keyfile = keystonekey.pem + default_md = sha256 + + prompt = no + distinguished_name = distinguished_name + + [ distinguished_name ] + countryName = US + stateOrProvinceName = CA + localityName = Sunnyvale + organizationName = OpenStack + organizationalUnitName = Keystone + commonName = Keystone Signing + emailAddress = keystone@openstack.org + +Then generate a CRS with OpenSSL CLI. **Do not encrypt the generated +private key. You must use the -nodes option.** + +For example: + +.. code-block:: console + + $ openssl req -newkey rsa:1024 -keyout signing_key.pem -keyform PEM \ + -out signing_cert_req.pem -outform PEM -config cert_req.conf -nodes + +If everything is successful, you should end up with +``signing_cert_req.pem`` and ``signing_key.pem``. Send +``signing_cert_req.pem`` to your CA to request a token signing certificate +and make sure to ask the certificate to be in PEM format. Also, make sure your +trusted CA certificate chain is also in PEM format. + +Install an external signing certificate +~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ + +Assuming you have the following already: + +- ``signing_cert.pem`` + (Keystone token) signing certificate in PEM format + +- ``signing_key.pem`` + Corresponding (non-encrypted) private key in PEM format + +- ``cacert.pem`` + Trust CA certificate chain in PEM format + +Copy the above to your certificate directory. For example: + +.. code-block:: console + + # mkdir -p /etc/keystone/ssl/certs + # cp signing_cert.pem /etc/keystone/ssl/certs/ + # cp signing_key.pem /etc/keystone/ssl/certs/ + # cp cacert.pem /etc/keystone/ssl/certs/ + # chmod -R 700 /etc/keystone/ssl/certs + +.. note:: + + Make sure the certificate directory is only accessible by root. + +.. note:: + + The procedure of copying the key and cert files may be improved if + done after first running :command:`keystone-manage pki_setup` since this + command also creates other needed files, such as the ``index.txt`` + and ``serial`` files. + + Also, when copying the necessary files to a different server for + replicating the functionality, the entire directory of files is + needed, not just the key and cert files. + +If your certificate directory path is different from the default +``/etc/keystone/ssl/certs``, make sure it is reflected in the +``[signing]`` section of the configuration file. + +Switching out expired signing certificates +~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ + +The following procedure details how to switch out expired signing +certificates with no cloud outages. + +#. Generate a new signing key. + +#. Generate a new certificate request. + +#. Sign the new certificate with the existing CA to generate a new + ``signing_cert``. + +#. Append the new ``signing_cert`` to the old ``signing_cert``. Ensure the + old certificate is in the file first. + +#. Remove all signing certificates from all your hosts to force OpenStack + Compute to download the new ``signing_cert``. + +#. Replace the old signing key with the new signing key. Move the new + signing certificate above the old certificate in the ``signing_cert`` + file. + +#. After the old certificate reads as expired, you can safely remove the + old signing certificate from the file. diff --git a/doc/source/admin/identity-concepts.rst b/doc/source/admin/identity-concepts.rst new file mode 100644 index 0000000000..cc60b4f9d6 --- /dev/null +++ b/doc/source/admin/identity-concepts.rst @@ -0,0 +1,354 @@ +================= +Identity concepts +================= + +Authentication + The process of confirming the identity of a user. To confirm an incoming + request, OpenStack Identity validates a set of credentials users + supply. Initially, these credentials are a user name and password, or a + user name and API key. When OpenStack Identity validates user credentials, + it issues an authentication token. Users provide the token in + subsequent requests. + +Credentials + Data that confirms the identity of the user. For example, user + name and password, user name and API key, or an authentication + token that the Identity service provides. + +Domain + An Identity service API v3 entity. Domains are a collection of + projects and users that define administrative boundaries for + managing Identity entities. Domains can represent an + individual, company, or operator-owned space. They expose + administrative activities directly to system users. Users can be + granted the administrator role for a domain. A domain + administrator can create projects, users, and groups in a domain + and assign roles to users and groups in a domain. + +Endpoint + A network-accessible address, usually a URL, through which you can + access a service. If you are using an extension for templates, you + can create an endpoint template that represents the templates of + all consumable services that are available across the regions. + +Group + An Identity service API v3 entity. Groups are a collection of + users owned by a domain. A group role, granted to a domain + or project, applies to all users in the group. Adding or removing + users to or from a group grants or revokes their role and + authentication to the associated domain or project. + +OpenStackClient + A command-line interface for several OpenStack services including + the Identity API. For example, a user can run the + :command:`openstack service create` and + :command:`openstack endpoint create` commands to register services + in their OpenStack installation. + +Project + A container that groups or isolates resources or identity objects. + Depending on the service operator, a project might map to a + customer, account, organization, or tenant. + +Region + An Identity service API v3 entity. Represents a general division + in an OpenStack deployment. You can associate zero or more + sub-regions with a region to make a tree-like structured hierarchy. + Although a region does not have a geographical connotation, a + deployment can use a geographical name for a region, such as ``us-east``. + +Role + A personality with a defined set of user rights and privileges to + perform a specific set of operations. The Identity service issues + a token to a user that includes a list of roles. When a user calls + a service, that service interprets the user role set, and + determines to which operations or resources each role grants + access. + +Service + An OpenStack service, such as Compute (nova), Object Storage + (swift), or Image service (glance), that provides one or more + endpoints through which users can access resources and perform + operations. + +Token + An alpha-numeric text string that enables access to OpenStack APIs + and resources. A token may be revoked at any time and is valid for + a finite duration. While OpenStack Identity supports token-based + authentication in this release, it intends to support additional + protocols in the future. OpenStack Identity is an integration + service that does not aspire to be a full-fledged identity store + and management solution. + +User + A digital representation of a person, system, or service that uses + OpenStack cloud services. The Identity service validates that + incoming requests are made by the user who claims to be making the + call. Users have a login and can access resources by using + assigned tokens. Users can be directly assigned to a particular + project and behave as if they are contained in that project. + +User management +~~~~~~~~~~~~~~~ + +Identity user management examples: + +* Create a user named ``alice``: + + .. code-block:: console + + $ openstack user create --password-prompt --email alice@example.com alice + +* Create a project named ``acme``: + + .. code-block:: console + + $ openstack project create acme --domain default + +* Create a domain named ``emea``: + + .. code-block:: console + + $ openstack --os-identity-api-version=3 domain create emea + +* Create a role named ``compute-user``: + + .. code-block:: console + + $ openstack role create compute-user + + .. note:: + + Individual services assign meaning to roles, typically through + limiting or granting access to users with the role to the + operations that the service supports. Role access is typically + configured in the service's ``policy.json`` file. For example, + to limit Compute access to the ``compute-user`` role, edit the + Compute service's ``policy.json`` file to require this role for + Compute operations. + +The Identity service assigns a project and a role to a user. You might +assign the ``compute-user`` role to the ``alice`` user in the ``acme`` +project: + +.. code-block:: console + + $ openstack role add --project acme --user alice compute-user + +A user can have different roles in different projects. For example, Alice +might also have the ``admin`` role in the ``Cyberdyne`` project. A user +can also have multiple roles in the same project. + +The ``/etc/[SERVICE_CODENAME]/policy.json`` file controls the +tasks that users can perform for a given service. For example, the +``/etc/nova/policy.json`` file specifies the access policy for the +Compute service, the ``/etc/glance/policy.json`` file specifies +the access policy for the Image service, and the +``/etc/keystone/policy.json`` file specifies the access policy for +the Identity service. + +The default ``policy.json`` files in the Compute, Identity, and +Image services recognize only the ``admin`` role. Any user with +any role in a project can access all operations that do not require the +``admin`` role. + +To restrict users from performing operations in, for example, the +Compute service, you must create a role in the Identity service and +then modify the ``/etc/nova/policy.json`` file so that this role +is required for Compute operations. + +For example, the following line in the ``/etc/cinder/policy.json`` +file does not restrict which users can create volumes: + +.. code-block:: none + + "volume:create": "", + +If the user has any role in a project, he can create volumes in that +project. + +To restrict the creation of volumes to users who have the +``compute-user`` role in a particular project, you add ``"role:compute-user"``: + +.. code-block:: none + + "volume:create": "role:compute-user", + +To restrict all Compute service requests to require this role, the +resulting file looks like: + +.. code-block:: json + + { + "admin_or_owner": "role:admin or project_id:%(project_id)s", + "default": "rule:admin_or_owner", + "compute:create": "role:compute-user", + "compute:create:attach_network": "role:compute-user", + "compute:create:attach_volume": "role:compute-user", + "compute:get_all": "role:compute-user", + "compute:unlock_override": "rule:admin_api", + "admin_api": "role:admin", + "compute_extension:accounts": "rule:admin_api", + "compute_extension:admin_actions": "rule:admin_api", + "compute_extension:admin_actions:pause": "rule:admin_or_owner", + "compute_extension:admin_actions:unpause": "rule:admin_or_owner", + "compute_extension:admin_actions:suspend": "rule:admin_or_owner", + "compute_extension:admin_actions:resume": "rule:admin_or_owner", + "compute_extension:admin_actions:lock": "rule:admin_or_owner", + "compute_extension:admin_actions:unlock": "rule:admin_or_owner", + "compute_extension:admin_actions:resetNetwork": "rule:admin_api", + "compute_extension:admin_actions:injectNetworkInfo": "rule:admin_api", + "compute_extension:admin_actions:createBackup": "rule:admin_or_owner", + "compute_extension:admin_actions:migrateLive": "rule:admin_api", + "compute_extension:admin_actions:migrate": "rule:admin_api", + "compute_extension:aggregates": "rule:admin_api", + "compute_extension:certificates": "role:compute-user", + "compute_extension:cloudpipe": "rule:admin_api", + "compute_extension:console_output": "role:compute-user", + "compute_extension:consoles": "role:compute-user", + "compute_extension:createserverext": "role:compute-user", + "compute_extension:deferred_delete": "role:compute-user", + "compute_extension:disk_config": "role:compute-user", + "compute_extension:evacuate": "rule:admin_api", + "compute_extension:extended_server_attributes": "rule:admin_api", + "compute_extension:extended_status": "role:compute-user", + "compute_extension:flavorextradata": "role:compute-user", + "compute_extension:flavorextraspecs": "role:compute-user", + "compute_extension:flavormanage": "rule:admin_api", + "compute_extension:floating_ip_dns": "role:compute-user", + "compute_extension:floating_ip_pools": "role:compute-user", + "compute_extension:floating_ips": "role:compute-user", + "compute_extension:hosts": "rule:admin_api", + "compute_extension:keypairs": "role:compute-user", + "compute_extension:multinic": "role:compute-user", + "compute_extension:networks": "rule:admin_api", + "compute_extension:quotas": "role:compute-user", + "compute_extension:rescue": "role:compute-user", + "compute_extension:security_groups": "role:compute-user", + "compute_extension:server_action_list": "rule:admin_api", + "compute_extension:server_diagnostics": "rule:admin_api", + "compute_extension:simple_tenant_usage:show": "rule:admin_or_owner", + "compute_extension:simple_tenant_usage:list": "rule:admin_api", + "compute_extension:users": "rule:admin_api", + "compute_extension:virtual_interfaces": "role:compute-user", + "compute_extension:virtual_storage_arrays": "role:compute-user", + "compute_extension:volumes": "role:compute-user", + "compute_extension:volume_attachments:index": "role:compute-user", + "compute_extension:volume_attachments:show": "role:compute-user", + "compute_extension:volume_attachments:create": "role:compute-user", + "compute_extension:volume_attachments:delete": "role:compute-user", + "compute_extension:volumetypes": "role:compute-user", + "volume:create": "role:compute-user", + "volume:get_all": "role:compute-user", + "volume:get_volume_metadata": "role:compute-user", + "volume:get_snapshot": "role:compute-user", + "volume:get_all_snapshots": "role:compute-user", + "network:get_all_networks": "role:compute-user", + "network:get_network": "role:compute-user", + "network:delete_network": "role:compute-user", + "network:disassociate_network": "role:compute-user", + "network:get_vifs_by_instance": "role:compute-user", + "network:allocate_for_instance": "role:compute-user", + "network:deallocate_for_instance": "role:compute-user", + "network:validate_networks": "role:compute-user", + "network:get_instance_uuids_by_ip_filter": "role:compute-user", + "network:get_floating_ip": "role:compute-user", + "network:get_floating_ip_pools": "role:compute-user", + "network:get_floating_ip_by_address": "role:compute-user", + "network:get_floating_ips_by_project": "role:compute-user", + "network:get_floating_ips_by_fixed_address": "role:compute-user", + "network:allocate_floating_ip": "role:compute-user", + "network:deallocate_floating_ip": "role:compute-user", + "network:associate_floating_ip": "role:compute-user", + "network:disassociate_floating_ip": "role:compute-user", + "network:get_fixed_ip": "role:compute-user", + "network:add_fixed_ip_to_instance": "role:compute-user", + "network:remove_fixed_ip_from_instance": "role:compute-user", + "network:add_network_to_project": "role:compute-user", + "network:get_instance_nw_info": "role:compute-user", + "network:get_dns_domains": "role:compute-user", + "network:add_dns_entry": "role:compute-user", + "network:modify_dns_entry": "role:compute-user", + "network:delete_dns_entry": "role:compute-user", + "network:get_dns_entries_by_address": "role:compute-user", + "network:get_dns_entries_by_name": "role:compute-user", + "network:create_private_dns_domain": "role:compute-user", + "network:create_public_dns_domain": "role:compute-user", + "network:delete_dns_domain": "role:compute-user" + } + +Service management +~~~~~~~~~~~~~~~~~~ + +The Identity service provides identity, token, catalog, and policy +services. It consists of: + +* keystone Web Server Gateway Interface (WSGI) service + Can be run in a WSGI-capable web server such as Apache httpd to provide + the Identity service. The service and administrative APIs are run as + separate instances of the WSGI service. + +* Identity service functions + Each has a pluggable back end that allow different ways to use the + particular service. Most support standard back ends like LDAP or SQL. + +* keystone-all + Starts both the service and administrative APIs in a single process. + Using federation with keystone-all is not supported. keystone-all is + deprecated in favor of the WSGI service. Also, this will be removed + in Newton. + +The Identity service also maintains a user that corresponds to each +service, such as, a user named ``nova`` for the Compute service, and a +special service project called ``service``. + +For information about how to create services and endpoints, see the +`OpenStack Administrator Guide `__. + +Groups +~~~~~~ + +A group is a collection of users in a domain. Administrators can +create groups and add users to them. A role can then be assigned to +the group, rather than individual users. Groups were introduced with +the Identity API v3. + +Identity API V3 provides the following group-related operations: + +* Create a group + +* Delete a group + +* Update a group (change its name or description) + +* Add a user to a group + +* Remove a user from a group + +* List group members + +* List groups for a user + +* Assign a role on a project to a group + +* Assign a role on a domain to a group + +* Query role assignments to groups + +.. note:: + + The Identity service server might not allow all operations. For + example, if you use the Identity server with the LDAP Identity + back end and group updates are disabled, a request to create, + delete, or update a group fails. + +Here are a couple of examples: + +* Group A is granted Role A on Project A. If User A is a member of Group + A, when User A gets a token scoped to Project A, the token also + includes Role A. + +* Group B is granted Role B on Domain B. If User B is a member of + Group B, when User B gets a token scoped to Domain B, the token also + includes Role B. diff --git a/doc/source/admin/identity-domain-specific-config.rst b/doc/source/admin/identity-domain-specific-config.rst new file mode 100644 index 0000000000..b15f69889a --- /dev/null +++ b/doc/source/admin/identity-domain-specific-config.rst @@ -0,0 +1,69 @@ +============================= +Domain-specific configuration +============================= + +The Identity service supports domain-specific Identity drivers. +The drivers allow a domain to have its own LDAP or SQL back end. +By default, domain-specific drivers are disabled. + +Domain-specific Identity configuration options can be stored in +domain-specific configuration files, or in the Identity SQL +database using API REST calls. + +.. note:: + + Storing and managing configuration options in an SQL database is + experimental in Kilo, and added to the Identity service in the + Liberty release. + +Enable drivers for domain-specific configuration files +------------------------------------------------------ + +To enable domain-specific drivers, set these options in the +``/etc/keystone/keystone.conf`` file: + +.. code-block:: ini + + [identity] + domain_specific_drivers_enabled = True + domain_config_dir = /etc/keystone/domains + +When you enable domain-specific drivers, Identity looks in the +``domain_config_dir`` directory for configuration files that are named as +``keystone.DOMAIN_NAME.conf``. A domain without a domain-specific +configuration file uses options in the primary configuration file. + +Enable drivers for storing configuration options in SQL database +---------------------------------------------------------------- + +To enable domain-specific drivers, set these options in the +``/etc/keystone/keystone.conf`` file: + +.. code-block:: ini + + [identity] + domain_specific_drivers_enabled = True + domain_configurations_from_database = True + +Any domain-specific configuration options specified through the +Identity v3 API will override domain-specific configuration files in the +``/etc/keystone/domains`` directory. + +Migrate domain-specific configuration files to the SQL database +--------------------------------------------------------------- + +You can use the ``keystone-manage`` command to migrate configuration +options in domain-specific configuration files to the SQL database: + +.. code-block:: console + + # keystone-manage domain_config_upload --all + +To upload options from a specific domain-configuration file, specify the +domain name: + +.. code-block:: console + + # keystone-manage domain_config_upload --domain-name DOMAIN_NAME + + diff --git a/doc/source/admin/identity-external-authentication.rst b/doc/source/admin/identity-external-authentication.rst new file mode 100644 index 0000000000..62b55714e4 --- /dev/null +++ b/doc/source/admin/identity-external-authentication.rst @@ -0,0 +1,41 @@ +===================================== +External authentication with Identity +===================================== + +When Identity runs in ``apache-httpd``, you can use external +authentication methods that differ from the authentication provided by +the identity store back end. For example, you can use an SQL identity +back end together with X.509 authentication and Kerberos, instead of +using the user name and password combination. + +Use HTTPD authentication +~~~~~~~~~~~~~~~~~~~~~~~~ + +Web servers, like Apache HTTP, support many methods of authentication. +Identity can allow the web server to perform the authentication. The web +server then passes the authenticated user to Identity by using the +``REMOTE_USER`` environment variable. This user must already exist in +the Identity back end to get a token from the controller. To use this +method, Identity should run on ``apache-httpd``. + +Use X.509 +~~~~~~~~~ + +The following Apache configuration snippet authenticates the user based +on a valid X.509 certificate from a known CA: + +.. code-block:: none + + + SSLEngine on + SSLCertificateFile /etc/ssl/certs/ssl.cert + SSLCertificateKeyFile /etc/ssl/private/ssl.key + + SSLCACertificatePath /etc/ssl/allowed_cas + SSLCARevocationPath /etc/ssl/allowed_cas + SSLUserName SSL_CLIENT_S_DN_CN + SSLVerifyClient require + SSLVerifyDepth 10 + + (...) + diff --git a/doc/source/admin/identity-fernet-token-faq.rst b/doc/source/admin/identity-fernet-token-faq.rst new file mode 100644 index 0000000000..2b2cdb0cb7 --- /dev/null +++ b/doc/source/admin/identity-fernet-token-faq.rst @@ -0,0 +1,345 @@ +=================================== +Fernet - Frequently Asked Questions +=================================== + +The following questions have been asked periodically since the initial release +of the fernet token format in Kilo. + +What are the different types of keys? +~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ + +A key repository is required by keystone in order to create fernet tokens. +These keys are used to encrypt and decrypt the information that makes up the +payload of the token. Each key in the repository can have one of three states. +The state of the key determines how keystone uses a key with fernet tokens. The +different types are as follows: + +Primary key: + There is only ever one primary key in a key repository. The primary key is + allowed to encrypt and decrypt tokens. This key is always named as the + highest index in the repository. +Secondary key: + A secondary key was at one point a primary key, but has been demoted in place + of another primary key. It is only allowed to decrypt tokens. Since it was + the primary at some point in time, its existence in the key repository is + justified. Keystone needs to be able to decrypt tokens that were created with + old primary keys. +Staged key: + The staged key is a special key that shares some similarities with secondary + keys. There can only ever be one staged key in a repository and it must + exist. Just like secondary keys, staged keys have the ability to decrypt + tokens. Unlike secondary keys, staged keys have never been a primary key. In + fact, they are opposites since the staged key will always be the next primary + key. This helps clarify the name because they are the next key staged to be + the primary key. This key is always named as ``0`` in the key repository. + +So, how does a staged key help me and why do I care about it? +~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ + +The fernet keys have a natural lifecycle. Each key starts as a staged key, is +promoted to be the primary key, and then demoted to be a secondary key. New +tokens can only be encrypted with a primary key. Secondary and staged keys are +never used to encrypt token. The staged key is a special key given the order of +events and the attributes of each type of key. The staged key is the only key +in the repository that has not had a chance to encrypt any tokens yet, but it +is still allowed to decrypt tokens. As an operator, this gives you the chance +to perform a key rotation on one keystone node, and distribute the new key set +over a span of time. This does not require the distribution to take place in an +ultra short period of time. Tokens encrypted with a primary key can be +decrypted, and validated, on other nodes where that key is still staged. + +Where do I put my key repository? +~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ + +The key repository is specified using the ``key_repository`` option in the +keystone configuration file. The keystone process should be able to read and +write to this location but it should be kept secret otherwise. Currently, +keystone only supports file-backed key repositories. + +.. code-block:: ini + + [fernet_tokens] + key_repository = /etc/keystone/fernet-keys/ + +What is the recommended way to rotate and distribute keys? +~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ + +The :command:`keystone-manage` command line utility includes a key rotation +mechanism. This mechanism will initialize and rotate keys but does not make +an effort to distribute keys across keystone nodes. The distribution of keys +across a keystone deployment is best handled through configuration management +tooling. Use :command:`keystone-manage fernet_rotate` to rotate the key +repository. + +Do fernet tokens still expire? +~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ + +Yes, fernet tokens can expire just like any other keystone token formats. + +Why should I choose fernet tokens over UUID tokens? +~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ + +Even though fernet tokens operate very similarly to UUID tokens, they do not +require persistence. The keystone token database no longer suffers bloat as a +side effect of authentication. Pruning expired tokens from the token database +is no longer required when using fernet tokens. Because fernet tokens do not +require persistence, they do not have to be replicated. As long as each +keystone node shares the same key repository, fernet tokens can be created and +validated instantly across nodes. + +Why should I choose fernet tokens over PKI or PKIZ tokens? +~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ + +The arguments for using fernet over PKI and PKIZ remain the same as UUID, in +addition to the fact that fernet tokens are much smaller than PKI and PKIZ +tokens. PKI and PKIZ tokens still require persistent storage and can sometimes +cause issues due to their size. This issue is mitigated when switching to +fernet because fernet tokens are kept under a 250 byte limit. PKI and PKIZ +tokens typically exceed 1600 bytes in length. The length of a PKI or PKIZ token +is dependent on the size of the deployment. Bigger service catalogs will result +in longer token lengths. This pattern does not exist with fernet tokens because +the contents of the encrypted payload is kept to a minimum. + +Should I rotate and distribute keys from the same keystone node every rotation? +~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ + +No, but the relationship between rotation and distribution should be lock-step. +Once you rotate keys on one keystone node, the key repository from that node +should be distributed to the rest of the cluster. Once you confirm that each +node has the same key repository state, you could rotate and distribute from +any other node in the cluster. + +If the rotation and distribution are not lock-step, a single keystone node in +the deployment will create tokens with a primary key that no other node has as +a staged key. This will cause tokens generated from one keystone node to fail +validation on other keystone nodes. + +How do I add new keystone nodes to a deployment? +~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ + +The keys used to create fernet tokens should be treated like super secret +configuration files, similar to an SSL secret key. Before a node is allowed to +join an existing cluster, issuing and validating tokens, it should have the +same key repository as the rest of the nodes in the cluster. + +How should I approach key distribution? +~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ + +Remember that key distribution is only required in multi-node keystone +deployments. If you only have one keystone node serving requests in your +deployment, key distribution is unnecessary. + +Key distribution is a problem best approached from the deployment's current +configuration management system. Since not all deployments use the same +configuration management systems, it makes sense to explore options around what +is already available for managing keys, while keeping the secrecy of the keys +in mind. Many configuration management tools can leverage something like +``rsync`` to manage key distribution. + +Key rotation is a single operation that promotes the current staged key to +primary, creates a new staged key, and prunes old secondary keys. It is easiest +to do this on a single node and verify the rotation took place properly before +distributing the key repository to the rest of the cluster. The concept behind +the staged key breaks the expectation that key rotation and key distribution +have to be done in a single step. With the staged key, we have time to inspect +the new key repository before syncing state with the rest of the cluster. Key +distribution should be an operation that can run in succession until it +succeeds. The following might help illustrate the isolation between key +rotation and key distribution. + +#. Ensure all keystone nodes in the deployment have the same key repository. +#. Pick a keystone node in the cluster to rotate from. +#. Rotate keys. + + #. Was it successful? + + #. If no, investigate issues with the particular keystone node you + rotated keys on. Fernet keys are small and the operation for + rotation is trivial. There should not be much room for error in key + rotation. It is possible that the user does not have the ability to + write new keys to the key repository. Log output from + ``keystone-manage fernet_rotate`` should give more information into + specific failures. + + #. If yes, you should see a new staged key. The old staged key should + be the new primary. Depending on the ``max_active_keys`` limit you + might have secondary keys that were pruned. At this point, the node + that you rotated on will be creating fernet tokens with a primary + key that all other nodes should have as the staged key. This is why + we checked the state of all key repositories in Step one. All other + nodes in the cluster should be able to decrypt tokens created with + the new primary key. At this point, we are ready to distribute the + new key set. + +#. Distribute the new key repository. + + #. Was it successful? + + #. If yes, you should be able to confirm that all nodes in the cluster + have the same key repository that was introduced in Step 3. All + nodes in the cluster will be creating tokens with the primary key + that was promoted in Step 3. No further action is required until the + next schedule key rotation. + + #. If no, try distributing again. Remember that we already rotated the + repository and performing another rotation at this point will + result in tokens that cannot be validated across certain hosts. + Specifically, the hosts that did not get the latest key set. You + should be able to distribute keys until it is successful. If certain + nodes have issues syncing, it could be permission or network issues + and those should be resolved before subsequent rotations. + +How long should I keep my keys around? +~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ + +The fernet tokens that keystone creates are only secure as the keys creating +them. With staged keys the penalty of key rotation is low, allowing you to err +on the side of security and rotate weekly, daily, or even hourly. Ultimately, +this should be less time than it takes an attacker to break a ``AES256`` key +and a ``SHA256 HMAC``. + +Is a fernet token still a bearer token? +~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ + +Yes, and they follow exactly the same validation path as UUID tokens, with the +exception of being written to, and read from, a back end. If someone +compromises your fernet token, they have the power to do all the operations you +are allowed to do. + +What if I need to revoke all my tokens? +~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ + +To invalidate every token issued from keystone and start fresh, remove the +current key repository, create a new key set, and redistribute it to all nodes +in the cluster. This will render every token issued from keystone as invalid +regardless if the token has actually expired. When a client goes to +re-authenticate, the new token will have been created with a new fernet key. + +What can an attacker do if they compromise a fernet key in my deployment? +~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ + +If any key used in the key repository is compromised, an attacker will be able +to build their own tokens. If they know the ID of an administrator on a +project, they could generate administrator tokens for the project. They will be +able to generate their own tokens until the compromised key has been removed +from from the repository. + +I rotated keys and now tokens are invalidating early, what did I do? +~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ + +Using fernet tokens requires some awareness around token expiration and the key +lifecycle. You do not want to rotate so often that secondary keys are removed +that might still be needed to decrypt unexpired tokens. If this happens, you +will not be able to decrypt the token because the key the was used to encrypt +it is now gone. Only remove keys that you know are not being used to encrypt or +decrypt tokens. + +For example, your token is valid for 24 hours and we want to rotate keys every +six hours. We will need to make sure tokens that were created at 08:00 AM on +Monday are still valid at 07:00 AM on Tuesday, assuming they were not +prematurely revoked. To accomplish this, we will want to make sure we set +``max_active_keys=6`` in our keystone configuration file. This will allow us to +hold all keys that might still be required to validate a previous token, but +keeps the key repository limited to only the keys that are needed. + +The number of ``max_active_keys`` for a deployment can be determined by +dividing the token lifetime, in hours, by the frequency of rotation in hours +and adding two. Better illustrated as:: + + token_expiration = 24 + rotation_frequency = 6 + max_active_keys = (token_expiration / rotation_frequency) + 2 + +The reason for adding two additional keys to the count is to include the staged +key and a buffer key. This can be shown based on the previous example. We +initially setup the key repository at 6:00 AM on Monday, and the initial state +looks like: + +.. code-block:: console + + $ ls -la /etc/keystone/fernet-keys/ + drwx------ 2 keystone keystone 4096 . + drwxr-xr-x 3 keystone keystone 4096 .. + -rw------- 1 keystone keystone 44 0 (staged key) + -rw------- 1 keystone keystone 44 1 (primary key) + +All tokens created after 6:00 AM are encrypted with key ``1``. At 12:00 PM we +will rotate keys again, resulting in, + +.. code-block:: console + + $ ls -la /etc/keystone/fernet-keys/ + drwx------ 2 keystone keystone 4096 . + drwxr-xr-x 3 keystone keystone 4096 .. + -rw------- 1 keystone keystone 44 0 (staged key) + -rw------- 1 keystone keystone 44 1 (secondary key) + -rw------- 1 keystone keystone 44 2 (primary key) + +We are still able to validate tokens created between 6:00 - 11:59 AM because +the ``1`` key still exists as a secondary key. All tokens issued after 12:00 PM +will be encrypted with key ``2``. At 6:00 PM we do our next rotation, resulting +in: + +.. code-block:: console + + $ ls -la /etc/keystone/fernet-keys/ + drwx------ 2 keystone keystone 4096 . + drwxr-xr-x 3 keystone keystone 4096 .. + -rw------- 1 keystone keystone 44 0 (staged key) + -rw------- 1 keystone keystone 44 1 (secondary key) + -rw------- 1 keystone keystone 44 2 (secondary key) + -rw------- 1 keystone keystone 44 3 (primary key) + +It is still possible to validate tokens issued from 6:00 AM - 5:59 PM because +keys ``1`` and ``2`` exist as secondary keys. Every token issued until 11:59 PM +will be encrypted with key ``3``, and at 12:00 AM we do our next rotation: + +.. code-block:: console + + $ ls -la /etc/keystone/fernet-keys/ + drwx------ 2 keystone keystone 4096 . + drwxr-xr-x 3 keystone keystone 4096 .. + -rw------- 1 keystone keystone 44 0 (staged key) + -rw------- 1 keystone keystone 44 1 (secondary key) + -rw------- 1 keystone keystone 44 2 (secondary key) + -rw------- 1 keystone keystone 44 3 (secondary key) + -rw------- 1 keystone keystone 44 4 (primary key) + +Just like before, we can still validate tokens issued from 6:00 AM the previous +day until 5:59 AM today because keys ``1`` - ``4`` are present. At 6:00 AM, +tokens issued from the previous day will start to expire and we do our next +scheduled rotation: + +.. code-block:: console + + $ ls -la /etc/keystone/fernet-keys/ + drwx------ 2 keystone keystone 4096 . + drwxr-xr-x 3 keystone keystone 4096 .. + -rw------- 1 keystone keystone 44 0 (staged key) + -rw------- 1 keystone keystone 44 1 (secondary key) + -rw------- 1 keystone keystone 44 2 (secondary key) + -rw------- 1 keystone keystone 44 3 (secondary key) + -rw------- 1 keystone keystone 44 4 (secondary key) + -rw------- 1 keystone keystone 44 5 (primary key) + +Tokens will naturally expire after 6:00 AM, but we will not be able to remove +key ``1`` until the next rotation because it encrypted all tokens from 6:00 AM +to 12:00 PM the day before. Once we do our next rotation, which is at 12:00 PM, +the ``1`` key will be pruned from the repository: + +.. code-block:: console + + $ ls -la /etc/keystone/fernet-keys/ + drwx------ 2 keystone keystone 4096 . + drwxr-xr-x 3 keystone keystone 4096 .. + -rw------- 1 keystone keystone 44 0 (staged key) + -rw------- 1 keystone keystone 44 2 (secondary key) + -rw------- 1 keystone keystone 44 3 (secondary key) + -rw------- 1 keystone keystone 44 4 (secondary key) + -rw------- 1 keystone keystone 44 5 (secondary key) + -rw------- 1 keystone keystone 44 6 (primary key) + +If keystone were to receive a token that was created between 6:00 AM and 12:00 +PM the day before, encrypted with the ``1`` key, it would not be valid because +it was already expired. This makes it possible for us to remove the ``1`` key +from the repository without negative validation side-effects. diff --git a/doc/source/admin/identity-integrate-with-ldap.rst b/doc/source/admin/identity-integrate-with-ldap.rst new file mode 100644 index 0000000000..a2ad2fb41d --- /dev/null +++ b/doc/source/admin/identity-integrate-with-ldap.rst @@ -0,0 +1,453 @@ +.. _integrate-identity-with-ldap: + +============================ +Integrate Identity with LDAP +============================ + +The OpenStack Identity service supports integration with existing LDAP +directories for authentication and authorization services. LDAP back +ends require initialization before configuring the OpenStack Identity +service to work with it. For more information, see `Setting up LDAP +for use with Keystone `__. + +When the OpenStack Identity service is configured to use LDAP back ends, +you can split authentication (using the *identity* feature) and +authorization (using the *assignment* feature). + +The *identity* feature enables administrators to manage users and groups +by each domain or the OpenStack Identity service entirely. + +The *assignment* feature enables administrators to manage project role +authorization using the OpenStack Identity service SQL database, while +providing user authentication through the LDAP directory. + +.. _identity_ldap_server_setup: + +Identity LDAP server set up +~~~~~~~~~~~~~~~~~~~~~~~~~~~ + +.. important:: + + For the OpenStack Identity service to access LDAP servers, you must + enable the ``authlogin_nsswitch_use_ldap`` boolean value for SELinux + on the server running the OpenStack Identity service. To enable and + make the option persistent across reboots, set the following boolean + value as the root user: + + .. code-block:: console + + # setsebool -P authlogin_nsswitch_use_ldap on + +The Identity configuration is split into two separate back ends; identity +(back end for users and groups), and assignments (back end for domains, +projects, roles, role assignments). To configure Identity, set options +in the ``/etc/keystone/keystone.conf`` file. See +:ref:`integrate-identity-backend-ldap` for Identity back end configuration +examples. Modify these examples as needed. + +**To define the destination LDAP server** + +#. Define the destination LDAP server in the + ``/etc/keystone/keystone.conf`` file: + + .. code-block:: ini + + [ldap] + url = ldap://localhost + user = dc=Manager,dc=example,dc=org + password = samplepassword + suffix = dc=example,dc=org + +**Additional LDAP integration settings** + +Set these options in the ``/etc/keystone/keystone.conf`` file for a +single LDAP server, or ``/etc/keystone/domains/keystone.DOMAIN_NAME.conf`` +files for multiple back ends. Example configurations appear below each +setting summary: + +**Query option** + +.. hlist:: + :columns: 1 + + * Use ``query_scope`` to control the scope level of data presented + (search only the first level or search an entire sub-tree) + through LDAP. + * Use ``page_size`` to control the maximum results per page. A value + of zero disables paging. + * Use ``alias_dereferencing`` to control the LDAP dereferencing + option for queries. + +.. code-block:: ini + + [ldap] + query_scope = sub + page_size = 0 + alias_dereferencing = default + chase_referrals = + +**Debug** + +Use ``debug_level`` to set the LDAP debugging level for LDAP calls. +A value of zero means that debugging is not enabled. + +.. code-block:: ini + + [ldap] + debug_level = 0 + +.. warning:: + + This value is a bitmask, consult your LDAP documentation for + possible values. + +**Connection pooling** + +Use ``use_pool`` to enable LDAP connection pooling. Configure the +connection pool size, maximum retry, reconnect trials, timeout (-1 +indicates indefinite wait) and lifetime in seconds. + +.. code-block:: ini + + [ldap] + use_pool = true + pool_size = 10 + pool_retry_max = 3 + pool_retry_delay = 0.1 + pool_connection_timeout = -1 + pool_connection_lifetime = 600 + +**Connection pooling for end user authentication** + +Use ``use_auth_pool`` to enable LDAP connection pooling for end user +authentication. Configure the connection pool size and lifetime in +seconds. + +.. code-block:: ini + + [ldap] + use_auth_pool = false + auth_pool_size = 100 + auth_pool_connection_lifetime = 60 + +When you have finished the configuration, restart the OpenStack Identity +service. + +.. warning:: + + During the service restart, authentication and authorization are + unavailable. + +.. _integrate-identity-backend-ldap: + +Integrate Identity back end with LDAP +~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ + +The Identity back end contains information for users, groups, and group +member lists. Integrating the Identity back end with LDAP allows +administrators to use users and groups in LDAP. + +.. important:: + + For OpenStack Identity service to access LDAP servers, you must + define the destination LDAP server in the + ``/etc/keystone/keystone.conf`` file. For more information, + see :ref:`identity_ldap_server_setup`. + +**To integrate one Identity back end with LDAP** + +#. Enable the LDAP Identity driver in the ``/etc/keystone/keystone.conf`` + file. This allows LDAP as an identity back end: + + .. code-block:: ini + + [identity] + #driver = sql + driver = ldap + +#. Create the organizational units (OU) in the LDAP directory, and define + the corresponding location in the ``/etc/keystone/keystone.conf`` + file: + + .. code-block:: ini + + [ldap] + user_tree_dn = ou=Users,dc=example,dc=org + user_objectclass = inetOrgPerson + + group_tree_dn = ou=Groups,dc=example,dc=org + group_objectclass = groupOfNames + + .. note:: + + These schema attributes are extensible for compatibility with + various schemas. For example, this entry maps to the person + attribute in Active Directory: + + .. code-block:: ini + + user_objectclass = person + +#. A read-only implementation is recommended for LDAP integration. These + permissions are applied to object types in the + ``/etc/keystone/keystone.conf`` file: + + .. code-block:: ini + + [ldap] + user_allow_create = False + user_allow_update = False + user_allow_delete = False + + group_allow_create = False + group_allow_update = False + group_allow_delete = False + + Restart the OpenStack Identity service. + + .. warning:: + + During service restart, authentication and authorization are + unavailable. + +**To integrate multiple Identity back ends with LDAP** + +#. Set the following options in the ``/etc/keystone/keystone.conf`` + file: + + #. Enable the LDAP driver: + + .. code-block:: ini + + [identity] + #driver = sql + driver = ldap + + #. Enable domain-specific drivers: + + .. code-block:: ini + + [identity] + domain_specific_drivers_enabled = True + domain_config_dir = /etc/keystone/domains + +#. Restart the OpenStack Identity service. + + .. warning:: + + During service restart, authentication and authorization are + unavailable. + +#. List the domains using the dashboard, or the OpenStackClient CLI. Refer + to the `Command List + `__ + for a list of OpenStackClient commands. + +#. Create domains using OpenStack dashboard, or the OpenStackClient CLI. + +#. For each domain, create a domain-specific configuration file in the + ``/etc/keystone/domains`` directory. Use the file naming convention + ``keystone.DOMAIN_NAME.conf``, where DOMAIN\_NAME is the domain name + assigned in the previous step. + + .. note:: + + The options set in the + ``/etc/keystone/domains/keystone.DOMAIN_NAME.conf`` file will + override options in the ``/etc/keystone/keystone.conf`` file. + +#. Define the destination LDAP server in the + ``/etc/keystone/domains/keystone.DOMAIN_NAME.conf`` file. For example: + + .. code-block:: ini + + [ldap] + url = ldap://localhost + user = dc=Manager,dc=example,dc=org + password = samplepassword + suffix = dc=example,dc=org + +#. Create the organizational units (OU) in the LDAP directories, and define + their corresponding locations in the + ``/etc/keystone/domains/keystone.DOMAIN_NAME.conf`` file. For example: + + .. code-block:: ini + + [ldap] + user_tree_dn = ou=Users,dc=example,dc=org + user_objectclass = inetOrgPerson + + group_tree_dn = ou=Groups,dc=example,dc=org + group_objectclass = groupOfNames + + .. note:: + + These schema attributes are extensible for compatibility with + various schemas. For example, this entry maps to the person + attribute in Active Directory: + + .. code-block:: ini + + user_objectclass = person + +#. A read-only implementation is recommended for LDAP integration. These + permissions are applied to object types in the + ``/etc/keystone/domains/keystone.DOMAIN_NAME.conf`` file: + + .. code-block:: ini + + [ldap] + user_allow_create = False + user_allow_update = False + user_allow_delete = False + + group_allow_create = False + group_allow_update = False + group_allow_delete = False + +#. Restart the OpenStack Identity service. + + .. warning:: + + During service restart, authentication and authorization are + unavailable. + +**Additional LDAP integration settings** + +Set these options in the ``/etc/keystone/keystone.conf`` file for a +single LDAP server, or ``/etc/keystone/domains/keystone.DOMAIN_NAME.conf`` +files for multiple back ends. Example configurations appear below each +setting summary: + +Filters + Use filters to control the scope of data presented through LDAP. + + .. code-block:: ini + + [ldap] + user_filter = (memberof=cn=openstack-users,ou=workgroups,dc=example,dc=org) + group_filter = + +Identity attribute mapping + Mask account status values (include any additional attribute + mappings) for compatibility with various directory services. + Superfluous accounts are filtered with ``user_filter``. + + Setting attribute ignore to list of attributes stripped off on + update. + + For example, you can mask Active Directory account status attributes + in the ``/etc/keystone/keystone.conf`` file: + + .. code-block:: ini + + [ldap] + user_id_attribute = cn + user_name_attribute = sn + user_mail_attribute = mail + user_pass_attribute = userPassword + user_enabled_attribute = userAccountControl + user_enabled_mask = 2 + user_enabled_invert = false + user_enabled_default = 512 + user_default_project_id_attribute = + user_additional_attribute_mapping = + + group_id_attribute = cn + group_name_attribute = ou + group_member_attribute = member + group_desc_attribute = description + group_additional_attribute_mapping = + +Enabled emulation + An alternative method to determine if a user is enabled or not is by + checking if that user is a member of the emulation group. + + Use DN of the group entry to hold enabled user when using enabled + emulation. + + .. code-block:: ini + + [ldap] + user_enabled_emulation = false + user_enabled_emulation_dn = false + +When you have finished configuration, restart the OpenStack Identity +service. + +.. warning:: + + During service restart, authentication and authorization are + unavailable. + +Secure the OpenStack Identity service connection to an LDAP back end +~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ + +The Identity service supports the use of TLS to encrypt LDAP traffic. +Before configuring this, you must first verify where your certificate +authority file is located. For more information, see the +`OpenStack Security Guide SSL introduction `_. + +Once you verify the location of your certificate authority file: + +**To configure TLS encryption on LDAP traffic** + +#. Open the ``/etc/keystone/keystone.conf`` configuration file. + +#. Find the ``[ldap]`` section. + +#. In the ``[ldap]`` section, set the ``use_tls`` configuration key to + ``True``. Doing so will enable TLS. + +#. Configure the Identity service to use your certificate authorities file. + To do so, set the ``tls_cacertfile`` configuration key in the ``ldap`` + section to the certificate authorities file's path. + + .. note:: + + You can also set the ``tls_cacertdir`` (also in the ``ldap`` + section) to the directory where all certificate authorities files + are kept. If both ``tls_cacertfile`` and ``tls_cacertdir`` are set, + then the latter will be ignored. + +#. Specify what client certificate checks to perform on incoming TLS + sessions from the LDAP server. To do so, set the ``tls_req_cert`` + configuration key in the ``[ldap]`` section to ``demand``, ``allow``, or + ``never``: + + .. hlist:: + :columns: 1 + + * ``demand`` - The LDAP server always receives certificate + requests. The session terminates if no certificate + is provided, or if the certificate provided cannot be verified + against the existing certificate authorities file. + * ``allow`` - The LDAP server always receives certificate + requests. The session will proceed as normal even if a certificate + is not provided. If a certificate is provided but it cannot be + verified against the existing certificate authorities file, the + certificate will be ignored and the session will proceed as + normal. + * ``never`` - A certificate will never be requested. + +On distributions that include openstack-config, you can configure TLS +encryption on LDAP traffic by running the following commands instead. + +.. code-block:: console + + # openstack-config --set /etc/keystone/keystone.conf \ + ldap use_tls True + # openstack-config --set /etc/keystone/keystone.conf \ + ldap tls_cacertfile ``CA_FILE`` + # openstack-config --set /etc/keystone/keystone.conf \ + ldap tls_req_cert ``CERT_BEHAVIOR`` + +Where: + +- ``CA_FILE`` is the absolute path to the certificate authorities file + that should be used to encrypt LDAP traffic. + +- ``CERT_BEHAVIOR`` specifies what client certificate checks to perform + on an incoming TLS session from the LDAP server (``demand``, + ``allow``, or ``never``). diff --git a/doc/source/admin/identity-keystone-usage-and-features.rst b/doc/source/admin/identity-keystone-usage-and-features.rst new file mode 100644 index 0000000000..7a71aaac72 --- /dev/null +++ b/doc/source/admin/identity-keystone-usage-and-features.rst @@ -0,0 +1,83 @@ + +Example usage and Identity features +~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ + +The ``openstack`` CLI is used to interact with the Identity service. +It is set up to expect commands in the general +form of ``openstack command argument``, followed by flag-like keyword +arguments to provide additional (often optional) information. For +example, the :command:`openstack user list` and +:command:`openstack project create` commands can be invoked as follows: + +.. code-block:: bash + + # Using token auth env variables + export OS_SERVICE_ENDPOINT=http://127.0.0.1:5000/v2.0/ + export OS_SERVICE_TOKEN=secrete_token + openstack user list + openstack project create demo --domain default + + # Using token auth flags + openstack --os-token secrete --os-endpoint http://127.0.0.1:5000/v2.0/ user list + openstack --os-token secrete --os-endpoint http://127.0.0.1:5000/v2.0/ project create demo + + # Using user + password + project_name env variables + export OS_USERNAME=admin + export OS_PASSWORD=secrete + export OS_PROJECT_NAME=admin + openstack user list + openstack project create demo --domain default + + # Using user + password + project-name flags + openstack --os-username admin --os-password secrete --os-project-name admin user list + openstack --os-username admin --os-password secrete --os-project-name admin project create demo + + +Logging +------- + +You configure logging externally to the rest of Identity. The name of +the file specifying the logging configuration is set using the +``log_config`` option in the ``[DEFAULT]`` section of the +``/etc/keystone/keystone.conf`` file. To route logging through syslog, +set ``use_syslog=true`` in the ``[DEFAULT]`` section. + +A sample logging configuration file is available with the project in +``etc/logging.conf.sample``. Like other OpenStack projects, Identity +uses the Python logging module, which provides extensive configuration +options that let you define the output levels and formats. + + +User CRUD +--------- + +Identity provides a user CRUD (Create, Read, Update, and Delete) filter that +Administrators can add to the ``public_api`` pipeline. The user CRUD filter +enables users to use a HTTP PATCH to change their own password. To enable +this extension you should define a ``user_crud_extension`` filter, insert +it after the ``*_body`` middleware and before the ``public_service`` +application in the ``public_api`` WSGI pipeline in +``keystone-paste.ini``. For example: + +.. code-block:: ini + + [filter:user_crud_extension] + paste.filter_factory = keystone.contrib.user_crud:CrudExtension.factory + + [pipeline:public_api] + pipeline = sizelimit url_normalize request_id build_auth_context token_auth admin_token_auth json_body ec2_extension user_crud_extension public_service + +Each user can then change their own password with a HTTP PATCH. + +.. code-block:: console + + $ curl -X PATCH http://localhost:5000/v2.0/OS-KSCRUD/users/USERID -H "Content-type: application/json" \ + -H "X_Auth_Token: AUTHTOKENID" -d '{"user": {"password": "ABCD", "original_password": "DCBA"}}' + +In addition to changing their password, all current tokens for the user +are invalidated. + +.. note:: + + Only use a KVS back end for tokens when testing. + diff --git a/doc/source/admin/identity-management.rst b/doc/source/admin/identity-management.rst new file mode 100644 index 0000000000..3c740b7ca1 --- /dev/null +++ b/doc/source/admin/identity-management.rst @@ -0,0 +1,31 @@ +.. _identity_management: + +==================== +Administrator Guides +==================== + +OpenStack Identity, code-named keystone, is the default Identity +management system for OpenStack. After you install Identity, you +configure it through the ``/etc/keystone/keystone.conf`` +configuration file and, possibly, a separate logging configuration +file. You initialize data into Identity by using the ``keystone`` +command-line client. + +.. toctree:: + :maxdepth: 1 + + identity-concepts.rst + identity-certificates-for-pki.rst + identity-domain-specific-config.rst + identity-external-authentication.rst + identity-integrate-with-ldap.rst + identity-tokens.rst + identity-token-binding.rst + identity-fernet-token-faq.rst + identity-use-trusts.rst + identity-caching-layer.rst + identity-security-compliance.rst + identity-keystone-usage-and-features.rst + identity-auth-token-middleware.rst + identity-service-api-protection.rst + identity-troubleshoot.rst diff --git a/doc/source/admin/identity-security-compliance.rst b/doc/source/admin/identity-security-compliance.rst new file mode 100644 index 0000000000..aefce53928 --- /dev/null +++ b/doc/source/admin/identity-security-compliance.rst @@ -0,0 +1,167 @@ +.. _identity_security_compliance: + +=============================== +Security compliance and PCI-DSS +=============================== + +As of the Newton release, the Identity service contains additional security +compliance features, specifically to satisfy Payment Card Industry - +Data Security Standard (PCI-DSS) v3.1 requirements. See +`Security Hardening PCI-DSS`_ for more information on PCI-DSS. + +Security compliance features are disabled by default and most of the features +only apply to the SQL backend for the identity driver. Other identity backends, +such as LDAP, should implement their own security controls. + +Enable these features by changing the configuration settings under the +``[security_compliance]`` section in ``keystone.conf``. + +Setting the account lockout threshold +------------------------------------- + +The account lockout feature limits the number of incorrect password attempts. +If a user fails to authenticate after the maximum number of attempts, the +service disables the user. Re-enable the user by explicitly setting the +enable user attribute with the update user API call, either +`v2.0`_ or `v3`_. + +You set the maximum number of failed authentication attempts by setting +the ``lockout_failure_attempts``: + +.. code-block:: ini + + [security_compliance] + lockout_failure_attempts = 6 + +You set the number of minutes a user would be locked out by setting +the ``lockout_duration`` in seconds: + +.. code-block:: ini + + [security_compliance] + lockout_duration = 1800 + +If you do not set the ``lockout_duration``, users may be locked out +indefinitely until the user is explicitly enabled via the API. + +Disabling inactive users +------------------------ + +PCI-DSS 8.1.4 requires that inactive user accounts be removed or disabled +within 90 days. You can achieve this by setting the +``disable_user_account_days_inactive``: + +.. code-block:: ini + + [security_compliance] + disable_user_account_days_inactive = 90 + +This above example means that users that have not authenticated (inactive) for +the past 90 days are automatically disabled. Users can be re-enabled by +explicitly setting the enable user attribute via the API. + +Configuring password expiration +------------------------------- + +Passwords can be configured to expire within a certain number of days by +setting the ``password_expires_days``: + +.. code-block:: ini + + [security_compliance] + password_expires_days = 90 + +Once set, any new password changes have an expiration date based on the +date/time of the password change plus the number of days defined here. Existing +passwords will not be impacted. If you want existing passwords to have an +expiration date, you would need to run a SQL script against the password table +in the database to update the expires_at column. + +In addition, you can set it so that passwords never expire for some users by +adding their user ID to ``password_expires_ignore_user_ids`` list: + +.. code-block:: ini + + [security_compliance] + password_expires_ignore_user_ids = [3a54353c9dcc44f690975ea768512f6a] + +In this example, the password for user ID ``3a54353c9dcc44f690975ea768512f6a`` +would never expire. + +Indicating password strength requirements +----------------------------------------- + +You set password strength requirements, such as requiring numbers in passwords +or setting a minimum password length, by adding a regular expression to the +``password_regex``: + +.. code-block:: ini + + [security_compliance] + password_regex = ^(?=.*\d)(?=.*[a-zA-Z]).{7,}$ + +The above example is a regular expression that requires a password to have +one letter, one digit, and a minimum length of seven characters. + +If you do set the ``password_regex``, you should provide text that +describes your password strength requirements. You can do this by setting the +``password_regex_description``: + +.. code-block:: ini + + [security_compliance] + password_regex_description = Passwords must contain at least 1 letter, 1 + digit, and be a minimum length of 7 + characters. + +The service returns that description to users to explain why their requested +password did not meet requirements. + +.. note:: + + You must ensure the ``password_regex_description`` accurately and + completely describes the ``password_regex``. If the two options are out of + sync, the help text could inaccurately describe the password requirements + being applied to the password. This would lead to poor user experience. + +Requiring a unique password history +----------------------------------- + +The password history requirements controls the number of passwords for a user +that must be unique before an old password can be reused. You can enforce this +by setting the ``unique_last_password_count``: + +.. code-block:: ini + + [security_compliance] + unique_last_password_count= 5 + +The above example does not allow a user to create a new password that is the +same as any of their last four previous passwords. + +Similarly, you can set the number of days that a password must be used before +the user can change it by setting the ``minimum_password_age``: + +.. code-block:: ini + + [security_compliance] + minimum_password_age = 1 + +In the above example, once a user changes their password, they would not be +able to change it again for one day. This prevents users from changing their +passwords immediately in order to wipe out their password history and reuse an +old password. + +.. note:: + + When you set ``password_expires_days``, the value for the + ``minimum_password_age`` should be less than the ``password_expires_days``. + Otherwise, users would not be able to change their passwords before they + expire. + +.. _Security Hardening PCI-DSS: https://specs.openstack.org/openstack/keystone-specs/specs/keystone/newton/pci-dss.html + + +.. _v2.0: https://developer.openstack.org/api-ref/identity/v2-admin/index.html?expanded=update-user-admin-endpoint-detail#update-user-admin-endpoint + +.. _v3: https://developer.openstack.org/api-ref/identity/v3/index.html#update-user diff --git a/doc/source/admin/identity-service-api-protection.rst b/doc/source/admin/identity-service-api-protection.rst new file mode 100644 index 0000000000..99e181ad1b --- /dev/null +++ b/doc/source/admin/identity-service-api-protection.rst @@ -0,0 +1,128 @@ +============================================================= +Identity API protection with role-based access control (RBAC) +============================================================= + +Like most OpenStack projects, Identity supports the protection of its +APIs by defining policy rules based on an RBAC approach. Identity stores +a reference to a policy JSON file in the main Identity configuration +file, ``/etc/keystone/keystone.conf``. Typically this file is named +``policy.json``, and contains the rules for which roles have access to +certain actions in defined services. + +Each Identity API v3 call has a line in the policy file that dictates +which level of governance of access applies. + +.. code-block:: none + + API_NAME: RULE_STATEMENT or MATCH_STATEMENT + +Where: + +``RULE_STATEMENT`` can contain ``RULE_STATEMENT`` or +``MATCH_STATEMENT``. + +``MATCH_STATEMENT`` is a set of identifiers that must match between the +token provided by the caller of the API and the parameters or target +entities of the API call in question. For example: + +.. code-block:: none + + "identity:create_user": "role:admin and domain_id:%(user.domain_id)s" + +Indicates that to create a user, you must have the admin role in your +token. The ``domain_id`` in your token must match the +``domain_id`` in the user object that you are trying +to create, which implies this must be a domain-scoped token. +In other words, you must have the admin role on the domain +in which you are creating the user, and the token that you use +must be scoped to that domain. + +Each component of a match statement uses this format: + +.. code-block:: none + + ATTRIB_FROM_TOKEN:CONSTANT or ATTRIB_RELATED_TO_API_CALL + +The Identity service expects these attributes: + +Attributes from token: + +- ``user_id`` +- ``domain_id`` +- ``project_id`` + +The ``project_id`` attribute requirement depends on the scope, and the +list of roles you have within that scope. + +Attributes related to API call: + +- ``user.domain_id`` +- Any parameters passed into the API call +- Any filters specified in the query string + +You reference attributes of objects passed with an object.attribute +syntax (such as, ``user.domain_id``). The target objects of an API are +also available using a target.object.attribute syntax. For instance: + +.. code-block:: none + + "identity:delete_user": "role:admin and domain_id:%(target.user.domain_id)s" + +would ensure that Identity only deletes the user object in the same +domain as the provided token. + +Every target object has an ``id`` and a ``name`` available as +``target.OBJECT.id`` and ``target.OBJECT.name``. Identity retrieves +other attributes from the database, and the attributes vary between +object types. The Identity service filters out some database fields, +such as user passwords. + +List of object attributes: + +.. code-block:: yaml + + role: + target.role.id + target.role.name + + user: + target.user.default_project_id + target.user.description + target.user.domain_id + target.user.enabled + target.user.id + target.user.name + + group: + target.group.description + target.group.domain_id + target.group.id + target.group.name + + domain: + target.domain.enabled + target.domain.id + target.domain.name + + project: + target.project.description + target.project.domain_id + target.project.enabled + target.project.id + target.project.name + +The default ``policy.json`` file supplied provides a somewhat +basic example of API protection, and does not assume any particular +use of domains. Refer to ``policy.v3cloudsample.json`` as an +example of multi-domain configuration installations where a cloud +provider wants to delegate administration of the contents of a domain +to a particular ``admin domain``. This example policy file also +shows the use of an ``admin_domain`` to allow a cloud provider to +enable administrators to have wider access across the APIs. + +A clean installation could start with the standard policy file, to +allow creation of the ``admin_domain`` with the first users within +it. You could then obtain the ``domain_id`` of the admin domain, +paste the ID into a modified version of +``policy.v3cloudsample.json``, and then enable it as the main +``policy file``. diff --git a/doc/source/admin/identity-token-binding.rst b/doc/source/admin/identity-token-binding.rst new file mode 100644 index 0000000000..82a7c837ba --- /dev/null +++ b/doc/source/admin/identity-token-binding.rst @@ -0,0 +1,64 @@ +============================================ +Configure Identity service for token binding +============================================ + +Token binding embeds information from an external authentication +mechanism, such as a Kerberos server or X.509 certificate, inside a +token. By using token binding, a client can enforce the use of a +specified external authentication mechanism with the token. This +additional security mechanism ensures that if a token is stolen, for +example, it is not usable without external authentication. + +You configure the authentication types for a token binding in the +``/etc/keystone/keystone.conf`` file: + +.. code-block:: ini + + [token] + bind = kerberos + +or + +.. code-block:: ini + + [token] + bind = x509 + +Currently ``kerberos`` and ``x509`` are supported. + +To enforce checking of token binding, set the ``enforce_token_bind`` +option to one of these modes: + +- ``disabled`` + Disables token bind checking. + +- ``permissive`` + Enables bind checking. If a token is bound to an unknown + authentication mechanism, the server ignores it. The default is this + mode. + +- ``strict`` + Enables bind checking. If a token is bound to an unknown + authentication mechanism, the server rejects it. + +- ``required`` + Enables bind checking. Requires use of at least authentication + mechanism for tokens. + +- ``kerberos`` + Enables bind checking. Requires use of kerberos as the authentication + mechanism for tokens: + + .. code-block:: ini + + [token] + enforce_token_bind = kerberos + +- ``x509`` + Enables bind checking. Requires use of X.509 as the authentication + mechanism for tokens: + + .. code-block:: ini + + [token] + enforce_token_bind = x509 diff --git a/doc/source/admin/identity-tokens.rst b/doc/source/admin/identity-tokens.rst new file mode 100644 index 0000000000..2932fb3249 --- /dev/null +++ b/doc/source/admin/identity-tokens.rst @@ -0,0 +1,108 @@ +=============== +Keystone tokens +=============== + +Tokens are used to authenticate and authorize your interactions with the +various OpenStack APIs. Tokens come in many flavors, representing various +authorization scopes and sources of identity. There are also several different +"token providers", each with their own user experience, performance, and +deployment characteristics. + +Authorization scopes +-------------------- + +Tokens can express your authorization in different scopes. You likely have +different sets of roles, in different projects, and in different domains. +While tokens always express your identity, they may only ever express one set +of roles in one authorization scope at a time. + +Each level of authorization scope is useful for certain types of operations in +certain OpenStack services, and are not interchangeable. + +Unscoped tokens +~~~~~~~~~~~~~~~ + +An unscoped token contains neither a service catalog, any roles, a project +scope, nor a domain scope. Their primary use case is simply to prove your +identity to keystone at a later time (usually to generate scoped tokens), +without repeatedly presenting your original credentials. + +The following conditions must be met to receive an unscoped token: + +* You must not specify an authorization scope in your authentication request + (for example, on the command line with arguments such as + ``--os-project-name`` or ``--os-domain-id``), + +* Your identity must not have a "default project" associated with it that you + also have role assignments, and thus authorization, upon. + +Project-scoped tokens +~~~~~~~~~~~~~~~~~~~~~ + +Project-scoped tokens are the bread and butter of OpenStack. They express your +authorization to operate in a specific tenancy of the cloud and are useful to +authenticate yourself when working with most other services. + +They contain a service catalog, a set of roles, and details of the project upon +which you have authorization. + +Domain-scoped tokens +~~~~~~~~~~~~~~~~~~~~ + +Domain-scoped tokens also have limited use cases in OpenStack. They express +your authorization to operate a domain-level, above that of the user and +projects contained therein (typically as a domain-level administrator). +Depending on Keystone's configuration, they are useful for working with a +single domain in Keystone. + +They contain a limited service catalog (only those services which do not +explicitly require per-project endpoints), a set of roles, and details of the +project upon which you have authorization. + +They can also be used to work with domain-level concerns in other services, +such as to configure domain-wide quotas that apply to all users or projects in +a specific domain. + +Token providers +--------------- + +The token type issued by keystone is configurable through the +``/etc/keystone/keystone.conf`` file. Currently, there are four supported +token types and they include ``UUID``, ``fernet``, ``PKI``, and ``PKIZ``. + +UUID tokens +~~~~~~~~~~~ + +UUID was the first token type supported and is currently the default token +provider. UUID tokens are 32 bytes in length and must be persisted in a back +end. Clients must pass their UUID token to the Identity service in order to +validate it. + +Fernet tokens +~~~~~~~~~~~~~ + +The fernet token format was introduced in the OpenStack Kilo release. Unlike +the other token types mentioned in this document, fernet tokens do not need to +be persisted in a back end. ``AES256`` encryption is used to protect the +information stored in the token and integrity is verified with a ``SHA256 +HMAC`` signature. Only the Identity service should have access to the keys used +to encrypt and decrypt fernet tokens. Like UUID tokens, fernet tokens must be +passed back to the Identity service in order to validate them. For more +information on the fernet token type, see the :doc:`identity-fernet-token-faq`. + +PKI and PKIZ tokens +~~~~~~~~~~~~~~~~~~~ + +PKI tokens are signed documents that contain the authentication context, as +well as the service catalog. Depending on the size of the OpenStack deployment, +these tokens can be very long. The Identity service uses public/private key +pairs and certificates in order to create and validate PKI tokens. + +The same concepts from PKI tokens apply to PKIZ tokens. The only difference +between the two is PKIZ tokens are compressed to help mitigate the size issues +of PKI. For more information on the certificate setup for PKI and PKIZ tokens, +see the :doc:`identity-certificates-for-pki`. + +.. note:: + + PKI and PKIZ tokens are deprecated and not supported in Ocata. diff --git a/doc/source/admin/identity-troubleshoot.rst b/doc/source/admin/identity-troubleshoot.rst new file mode 100644 index 0000000000..f8971ef52d --- /dev/null +++ b/doc/source/admin/identity-troubleshoot.rst @@ -0,0 +1,199 @@ +================================= +Troubleshoot the Identity service +================================= + +To troubleshoot the Identity service, review the logs in the +``/var/log/keystone/keystone.log`` file. + +Use the ``/etc/keystone/logging.conf`` file to configure the +location of log files. + +.. note:: + + The ``insecure_debug`` flag is unique to the Identity service. + If you enable ``insecure_debug``, error messages from the API change + to return security-sensitive information. For example, the error message + on failed authentication includes information on why your authentication + failed. + +The logs show the components that have come in to the WSGI request, and +ideally show an error that explains why an authorization request failed. +If you do not see the request in the logs, run keystone with the +``--debug`` parameter. Pass the ``--debug`` parameter before the +command parameters. + +Debug PKI middleware +~~~~~~~~~~~~~~~~~~~~ + +Problem +------- + +If you receive an ``Invalid OpenStack Identity Credentials`` message when +you accessing and reaching an OpenStack service, it might be caused by +the changeover from UUID tokens to PKI tokens in the Grizzly release. + +The PKI-based token validation scheme relies on certificates from +Identity that are fetched through HTTP and stored in a local directory. +The location for this directory is specified by the ``signing_dir`` +configuration option. + +Solution +-------- + +In your services configuration file, look for a section like this: + +.. code-block:: ini + + [keystone_authtoken] + signing_dir = /var/cache/glance/api + auth_uri = http://controller:5000/v2.0 + identity_uri = http://controller:35357 + admin_tenant_name = service + admin_user = glance + +The first thing to check is that the ``signing_dir`` does, in fact, +exist. If it does, check for certificate files: + +.. code-block:: console + + $ ls -la /var/cache/glance/api/ + + total 24 + drwx------. 2 ayoung root 4096 Jul 22 10:58 . + drwxr-xr-x. 4 root root 4096 Nov 7 2012 .. + -rw-r-----. 1 ayoung ayoung 1424 Jul 22 10:58 cacert.pem + -rw-r-----. 1 ayoung ayoung 15 Jul 22 10:58 revoked.pem + -rw-r-----. 1 ayoung ayoung 4518 Jul 22 10:58 signing_cert.pem + +This directory contains two certificates and the token revocation list. +If these files are not present, your service cannot fetch them from +Identity. To troubleshoot, try to talk to Identity to make sure it +correctly serves files, as follows: + +.. code-block:: console + + $ curl http://localhost:35357/v2.0/certificates/signing + +This command fetches the signing certificate: + +.. code-block:: yaml + + Certificate: + Data: + Version: 3 (0x2) + Serial Number: 1 (0x1) + Signature Algorithm: sha1WithRSAEncryption + Issuer: C=US, ST=Unset, L=Unset, O=Unset, CN=www.example.com + Validity + Not Before: Jul 22 14:57:31 2013 GMT + Not After : Jul 20 14:57:31 2023 GMT + Subject: C=US, ST=Unset, O=Unset, CN=www.example.com + +Note the expiration dates of the certificate: + +.. code-block:: console + + Not Before: Jul 22 14:57:31 2013 GMT + Not After : Jul 20 14:57:31 2023 GMT + +The token revocation list is updated once a minute, but the certificates +are not. One possible problem is that the certificates are the wrong +files or garbage. You can remove these files and run another command +against your server; they are fetched on demand. + +The Identity service log should show the access of the certificate files. You +might have to turn up your logging levels. Set ``debug = True`` in your +Identity configuration file and restart the Identity server. + +.. code-block:: console + + (keystone.common.wsgi): 2013-07-24 12:18:11,461 DEBUG wsgi __call__ + arg_dict: {} + (access): 2013-07-24 12:18:11,462 INFO core __call__ 127.0.0.1 - - [24/Jul/2013:16:18:11 +0000] + "GET http://localhost:35357/v2.0/certificates/signing HTTP/1.0" 200 4518 + +If the files do not appear in your directory after this, it is likely +one of the following issues: + +* Your service is configured incorrectly and cannot talk to Identity. + Check the ``auth_port`` and ``auth_host`` values and make sure that + you can talk to that service through cURL, as shown previously. + +* Your signing directory is not writable. Use the ``chmod`` command to + change its permissions so that the service (POSIX) user can write to + it. Verify the change through ``su`` and ``touch`` commands. + +* The SELinux policy is denying access to the directory. + +SELinux troubles often occur when you use Fedora or RHEL-based packages and +you choose configuration options that do not match the standard policy. +Run the ``setenforce permissive`` command. If that makes a difference, +you should relabel the directory. If you are using a sub-directory of +the ``/var/cache/`` directory, run the following command: + +.. code-block:: console + + # restorecon /var/cache/ + +If you are not using a ``/var/cache`` sub-directory, you should. Modify +the ``signing_dir`` configuration option for your service and restart. + +Set back to ``setenforce enforcing`` to confirm that your changes solve +the problem. + +If your certificates are fetched on demand, the PKI validation is +working properly. Most likely, the token from Identity is not valid for +the operation you are attempting to perform, and your user needs a +different role for the operation. + +Debug signing key file errors +~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ + +Problem +------- + +If an error occurs when the signing key file opens, it is possible that +the person who ran the :command:`keystone-manage pki_setup` command to +generate certificates and keys did not use the correct user. + +Solution +-------- + +When you run the :command:`keystone-manage pki_setup` command, Identity +generates a set of certificates and keys in ``/etc/keystone/ssl*``, which +is owned by ``root:root``. This can present a problem when you run the +Identity daemon under the keystone user account (nologin) when you try +to run PKI. Unless you run the :command:`chown` command against the +files ``keystone:keystone``, or run the :command:`keystone-manage pki_setup` +command with the ``--keystone-user`` and +``--keystone-group`` parameters, you will get an error. +For example: + +.. code-block:: console + + 2012-07-31 11:10:53 ERROR [keystone.common.cms] Error opening signing key file + /etc/keystone/ssl/private/signing_key.pem + 140380567730016:error:0200100D:system library:fopen:Permission + denied:bss_file.c:398:fopen('/etc/keystone/ssl/private/signing_key.pem','r') + 140380567730016:error:20074002:BIO routines:FILE_CTRL:system lib:bss_file.c:400: + unable to load signing key file + +Flush expired tokens from the token database table +~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ + +Problem +------- + +As you generate tokens, the token database table on the Identity server +grows. + +Solution +-------- + +To clear the token table, an administrative user must run the +:command:`keystone-manage token_flush` command to flush the tokens. When you +flush tokens, expired tokens are deleted and traceability is eliminated. + +Use ``cron`` to schedule this command to run frequently based on your +workload. For large workloads, running it every minute is recommended. + diff --git a/doc/source/admin/identity-use-trusts.rst b/doc/source/admin/identity-use-trusts.rst new file mode 100644 index 0000000000..077e2e993c --- /dev/null +++ b/doc/source/admin/identity-use-trusts.rst @@ -0,0 +1,56 @@ +========== +Use trusts +========== + +OpenStack Identity manages authentication and authorization. A trust is +an OpenStack Identity extension that enables delegation and, optionally, +impersonation through ``keystone``. A trust extension defines a +relationship between: + +**Trustor** + The user delegating a limited set of their own rights to another user. + +**Trustee** + The user trust is being delegated to, for a limited time. + + The trust can eventually allow the trustee to impersonate the trustor. + For security reasons, some safeties are added. For example, if a trustor + loses a given role, any trusts the user issued with that role, and the + related tokens, are automatically revoked. + +The delegation parameters are: + +**User ID** + The user IDs for the trustor and trustee. + +**Privileges** + The delegated privileges are a combination of a project ID and a + number of roles that must be a subset of the roles assigned to the + trustor. + + If you omit all privileges, nothing is delegated. You cannot + delegate everything. + +**Delegation depth** + Defines whether or not the delegation is recursive. If it is + recursive, defines the delegation chain length. + + Specify one of the following values: + + - ``0``. The delegate cannot delegate these permissions further. + + - ``1``. The delegate can delegate the permissions to any set of + delegates but the latter cannot delegate further. + + - ``inf``. The delegation is infinitely recursive. + +**Endpoints** + A list of endpoints associated with the delegation. + + This parameter further restricts the delegation to the specified + endpoints only. If you omit the endpoints, the delegation is + useless. A special value of ``all_endpoints`` allows the trust to be + used by all endpoints associated with the delegated project. + +**Duration** + (Optional) Comprised of the start time and end time for the trust. diff --git a/doc/source/index.rst b/doc/source/index.rst index 1147fbbc2a..75951f43c1 100644 --- a/doc/source/index.rst +++ b/doc/source/index.rst @@ -85,6 +85,14 @@ the keystone service. advanced-topics/index.rst sample_files/index.rst +Administrator Guides +~~~~~~~~~~~~~~~~~~~~ + +.. toctree:: + :maxdepth: 2 + + admin/identity-management.rst + API Documentation ~~~~~~~~~~~~~~~~~ An end user can find the specific API documentation here, `OpenStack's Identity API`_.