An error in function get_user_unique_id_and_display_name()

Bug #1711883 reported by Lei Lei
10
This bug affects 2 people
Affects Status Importance Assigned to Milestone
OpenStack Identity (keystone)
Fix Released
Medium
Vishakha Agarwal

Bug Description

Firstly, see the code of function get_user_unique_id_and_display_name() of keystone/auth/plugins/mapped.py

    # keystone/auth/plugins/mapped.py

    def get_user_unique_id_and_display_name(request, mapped_properties):

        user = mapped_properties['user']

        user_id = user.get('id')
        user_name = user.get('name') or request.remote_user

        if not any([user_id, user_name]):
            msg = _("Could not map user while setting ephemeral user identity. "
                    "Either mapping rules must specify user id/name or "
                    "REMOTE_USER environment variable must be set.")
            raise exception.Unauthorized(msg)

        elif not user_name:
            user['name'] = user_id

        elif not user_id:
            user_id = user_name

        user['id'] = parse.quote(user_id)
        return (user['id'], user['name'])

There is an error inside above function.
If user.get('name') is None, but request.remote_user is not None, e.g. request.remote_user is "fed_user", then user_name will be "fed_user".
So, the execution path will not go into "elif not user_name". So, for last line "return (user['id'], user['name'])", user['name'] will raise KeyError exception.

https://github.com/openstack/keystone/blob/682cfa5c6d135641797ec9e51299287e8191e858/keystone/auth/plugins/mapped.py#L324-L368

Tags: federation
Revision history for this message
Lance Bragstad (lbragstad) wrote :

Thanks for the bug report. Do you have inputs or steps to recreate this by interacting with keystone?

description: updated
Revision history for this message
Lei Lei (leilei) wrote :
Download full text (4.5 KiB)

Thanks for asking, Lance.
Yep. The steps are used to create SSO (Single Sign on) for using Google Account to login on OpenStack.
The steps seem not a few. They are as below.

[Environment] CentOS 7.3

1. Login on "Google Developers Console", and set up your own project, which is a "web application".
   Note:
   1> After the project is created successfully, write down the "client ID" and "client secret". They will be used later.
   2> Set "http://demo.sso.org:5000/v3/auth/OS-FEDERATION/websso/oidc/redirect" to "the authorized redirected URL"

2. Set up a PackStack.

3. Run the commands below in the PackStack:

   source ~/keystonerc_admin
   openstack group create --domain default --description "Federation User Group" federation_group
   openstack project create --domain default --description "Federation Demo Project" federation_demo_project
   openstack role add --domain default --group federation_group admin
   openstack role add --project federation_demo_project --group federation_group admin
   openstack identity provider create google --remote-id https://accounts.google.com

   cat > /tmp/google-mapping-rules.json <<EOF
[
    {
        "local": [
            {
                "group": {
                    "id": "xxx" # Note, this is the group id created by the second command above
                }
            }
        ],

        "remote": [
            {
                "type": "HTTP_OIDC_ISS",
                "any_one_of": [
                    "https://accounts.google.com"
                ]
            }
        ]
    }
]
EOF

   openstack mapping create google-idp-mapping --rules ./google-mapping-rules.json
   openstack federation protocol create oidc --identity-provider google --mapping google-idp-mapping

4. Append/Add the following to the proper section of /etc/keystone.conf

    [auth]
    # Allowed authentication methods. (list value)
    methods = external,password,token,oauth1,oidc
    oidc = keystone.auth.plugins.mapped.Mapped

    [federation]
    # Value to be used to obtain the entity ID of the Identity Provider from the
    # environment (e.g. if using the mod_shib plugin this value is `Shib-Identity-
    # Provider`). (string value)
    remote_id_attribute = HTTP_OIDC_ISS
    trusted_dashboard = http://demo.sso.org/dashboard/auth/websso/

5. Install mod_auth_openidc module for Apache
   Commands are like below:

    wget https://github.com/pingidentity/mod_auth_openidc/releases/download/v2.3.0/cjose-0.5.1-1.el7.centos.x86_64.rpm
    wget https://github.com/pingidentity/mod_auth_openidc/releases/download/v2.3.0/mod_auth_openidc-2.3.0-1.el7.centos.x86_64.rpm
    wget http://springdale.math.ias.edu/data/puias/unsupported/6/x86_64/hiredis-0.12.1-1.sdl6.x86_64.rpm

    yum localinstall -y ./cjose-0.5.1-1.el7.centos.x86_64.rpm
    yum localinstall -y ./hiredis-0.12.1-1.sdl6.x86_64.rpm
    yum localinstall -y ./mod_auth_openidc-2.3.0-1.el7.centos.x86_64.rpm

6. Add the following content to /etc/httpd/conf.d/10-keystone_wsgi_main.conf

    <VirtualHost *:5000>
        ...

        OIDCClaimPrefix "OIDC-"
        OIDCResponseType "id_token"
        OIDCScope "openid email profile"
       ...

Read more...

Revision history for this message
Lei Lei (leilei) wrote :

The reproduced steps are complex. However, just from the code itself, I think the error is not hard to be found. The point is, if "request.remote_user" is not None but user.get('name') is None, then the last statement "return (user['id'], user['name'])" will raise a KeyError.

Lei Lei (leilei)
summary: - A logic error in function get_user_unique_id_and_display_name()
+ An error in function get_user_unique_id_and_display_name()
jiapei (jeremy.jia)
Changed in keystone:
status: New → Confirmed
Lei Lei (leilei)
Changed in keystone:
assignee: nobody → Lei Lei (leilei)
Revision history for this message
OpenStack Infra (hudson-openstack) wrote : Fix proposed to keystone (master)

Fix proposed to branch: master
Review: https://review.openstack.org/499959

Changed in keystone:
importance: Undecided → Medium
Revision history for this message
Lance Bragstad (lbragstad) wrote :

Unassigning due to inactivity.

Changed in keystone:
assignee: Lei Lei (leilei) → nobody
Rajat Sharma (tajar29)
Changed in keystone:
assignee: nobody → Rajat Sharma (tajar29)
Changed in keystone:
assignee: Rajat Sharma (tajar29) → Vishakha Agarwal (vishakha.agarwal)
Revision history for this message
OpenStack Infra (hudson-openstack) wrote :

Fix proposed to branch: master
Review: https://review.openstack.org/576433

Changed in keystone:
status: Confirmed → In Progress
Revision history for this message
OpenStack Infra (hudson-openstack) wrote : Fix merged to keystone (master)

Reviewed: https://review.openstack.org/576433
Committed: https://git.openstack.org/cgit/openstack/keystone/commit/?id=f4729795ecfbc53ae391204726fd441ce4b462ef
Submitter: Zuul
Branch: master

commit f4729795ecfbc53ae391204726fd441ce4b462ef
Author: Vishakha Agarwal <email address hidden>
Date: Tue Jun 19 14:21:46 2018 +0530

    Added check to avoid keyerror "user['name']"

    In get_user_unique_id_and_display_name() of
    keystone/auth/plugins/mapped.py, the checking
    of user dict's key "name" is not very strict.
    So, we need to add more strict validation here.

    Change-Id: Ib147e90e4076c1c2ca7a9fd1cf8d17ce3ddc5e34
    Closes-Bug: #1711883

Changed in keystone:
status: In Progress → Fix Released
Revision history for this message
OpenStack Infra (hudson-openstack) wrote : Fix included in openstack/keystone 14.0.0.0rc1

This issue was fixed in the openstack/keystone 14.0.0.0rc1 release candidate.

Changed in keystone:
milestone: none → rocky-3
To post a comment you must log in.
This report contains Public information  
Everyone can see this information.

Other bug subscribers

Remote bug watches

Bug watches keep track of this bug in other bug trackers.