Giter Site home page Giter Site logo

keitaroinc / ckanext-saml2auth Goto Github PK

View Code? Open in Web Editor NEW
23.0 5.0 25.0 257 KB

CKAN extension to enable Single Sign-On (SSO) for CKAN data portals via SAML2 Authentication.

License: GNU Affero General Public License v3.0

Shell 1.65% Python 95.99% HTML 2.36%
ckan ckanext saml2 saml opendata

ckanext-saml2auth's Introduction

CI Coverage Gitter Pypi Python CKAN

ckanext-saml2auth

A CKAN extension to enable Single Sign-On (SSO) for CKAN data portals via SAML2 Authentication.

Requirements

This extension works with CKAN 2.9+.

Installation

To install ckanext-saml2auth:

  1. Install the required system packages:

    sudo apt install xmlsec1
    
  2. Activate your CKAN virtual environment, for example:

    . /usr/lib/ckan/default/bin/activate
    
  3. Install the required system packages to install the necessary python module dependencies:

    # rustc and cargo are neeeded to build cryptography if no binary wheel exists
    sudo apt install rustc cargo
    
  4. Install the ckanext-saml2auth Python package into your virtual environment:

    pip install ckanext-saml2auth
    
  5. Add saml2auth to the ckan.plugins setting in your CKAN config file (by default the config file is located at /etc/ckan/default/ckan.ini).

  6. Restart CKAN. For example if you've deployed CKAN with Apache on Ubuntu:

    sudo service apache2 reload
    

Config settings

Required:

# Specifies the metadata location type
# Options: local or remote
ckanext.saml2auth.idp_metadata.location = remote

# Path to a local file accessible on the server the service runs on
# Ignore this config if the idp metadata location is set to: remote
ckanext.saml2auth.idp_metadata.local_path = /opt/metadata/idp.xml

# A remote URL serving aggregate metadata
# Ignore this config if the idp metadata location is set to: local
ckanext.saml2auth.idp_metadata.remote_url = https://kalmar2.org/simplesaml/module.php/aggregator/?id=kalmarcentral2&set=saml2

# Path to a local file accessible on the server the service runs on
# Ignore this config if the idp metadata location is set to: local and metadata is public
ckanext.saml2auth.idp_metadata.remote_cert = /opt/metadata/kalmar2.cert

# Corresponding SAML user field for firstname
ckanext.saml2auth.user_firstname = firstname

# Corresponding SAML user field for lastname
ckanext.saml2auth.user_lastname = lastname

# Corresponding SAML user field for fullname
# (Optional: Can be used as an alternative to firstname + lastname)
ckanext.saml2auth.user_fullname = fullname

# Corresponding SAML user field for email
ckanext.saml2auth.user_email = email

Optional:

# URL route of the endpoint where the SAML assertion is sent, also known as Assertion Consumer Service (ACS).
# Default: /acs
ckanext.saml2auth.acs_endpoint = /sso/post

# Configuration setting that enables CKAN's internal register/login functionality as well
# Default: False
ckanext.saml2auth.enable_ckan_internal_login = True

# List of email addresses from users that should be created as sysadmins (system administrators)
# Note that this means that CKAN sysadmins will _only_ be managed based on this config option and will override existing user permissions in the CKAN database
# If not set then it is ignored and CKAN sysadmins are managed through normal means
# Default: <Not set>
ckanext.saml2auth.sysadmins_list = [email protected] [email protected] [email protected]

# Indicates that attributes that are not recognized (they are not configured in attribute-mapping),
# will not be discarded.
# Default: True
ckanext.saml2auth.allow_unknown_attributes = False

# A list of string values that will be used to set the <NameIDFormat> element of the metadata of an entity.
# Default: urn:oasis:names:tc:SAML:2.0:nameid-format:persistent
ckanext.saml2auth.sp.name_id_format = urn:oasis:names:tc:SAML:2.0:nameid-format:persistent urn:oasis:names:tc:SAML:2.0:nameid-format:transient

# A string value that will be used to set the Format attribute of the <NameIDPolicy> element of the metadata of an entity.
# Default: <Not set>
ckanext.saml2auth.sp.name_id_policy_format = urn:oasis:names:tc:SAML:2.0:nameid-format:persistent

# Entity ID (also know as Issuer)
# Define the entity ID. Default is urn:mace:umu.se:saml:ckan:sp
ckanext.saml2auth.entity_id = urn:gov:gsa:SAML:2.0.profiles:sp:sso:gsa:catalog-dev

# Signed responses and assertions
ckanext.saml2auth.want_response_signed = True
ckanext.saml2auth.want_assertions_signed = False
ckanext.saml2auth.want_assertions_or_response_signed = False

# Cert & key files
ckanext.saml2auth.key_file_path = /path/to/mykey.pem
ckanext.saml2auth.cert_file_path = /path/to/mycert.pem

# Attribute map directory
ckanext.saml2auth.attribute_map_dir = /path/to/dir/attributemaps

# Authentication context request before redirect to login
# e.g. to ask for a PIV card with login.gov provider (https://developers.login.gov/oidc/#aal-values) use:
ckanext.saml2auth.requested_authn_context = http://idmanagement.gov/ns/assurance/aal/3?hspd12=true
# You can use multiple context separated by spaces
ckanext.saml2auth.requested_authn_context = req1 req2

# Define the comparison value for RequestedAuthnContext
# Comparison could be one of this: exact, minimum, maximum or better
ckanext.saml2auth.requested_authn_context_comparison = exact

# Indicates if this entity will sign the Logout Requests originated from it
ckanext.saml2auth.logout_requests_signed = False

# Saml logout request preferred binding settings variable
# Default: urn:oasis:names:tc:SAML:2.0:bindings:HTTP-POST
ckanext.saml2auth.logout_expected_binding =  urn:oasis:names:tc:SAML:2.0:bindings:HTTP-POST

# Default fallback endpoint to redirect to if no RelayState provided in the SAML Response
# Default: user.me (ie /dashboard)
# e.g. to redirect to the home page
ckanext.saml2auth.default_fallback_endpoint = home.index

Plugin interface

This extension provides the [ISaml2Auth]{.title-ref} interface that allows other plugins to hook into the Saml2 authorization flow. This allows plugins to integrate custom logic like:

  • Include additional attributes returned via the IdP as [plugin_extras]{.title-ref} in the CKAN users
  • Assign users to specific organizations with specific roles based on Saml2 attributes
  • Customize the flow response, to eg issue redirects or include custom headers.

For a list of available methods and their parameters check the ckanext/saml2auth/interfaces.py file, and for a basic example see the ExampleISaml2AuthPlugin class.

Developer installation

To install ckanext-saml2auth for development, activate your CKAN virtualenv and do:

sudo apt install xmlsec1
git clone https://github.com/duskobogdanovski/ckanext-saml2auth.git
cd ckanext-saml2auth
python setup.py develop
pip install -r dev-requirements.txt

Tests

To run the tests, do:

pytest --ckan-ini=test.ini

To run the tests and produce a coverage report, first make sure you have pytest-cov installed in your virtualenv (pip install pytest-cov) then run:

pytest --ckan-ini=test.ini  --cov=ckanext.saml2auth

Releasing a new version of ckanext-saml2auth

ckanext-saml2auth should be available on PyPI as https://pypi.org/project/ckanext-saml2auth. To publish a new version to PyPI follow these steps:

  1. Update the version number in the setup.py file. See PEP 440 for how to choose version numbers.

  2. Make sure you have the latest version of necessary packages:

    pip install --upgrade setuptools wheel twine
    
  3. Create a source and binary distributions of the new version:

    python setup.py sdist bdist_wheel && twine check dist/*
    

    Fix any errors you get.

  4. Upload the source distribution to PyPI:

    twine upload dist/*
    
  5. Commit any outstanding changes:

    git commit -a
    git push
    
  6. Tag the new release of the project on GitHub with the version number from the setup.py file. For example if the version number in setup.py is 0.0.1 then do:

    git tag 0.0.1
    git push --tags
    

ckanext-saml2auth's People

Contributors

amercader avatar avdata99 avatar blazhovsky avatar duskobogdanovski avatar elenakusevska avatar gregoxx avatar jin-sun-tts avatar mbocevski avatar nickumia-reisys avatar pdelboca avatar robert-bryson avatar

Stargazers

 avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar

Watchers

 avatar  avatar  avatar  avatar  avatar

ckanext-saml2auth's Issues

[BUG]Infinite Loop when logout of CKAN

We are having an issue after we have upgraded our CKAN from 2.9.5 to 2.9.8 and saml2auth from 1.2.2 to 1.2.3/1.3.0.

Upon clicking Logout from a SSO login, it will send a request to the client SSO page and redirect to /slo once done. However, it keeps looping back to the client SSO page when redirected back to /slo which redirect to user/_logout

Looking at the cookies, it seems like there are 2 cookeis for auth_tkt and it only clear one of them which keeps gettting in the loop.

We tried to add one code within _perform_slo(): after subject_id = get_subject_id(session) to ensure that the subject_id is none and it got out of the loop.

session.clear()

Can you please advise if this is a bug or this should be handle by CKAN core but somehow was called properly when logging out via SSO?

Thanks

[BUG] Ckan cookie is not accessible for more replicas

Describe the bug
I have set 2 ckan replicas and when refreshing ckan home page sometimes i'm logged from my profile.

ckanext-saml2auth version affected
v1.3.0

Expected behaviour
I should not have logged from my profile when refreshing page.

[BUG] Cannot post to default location

Describe the bug
Once the extension was installed and the configuration was performed within ckan.ini. The user cannot login via SSO. Receive and Internal error after the saml query. Looking at the web browser diagnostic options, the folder /acs is not available Error 500.

ckanext-saml2auth version affected
v1.1.0

Expected behaviour
The post occurs and the correct info is pulled into the require parameters to create the user if that user is not present or login.
Where should this directory be created within the system? Are there any other options that are required in the ckan.ini file? This is installed on Ubuntu 22.04

[BUG] Keycloak SAML2 Issue

Describe the bug
I have integrated ckan into our keycloak using SAML2. But the login session seems different with the other clients (in the same realm).
When I logged in in the portal web apps (using Oauth2 Keycloak, same realm, different client), the ckan is not logged in.
It also the same issue with the logout.

ckanext-saml2auth version affected
v1.2.2

SP Metadata

Hello, I don't know how to get the sp-metadata. do i need to create it by manually?

Can't install saml2auth in ckan-docker

I am trying to install saml2auth in my ckan docker 2.10 instance. I am quite new to the docker world, so I don't know if I am doing it correctly. I usually entered the bash console in the running container by using the command docker exec -it ckan /bin/bash. Then I installed the required packages with pip. However, for saml2auth I need to use apt for xmlsec1. When I try to execute the command 'apt install xmlsec1' it tells me bash: apt: command not found. What is the correct way to install this extension in ckan docker?

PyPi package not published

Documentation has this plugin published to PyPi for pip install. Right now we are installing via a tag using pips VCS egg install:

pip install -e "git+https://github.com/keitaroinc/[email protected]#egg=ckanext-saml2auth"

I know this is plugin is relatively new and documentation may not be updated.

[BUG] SLO not working correctly, cookies not removed

Describe the bug
Upon logging the user out (either via IDP-initiated logout or via SP-initiated Logout) the session remains, although the IdP reports a clear logout.

The Binding used for logout is 'urn:oasis:names:tc:SAML:2.0:bindings:HTTP-Redirect'

This appears to be related to #55 , #56 and #58, because the auth_tkt and ckan cookies do not get deleted.

The behaviour was tested in firefox (100.0.2) and chromium (91.0.4472.27) browsers.

ckanext-saml2auth version affected
v1.2.2

Expected behaviour
User is logged out and the auth_tkt and ckan cookies get deleted

Further info
The following hack 'solves' the problem:


diff --git a/ckanext/saml2auth/plugin.py b/ckanext/saml2auth/plugin.py
index 83f703b..c153f37 100644
--- a/ckanext/saml2auth/plugin.py
+++ b/ckanext/saml2auth/plugin.py
@@ -103,7 +103,7 @@ class Saml2AuthPlugin(plugins.SingletonPlugin):
             domain = h.get_site_domain_for_cookie()
 
             # Clear auth cookie in the browser
-            response.set_cookie('auth_tkt', domain=domain, expires=0)
+            response.set_cookie('auth_tkt', expires=0)
 
             # Clear session cookie in the browser
             response.set_cookie('ckan', domain=domain, expires=0)

This can in my opinion not be seen as a solution, because it indiscriminantly removes all auth_tkt cookies, so I would appreciate, if someone with more in-depth knowledge looks into a real solution.

Stop revoking privileges

If you manually promote a user as sysadmin this extension will revoke these privileges in the next login

User's email must be explicitly defined in the ckanext.saml2auth.sysadmins_list list
This may not be intuitive and could be interpreted as a bug.

Proposed solution

If ckanext.saml2auth.sysadmins_list is empty or not defined then we don't change any privileges at login time.

Help: Azure AD config. AudienceRestrictions conditions not satisfied!

I'm testing an Azure AD setup using my AAD sandbox.

On login I see this error message in ckan page /acs
Bad login request: AudienceRestrictions conditions not satisfied! (Local entity_id=612c702a-1a00-492f-a30c-3728a8b56c00)

AAD logs show that I passed authentication.

AAD provides properties for: Name, Application ID and Object ID.
Web redirect URL is set to : http://localhost:5100/acs

CKAN config has:
ckanext.saml2auth.idp_metadata.remote_url = https://login.microsoftonline.com/{my_tenant_id}/federationmetadata/2007-06/federationmetadata.xml

ckanext.saml2auth.entity_id={ad_application_id}

I can't work out whether I need to set another config value in the ckan config or in the AAD config to avoid this AudienceRestrictions not satisfied. This check is being performed after receiving the token back from the IDP.

Logfile shows the same error
2023-09-15 12:48:15,084 ERROR [saml2.client_base] XML parse error: AudienceRestrictions conditions not satisfied! (Local entity_id=612c702a-1a00-492f-a30c-3728a8b56c00)

I'm slightly confused because the example values for ckanext.saml2auth.entity_id are URNs rather than this GUID.

Service Provider specified Requested Authentication Context

In order to specify additional requirements to the Idp for the authentication context, Data.gov would like a way to customize the SAML2 RequestedAuthnContext, either through configuration or plugin extension .

Background

In order to require a higher level of authentication assurance, we need to be able to specify additional elements for the RequestedAuthnContext.

AFAICT, pySAML2 doesn't provide this through configuration, it has to be done through code on a per-login basis. I believe it would be implemented with additional parameters to the client.prepare_for_authenticate(). I haven't tested this:

def saml2login():
    client = h.saml_client(sp_config())
    requested_authn_context = None
    if config.get('saml2auth.requested_authn_context'):
        requested_authn_context = samlp.RequestedAuthnContext()
        prepare_kwargs['requested_authn_context'] = requested_authn_context
        for item in config.get('saml2auth.requested_authn_context', []):
            context_class_ref = saml.AuthnContextClassRef()
            context_class_ref.text = item
        requested_authn_context.authn_context_class_ref.append(context_class_ref)

    reqid, info = client.prepare_to_authenticate(requested_authn_context=requested_authn_context)
    # ...

I think this would be a good candidate for an ISaml2Auth interface since I imagine the Service Provider might want to modify the request directly instead of having to work with strings in the CKAN config.

[BUG ]logging out with version 1.2.0 logs out of IDP but not CKAN

Describe the bug
After upgrading to version 1.2.0 of this plugin, the new SLO behaviour added in #51 logs me out of a Microsoft account using SAML2, but after the "logout" if I navigate back to the CKAN site I'm still logged in. This is because the CKAN cookies are not being expired/deleted before redirecting to the external provider to logout.
I am using ckanext.saml2auth.logout_expected_binding="urn:oasis:names:tc:SAML:2.0:bindings:HTTP-Redirect".

ckanext-saml2auth version affected
v1.2.0

Expected behaviour
Logging out logs me out of CKAN itself and the external identity provider.
I guess roughly speaking the solution to this should be that the /slo endpoint should expire/delete the CKAN cookie before calling toolkit.redirect_to(u'user.logout') but I'm not exactly sure how to achieve this. Under older CKAN versions the pylons response object was exposed on the plugin toolkit, so it would have been possible to call toolkit.response.delete_cookie() in slo() but in CKAN >=2.9 the flask response object is not exposed on the toolkit, making this trickier to achieve.

[BUG] ckanext-saml2auth with Keycloak - How define client id (issuer / entity)

Hi,
I installed the ckanext-saml2auth module under CKAN 2.9 in order to interface with Keycloak. I can't find a way to specify the id of the client on which the request should be sent.

When I use the connection button via CKAN, I am directed to Keycloak but the latter receives the following message:

2021-10-25 16:05:10,095 WARN [org.keycloak.events] (default task-218) type=LOGIN_ERROR, realmId=MYREALM, clientId=null, userId=null, ipAddress=myaddress.com, error=client_not_found, reason=Cannot_match_source_hash

I'm trying to use ckanext.saml2auth.entity_id but it seems not working for me.

[BUG] saml2.SAMLError: URL not specified.

I am using ckan docker 2.10. When I click on "Login" I get the error: saml2.SAMLError: URL not specified. After installing saml2auth I pasted these settings from the readme into my ckan.ini:

# Specifies the metadata location type
# Options: local or remote
ckanext.saml2auth.idp_metadata.location = remote

# Path to a local file accessible on the server the service runs on
# Ignore this config if the idp metadata location is set to: remote
ckanext.saml2auth.idp_metadata.local_path = /opt/metadata/idp.xml

# A remote URL serving aggregate metadata
# Ignore this config if the idp metadata location is set to: local
ckanext.saml2auth.idp_metadata.remote_url = https://kalmar2.org/simplesaml/module.php/aggregator/?id=kalmarcentral2&set=saml2

# Path to a local file accessible on the server the service runs on
# Ignore this config if the idp metadata location is set to: local and metadata is public
ckanext.saml2auth.idp_metadata.remote_cert = /opt/metadata/kalmar2.cert

# Corresponding SAML user field for firstname
ckanext.saml2auth.user_firstname = firstname

# Corresponding SAML user field for lastname
ckanext.saml2auth.user_lastname = lastname

# Corresponding SAML user field for fullname
# (Optional: Can be used as an alternative to firstname + lastname)
ckanext.saml2auth.user_fullname = fullname

# Corresponding SAML user field for email
ckanext.saml2auth.user_email = email

I don't know much about SSO stuff, thats why I am asking if I can just copy these settings as they are or do I need to adjust the values? I am developing this ckan instance for someone else and just want them to be able to use saml2auth with their organizations SSO, so I don't configure the SSO settings but they do when they receive the ckan instance from me. Thanks in advance for your help!

Ability to Customize 403 After Unauthorized Redirect

We have implemented saml2auth in catalog.data.gov and have discovered a behavior we think should be customizable. When saml2auth is enabled and a user is logged out of CKAN, when they go to an unauthorized url they are redirected to this method with a 403 error. Since we are trying to replace the /user/login everywhere else with /user/saml2login this seems like bug or should be optional. We would like the ability to redirect to the /user/saml2login instead. If we suggest an upstream change would it be preferred to override the existing behavior or add additional behavior to customize this?

Send logout request to IdP

Is your feature request related to a problem? Please describe.
After a user logs out but leaves the browser tab open, clicking the login button will log the user back in without asking for credentials.

Describe the solution you'd like
After a local logout or session time out, direct browser to the IdP logout URL with a SAMLRequest. IdP will kill its session and redirect back with a POST request to SP's registered Assertion Consumer Service Logout URL.

Additional context
This is not necessarily a SLO request.

saml2.mdstore.SourceNotFound[BUG]

Describe the bug
I am trying to use the "SAML2 Authentication" extension in my CKAN 2.9.7 version. It is giving me some error, while this url work perfectly

File "/usr/lib/ckan/venv/lib/python3.8/site-packages/saml2/mdstore.py", line 873, in load

raise SourceNotFound(self.url)

saml2.mdstore.SourceNotFound: https://dev-33rd3qjmd1757pd7.us.auth0.com/samlp/NMnoJCAIzfeARNrECDxYLRPbkguPnDI3
I am using Auth0 (https://auth0.com/) for sso. "SAML2 Web APP" part of their free service application addon.
ckanext-saml2auth version affected
v1.1.0

Expected behaviour
It should open SSO (Auth0) login page.

Logs
If applicable, add logs to help explain your problem.

Please find my configuration in production.ini file:

[app:main]

use = egg:ckan

Required param for SAML 2 extension SSO login

Specifies the metadata location type

Options: local or remote

ckanext.saml2auth.idp_metadata.location = remote

Path to a local file accessible on the server the service runs on

Ignore this config if the idp metadata location is set to: remote

####ckanext.saml2auth.idp_metadata.local_path = /opt/metadata/idp.xml

ckanext.saml2auth.idp_metadata.local_path = /opt/metadata/dev-33rd3qjmd1757pd7_us_auth0_com-metadata.xml

A remote URL serving aggregate metadata

Ignore this config if the idp metadata location is set to: local

ckanext.saml2auth.idp_metadata.remote_url = https://kalmar2.org/simplesaml[...]

ckanext.saml2auth.idp_metadata.remote_url = https://dev-33rd3qjmd1757pd7.us.auth0.com/samlp/NMnoJCAIzfeARNrECDxYLRPbkguPnDI3

Path to a local file accessible on the server the service runs on

Ignore this config if the idp metadata location is set

to local and metadata is public

ckanext.saml2auth.idp_metadata.remote_cert = /opt/metadata/dev-33rd3qjmd1757pd7.crt

Corresponding SAML user field for firstname

ckanext.saml2auth.user_firstname = firstname

Corresponding SAML user field for lastname

ckanext.saml2auth.user_lastname = lastname

Corresponding SAML user field for fullname

(Optional: Can be used as an alternative to firstname + lastname)

ckanext.saml2auth.user_fullname = fullname

Corresponding SAML user field for email

ckanext.saml2auth.user_email = email

###----- In bottom/last of the file ------

Optional Param for SAML2

URL route of the endpoint where the SAML assertion is sent, also known as Assertion Consumer Service (ACS).

Default: /acs

ckanext.saml2auth.acs_endpoint = /sso/post

####ckanext.saml2auth.acs_endpoint = https://explore.tad3.org

####### Configuration setting that enables CKAN's internal register/login functionality as well

Default: False

ckanext.saml2auth.enable_ckan_internal_login = True

List of email addresses from users that should be created as sysadmins (system administrators)

Note that this means that CKAN sysadmins will only be managed based on this config option and will override existing user permissions in the CKAN database

If not set then it is ignored and CKAN sysadmins are managed through normal means

Default:

ckanext.saml2auth.sysadmins_list = [email protected] [email protected] [email protected]

Indicates that attributes that are not recognized (they are not configured in attribute-mapping),

will not be discarded.

Default: True

ckanext.saml2auth.allow_unknown_attributes = False

A list of string values that will be used to set the element of the metadata of an entity.

Default: urn:oasis:names:tc:SAML:2.0:nameid-format:persistent

ckanext.saml2auth.sp.name_id_format = urn:oasis:names:tc:SAML:2.0:nameid-format:persistent urn:oasis:names:tc:SAML:2.0:nameid-format:transient

A string value that will be used to set the Format attribute of the element of the metadata of an entity.

Default:

ckanext.saml2auth.sp.name_id_policy_format = urn:oasis:names:tc:SAML:2.0:nameid-format:persistent

Entity ID (also know as Issuer)

Define the entity ID. Default is urn:mace:umu.se:saml:ckan:sp

ckanext.saml2auth.entity_id = urn:gov:gsa:SAML:2.0.profiles:sp:sso:gsa:catalog-dev

Signed responses and assertions

ckanext.saml2auth.want_response_signed = True

ckanext.saml2auth.want_assertions_signed = False

ckanext.saml2auth.want_assertions_or_response_signed = False

Cert & key files

####ckanext.saml2auth.key_file_path = /path/to/mykey.pem

####ckanext.saml2auth.cert_file_path = /path/to/mycert.pem

Attribute map directory

####ckanext.saml2auth.attribute_map_dir = /path/to/dir/attributemaps

Authentication context request before redirect to login

e.g. to ask for a PIV card with login.gov provider (https://developers.login.gov/oidc/#aal-values) use:

####ckanext.saml2auth.requested_authn_context = http://idmanagement.gov/ns/assurance/aal/3?hspd12=true

ckanext.saml2auth.requested_authn_context = https://dev-33rd3qjmd1757pd7.us.auth0.com/samlp/NMnoJCAIzfeARNrECDxYLRPbkguPnDI3

it would have something like value: urn:oasis:names:tc:SAML:2.0:ac:classes:unspecified

You can use multiple context separated by spaces

####ckanext.saml2auth.requested_authn_context = req1 req2

Define the comparison value for RequestedAuthnContext

Comparison could be one of this: exact, minimum, maximum or better

ckanext.saml2auth.requested_authn_context_comparison = exact

Indicates if this entity will sign the Logout Requests originated from it

ckanext.saml2auth.logout_requests_signed = False

Saml logout request preferred binding settings variable

Default: urn:oasis:names:tc:SAML:2.0:bindings:HTTP-POST

ckanext.saml2auth.logout_expected_binding = urn:oasis:names:tc:SAML:2.0:bindings:HTTP-POST

Default fallback endpoint to redirect to if no RelayState provided in the SAML Response

Default: user.me (ie /dashboard)

e.g. to redirect to the home page

####ckanext.saml2auth.default_fallback_endpoint = home.index

ckanext.saml2auth.default_fallback_endpoint = /dataset

[BUG] saml2auth doesn't see my ckanext.saml2auth.user_email config setting

Describe the bug
CKAN fails to start with ckanext-saml2auth plugin enabled. I see the following error in the error log when I try to start it up:
RuntimeError: ckanext.saml2auth.user_email is not configured. Please amend your .ini file.

I verified I have this samle2auth config line in my ckan.ini (in addition to others):
ckanext.saml2auth.user_email = NameID

If I comment out the saml2auth plugin, CKAN will start up normally when I restart.

I am fairly certain I am probably doing something wrong and this is not a bug but I can't figure out what. Any help is appreciated. ๐Ÿ™‚

ckanext-saml2auth version affected
ckanext-saml2auth: 1.2.2
CKAN: ckan-2.9.4

Expected behavior
CKAN to startup saml2auth enabled.

Logs
2021-10-19 16:28:08,657 INFO [ckan.config.environment] Loading templates from /usr/lib/ckan/default/src/ckan/ckan/templates
Traceback (most recent call last):
File "/etc/ckan/default/wsgi.py", line 20, in
application = make_app(config)
File "/usr/lib/ckan/default/src/ckan/ckan/config/middleware/init.py", line 56, in make_app
load_environment(conf)
File "/usr/lib/ckan/default/src/ckan/ckan/config/environment.py", line 123, in load_environment
p.load_all()
File "/usr/lib/ckan/default/src/ckan/ckan/plugins/core.py", line 165, in load_all
load(*plugins)
File "/usr/lib/ckan/default/src/ckan/ckan/plugins/core.py", line 193, in load
plugins_update()
File "/usr/lib/ckan/default/src/ckan/ckan/plugins/core.py", line 153, in plugins_update
environment.update_config()
File "/usr/lib/ckan/default/src/ckan/ckan/config/environment.py", line 309, in update_config
plugin.configure(config)
File "/usr/lib/ckan/default/lib/python3.8/site-packages/ckanext/saml2auth/plugin.py", line 68, in configure
raise RuntimeError(missing_config.format(option))
RuntimeError: ckanext.saml2auth.user_email is not configured. Please amend your .ini file.
unable to load app 0 (mountpoint='') (callable not found or import error)
*** no app loaded. going in full dynamic mode ***

First and Last Name vs Full name?

I noticed that there is a requirement to provide separate fields for First and Last Name on the SAML fields.

Is there a reason for this? It is not always the case that you will get these as part of a SAML payload, and a single field for the full name is more common in my experience. Besides CKAN itself only supports fullname on the User model, and the code seems to do 'fullname': '{0} {1}'.format(firstname, lastname) anyway.

Perhaps there could be support for a ckanext.saml2auth.user_fullname option that can be used instead of ckanext.saml2auth.user_firstname + ckanext.saml2auth.user_lastname?

Happy to submit a PR if that sounds good

[BUG] Two auth_tkt cookies created after login

Describe the bug
Using Azure AD for SSO with CKAN, two auth_tkt cookies are created after login. They are equal, but with different domain:

  • cookie1: test-data.mydomain.com
  • cookie2: .test-data.mydomain.com

When logging out, only cookie2 is deleted, leaving cookie1 to keep my session towards CKAN alive. If I try logout again, Azure says I am already logged out and cookie1 remains active.

ckanext-saml2auth version affected
v1.2.1

Expected behaviour
To be logged out of CKAN when I click "Log out"

[BUG] SAML request is not signed

Describe the bug
SAML request is not signed.
We already have these two configured:

ckanext.saml2auth.key_file_path
ckanext.saml2auth.cert_file_path

ckanext-saml2auth version affected
v1.1.0

Expected behaviour
Expected to see the Signature tag in the SAML request but it is missing:

image

[BUG] Auth Cookies Not Removed On Logout

Describe the bug
Upon logging out of my CKAN instance, the authentication cookies are not removed. This seems to be identical to #68. I tried the fix that they suggested by making this change in plugin.py:
from
response.set_cookie('auth_tkt', domain=domain, expires=0)
to
response.set_cookie('auth_tkt', expires=0)

Similar to #68, I also had to change the ckanext.saml2auth.logout_expected_binding to urn:oasis:names:tc:SAML:2.0:bindings:HTTP-Redirect as urn:oasis:names:tc:SAML:2.0:bindings:HTTP-POST was causing an Internal Server Error.

Here is all of my relevant ckanext-saml2 configurations from ckan.ini

# Specifies the metadata location type
# Options: local or remote
ckanext.saml2auth.idp_metadata.location = local

# Path to a local file accessible on the server the service runs on
# Ignore this config if the idp metadata location is set to: remote
ckanext.saml2auth.idp_metadata.local_path = /opt/metadata/some.xml

# Path to a local file accessible on the server the service runs on
# Ignore this config if the idp metadata location is set to: local and metadata is public
ckanext.saml2auth.idp_metadata.remote_cert = /opt/metadata/some.cert

# Corresponding SAML user field for firstname
ckanext.saml2auth.user_firstname = givenName

# Corresponding SAML user field for lastname
ckanext.saml2auth.user_lastname = surname

# Corresponding SAML user field for email
ckanext.saml2auth.user_email = emailAddress

# Entity ID (also know as Issuer)
# Define the entity ID. Default is urn:mace:umu.se:saml:ckan:sp
ckanext.saml2auth.entity_id = https://subdomain.domain.com/ckan/
ckanext.saml2auth.want_response_signed = False
ckanext.saml2auth.want_assertions_signed = True
ckanext.saml2auth.want_assertions_or_response_signed = True

# URL route of the endpoint where the SAML assertion is sent, also known as Assertion Consumer Service (ACS).
# Default: /acs
ckanext.saml2auth.acs_endpoint = /acs/

# Indicates if this entity will sign the Logout Requests originated from it
#ckanext.saml2auth.logout_requests_signed = True

# Saml logout request preferred binding settings variable
# Default: urn:oasis:names:tc:SAML:2.0:bindings:HTTP-POST
ckanext.saml2auth.logout_expected_binding =  urn:oasis:names:tc:SAML:2.0:bindings:HTTP-Redirect

ckanext-saml2auth version affected
v1.3.0

CKAN Core version
2.10.1

Expected behaviour
Upon clicking the logout button, the browser should redirect to the SLO page and remove the authentication cookie forcing the user to login again.

[BUG] Can't install xmlsec1 with ckan-docker (saml2.sigver.SigverError: Cannot find ['xmlsec1'])

I am using ckan-docker 2.10 and I want to install saml2auth. However, the ckan docker image is alpine based, therefore I can't use the command sudo apt install xmlsec1 as this will result in the error: bash: apt: command not found (because there is no apt in alpine. However I can use apk and pip. Is there some other way to install xmlsec1? I installed it with pip install xmlsec, however I am not sure if this is the same package? Because when I run ckan with saml2auth, it tells me saml2.sigver.SigverError: Cannot find ['xmlsec1']. Any ideas how to solve this issue?

[BUG] Assertions not in the request

Describe the bug
When activating either of:

ckanext.saml2auth.want_assertions_signed
ckanext.saml2auth.want_assertions_or_response_signed

The signature is not included in the request.

image

ckanext-saml2auth version affected
v1.1.1

Expected behaviour
Signature is expected to be applied to the request.

ValueError: Missing assertion /python3.8/site-packages/saml2/response.py line 745, in get_subject

Describe the bug
ValueError: Missing assertion

This is my saml response

<saml2p:Response
xmlns:saml2p="urn:oasis:names:tc:SAML:2.0:protocol" Destination="https://testckan.abraxasint.com/sso/post" ID="_4052f8d933b98e7ddd4a3b8115cc7c3c" IssueInstant="2021-12-23T11:15:29.375Z" Version="2.0">
<saml2:Issuer
xmlns:saml2="urn:oasis:names:tc:SAML:2.0:assertion">https://elkgluustage.abraxasint.com/idp/shibboleth
</saml2:Issuer>
<ds:Signature
xmlns:ds="http://www.w3.org/2000/09/xmldsig#">
ds:SignedInfo
<ds:CanonicalizationMethod Algorithm="http://www.w3.org/2001/10/xml-exc-c14n#"/>
<ds:SignatureMethod Algorithm="http://www.w3.org/2001/04/xmldsig-more#rsa-sha256"/>
<ds:Reference URI="#_4052f8d933b98e7ddd4a3b8115cc7c3c">
ds:Transforms
<ds:Transform Algorithm="http://www.w3.org/2000/09/xmldsig#enveloped-signature"/>
<ds:Transform Algorithm="http://www.w3.org/2001/10/xml-exc-c14n#"/>
</ds:Transforms>
<ds:DigestMethod Algorithm="http://www.w3.org/2001/04/xmlenc#sha256"/>
ds:DigestValueGUrF75jyGot6qNYY/X35ZwVgfdEgqgqXl3f+WzksDxg=</ds:DigestValue>
</ds:Reference>
</ds:SignedInfo>
ds:SignatureValueb/JV1FjOWQLbHCCvuohrS+QccYaC/qBnPBjRv/WEWacMkZc9paThqjAlKU0dJq4JPklGSdcZAiH0o+ecR78LMvT1VPzbGX0pcw2aHSiOmkezh6vCZgpsiUxMlvXSmFeOtqow6Y+SSCLFM5BhtZATFsnsIuEwRBeYhftdHJQSWUn1ZGVIkrObBMMKEqevdPTmK3h1k0RjqHwhQtTMZMBI1duL18wZI6bZEkjhJl5L0EEgRBgLL8L1B3FpFLOzRCQh6ybm2oei+a8xvLlMurU9+D+JjrYbfgCr+bFNfhN8Y6kny6xli2OhOd0iazd1kyjb7zwxb8M7tTl/o9o1EeQbOQ==</ds:SignatureValue>
ds:KeyInfo
ds:X509Data
ds:X509CertificateMIIDnzCCAocCFGegBIVhYiABIFrcgH1bu7voSQbWMA0GCSqGSIb3DQEBCwUAMIGLMQswCQYDVQQG
EwJDQTELMAkGA1UECAwCT04xEDAOBgNVBAcMB1Rvcm9udG8xDzANBgNVBAoMBkNDUkVFRTEkMCIG
A1UEAwwbZWxrZ2x1dXN0YWdlLmFicmF4YXNpbnQuY29tMSYwJAYJKoZIhvcNAQkBFhdhYWxsZXlu
ZUBhYnJheGFzaW50LmNvbTAeFw0yMTAzMTYxNTUxNDRaFw0yMjAzMTYxNTUxNDRaMIGLMQswCQYD
VQQGEwJDQTELMAkGA1UECAwCT04xEDAOBgNVBAcMB1Rvcm9udG8xDzANBgNVBAoMBkNDUkVFRTEk
MCIGA1UEAwwbZWxrZ2x1dXN0YWdlLmFicmF4YXNpbnQuY29tMSYwJAYJKoZIhvcNAQkBFhdhYWxs
ZXluZUBhYnJheGFzaW50LmNvbTCCASIwDQYJKoZIhvcNAQEBBQADggEPADCCAQoCggEBALG8uVKE
AZ9XZxj3vQ19LvRN/dZOmRP/+5H24X7xAd4PF1L3x9pMDP60iYoAgdRofetGVU5iDqpFupZQqy8z
mWfu0GP669g2c3IWCAFU9YTmDHajb3vGaxbhKN4vgkJMr25uQxAUrUgNPNPC12gREzwreTBqmIT0
odptEgRbGOu3vPKdTSQDbZLirpR6GJKnUFj/sapK/zblRiQB0oylemA1Rn9DXZf6mDKGQZ94haUR
Cjlp1SxNOi9UT084cQPa0FyKw79zqUWZbmUPlkp7hbU5wN2+8Ut9NfArrQntdxWa9KjGPnaS0rMZ
OT0k8CfHiSJYxpEQI194dlw6mnwpqF0CAwEAATANBgkqhkiG9w0BAQsFAAOCAQEAF/s+7B2lhHh2
ANq/O9UpNnTh2qt/5ePernJebycHSgJrbzSQ4TqrUReepmqfjBiuMfSrbXju58dQSW5AAW+VIEWW
fGTsTFGmZTRLfI3fbrKhQKkTqYuhDfm4G9kgyJoIK9jBAi4JYKtIiplWPulzYkcyA/re7UDdZU8D
mtzTSYhFeILv8UDPDqIAehxFK25/Eg5DVRTSrexRnwjGj2AS402foOX7W1igky841JvCNZBLSVwj
Aq5OKnAZgqnmQ5NGRFlhnBMiNRt2HZ27TTC4RrqEnjO1UX5Fgg6LT5IvLRoRoid0DYbkFmP6dvWd
Q4GqYFpuoiE6j5STew5k2ZiJUQ==</ds:X509Certificate>
</ds:X509Data>
</ds:KeyInfo>
</ds:Signature>
saml2p:Status
<saml2p:StatusCode Value="urn:oasis:names:tc:SAML:2.0:status:Success"/>
</saml2p:Status>
<saml2:Assertion
xmlns:saml2="urn:oasis:names:tc:SAML:2.0:assertion" ID="_c9fa2a523188bba70d26581678fdfc39" IssueInstant="2021-12-23T11:15:29.375Z" Version="2.0">
saml2:Issuerhttps://elkgluustage.abraxasint.com/idp/shibboleth</saml2:Issuer>
<ds:Signature
xmlns:ds="http://www.w3.org/2000/09/xmldsig#">
ds:SignedInfo
<ds:CanonicalizationMethod Algorithm="http://www.w3.org/2001/10/xml-exc-c14n#"/>
<ds:SignatureMethod Algorithm="http://www.w3.org/2001/04/xmldsig-more#rsa-sha256"/>
<ds:Reference URI="#_c9fa2a523188bba70d26581678fdfc39">
ds:Transforms
<ds:Transform Algorithm="http://www.w3.org/2000/09/xmldsig#enveloped-signature"/>
<ds:Transform Algorithm="http://www.w3.org/2001/10/xml-exc-c14n#"/>
</ds:Transforms>
<ds:DigestMethod Algorithm="http://www.w3.org/2001/04/xmlenc#sha256"/>
ds:DigestValueaDaP5VkPGcBjsGlcVVzjjSWAYv9wx/d9Uy5VkB/6O98=</ds:DigestValue>
</ds:Reference>
</ds:SignedInfo>
ds:SignatureValueo1CDFLwfYoEJT5os5bHOMrX2grtIEsFjBOWlIY5ou+Ksqi8wxbJjDgMzbf0AhXOpVbfBC6BX6vILc3hYD5IKE8nSkSTCjH/3Z4WYFpbSBMuifoLcDHr6bXiFQ0Vq1uz3zPaf1pKFv/qQKJY8kWYoFv70zI4arU92cyiVNR5IbWU9SSU6zBQOsGIqg1WgvVeJFbST2I4d09PqjA3qMhdh0/AOW2gm1Z5CEwKk+VsSusdEW8i2rAGCd5++Xx2HqaXORHJIKx7fGeSr+4EIM/YlHpqTMkUUEW9PyjfktbO8DGTMZ0F59Qp1+fAs713XPoU7zZLztBdM8HbNBUATnMB3TA==</ds:SignatureValue>
ds:KeyInfo
ds:X509Data
ds:X509CertificateMIIDnzCCAocCFGegBIVhYiABIFrcgH1bu7voSQbWMA0GCSqGSIb3DQEBCwUAMIGLMQswCQYDVQQG
EwJDQTELMAkGA1UECAwCT04xEDAOBgNVBAcMB1Rvcm9udG8xDzANBgNVBAoMBkNDUkVFRTEkMCIG
A1UEAwwbZWxrZ2x1dXN0YWdlLmFicmF4YXNpbnQuY29tMSYwJAYJKoZIhvcNAQkBFhdhYWxsZXlu
ZUBhYnJheGFzaW50LmNvbTAeFw0yMTAzMTYxNTUxNDRaFw0yMjAzMTYxNTUxNDRaMIGLMQswCQYD
VQQGEwJDQTELMAkGA1UECAwCT04xEDAOBgNVBAcMB1Rvcm9udG8xDzANBgNVBAoMBkNDUkVFRTEk
MCIGA1UEAwwbZWxrZ2x1dXN0YWdlLmFicmF4YXNpbnQuY29tMSYwJAYJKoZIhvcNAQkBFhdhYWxs
ZXluZUBhYnJheGFzaW50LmNvbTCCASIwDQYJKoZIhvcNAQEBBQADggEPADCCAQoCggEBALG8uVKE
AZ9XZxj3vQ19LvRN/dZOmRP/+5H24X7xAd4PF1L3x9pMDP60iYoAgdRofetGVU5iDqpFupZQqy8z
mWfu0GP669g2c3IWCAFU9YTmDHajb3vGaxbhKN4vgkJMr25uQxAUrUgNPNPC12gREzwreTBqmIT0
odptEgRbGOu3vPKdTSQDbZLirpR6GJKnUFj/sapK/zblRiQB0oylemA1Rn9DXZf6mDKGQZ94haUR
Cjlp1SxNOi9UT084cQPa0FyKw79zqUWZbmUPlkp7hbU5wN2+8Ut9NfArrQntdxWa9KjGPnaS0rMZ
OT0k8CfHiSJYxpEQI194dlw6mnwpqF0CAwEAATANBgkqhkiG9w0BAQsFAAOCAQEAF/s+7B2lhHh2
ANq/O9UpNnTh2qt/5ePernJebycHSgJrbzSQ4TqrUReepmqfjBiuMfSrbXju58dQSW5AAW+VIEWW
fGTsTFGmZTRLfI3fbrKhQKkTqYuhDfm4G9kgyJoIK9jBAi4JYKtIiplWPulzYkcyA/re7UDdZU8D
mtzTSYhFeILv8UDPDqIAehxFK25/Eg5DVRTSrexRnwjGj2AS402foOX7W1igky841JvCNZBLSVwj
Aq5OKnAZgqnmQ5NGRFlhnBMiNRt2HZ27TTC4RrqEnjO1UX5Fgg6LT5IvLRoRoid0DYbkFmP6dvWd
Q4GqYFpuoiE6j5STew5k2ZiJUQ==</ds:X509Certificate>
</ds:X509Data>
</ds:KeyInfo>
</ds:Signature>
saml2:Subject
<saml2:SubjectConfirmation Method="urn:oasis:names:tc:SAML:2.0:cm:bearer">
<saml2:SubjectConfirmationData Address="112.196.0.226" NotOnOrAfter="2021-12-23T11:20:29.382Z" Recipient="https://testckan.abraxasint.com/sso/post"/>
</saml2:SubjectConfirmation>
</saml2:Subject>
<saml2:Conditions NotBefore="2021-12-23T11:15:29.375Z" NotOnOrAfter="2021-12-23T11:20:29.435Z">
saml2:AudienceRestriction
saml2:Audiencehttp://testckan.abraxasint.com:8090/ckan_sp.xml</saml2:Audience>
</saml2:AudienceRestriction>
</saml2:Conditions>
<saml2:AuthnStatement AuthnInstant="2021-12-23T10:35:23.586Z" SessionIndex="_0ee9767f27b75ed90d4d0569f3dab79e">
<saml2:SubjectLocality Address="112.196.0.226"/>
saml2:AuthnContext
saml2:AuthnContextClassRefurn:oasis:names:tc:SAML:2.0:ac:classes:PasswordProtectedTransport</saml2:AuthnContextClassRef>
</saml2:AuthnContext>
</saml2:AuthnStatement>
saml2:AttributeStatement
<saml2:Attribute FriendlyName="sn" Name="urn:oid:2.5.4.4" NameFormat="urn:oasis:names:tc:SAML:2.0:attrname-format:uri">
saml2:AttributeValueLastName</saml2:AttributeValue>
</saml2:Attribute>
<saml2:Attribute FriendlyName="givenName" Name="urn:oid:2.5.4.42" NameFormat="urn:oasis:names:tc:SAML:2.0:attrname-format:uri">
saml2:AttributeValueFirstName</saml2:AttributeValue>
</saml2:Attribute>
<saml2:Attribute FriendlyName="mail" Name="urn:oid:0.9.2342.19200300.100.1.3" NameFormat="urn:oasis:names:tc:SAML:2.0:attrname-format:uri">
saml2:AttributeValue[email protected]</saml2:AttributeValue>
</saml2:Attribute>
</saml2:AttributeStatement>
</saml2:Assertion>
</saml2p:Response>

ckanext-saml2auth version affected
v1.1.0

Expected behaviour
A clear and concise description of what you expected to happen.

Logs
If applicable, add logs to help explain your problem.

[BUG] - With CKAN vulnerability upgrade 2.9.9, getting the error below

Describe the bug
With CKAN vulnerability, we are asked to upgrade to CKAN 2.9.9 and set session to use cookie.

https://docs.ckan.org/en/2.9/changelog.html

ckanext-saml2auth version affected
v1.3.0

Expected behaviour
Should be able to SSO in to CKAN

Logs

Getting the error below when trying to SSO after upgrade to CKAN 2.9.9 and change beaker.session to cookie.

Traceback (most recent call last):
File "/usr/lib/ckan/ckan-py3/src/ckan/ckan/config/middleware/flask_app.py", line 66, in call
return self.app(environ, start_response)
File "/usr/lib/ckan/ckan-py3/src/ckan/ckan/config/middleware/common_middleware.py", line 114, in call
return self.app(environ, start_response)
File "/usr/lib/ckan/ckan-py3/lib/python3.8/site-packages/repoze/who/middleware.py", line 86, in call
app_iter = app(environ, wrapper.wrap_start_response)
File "/usr/lib/ckan/ckan-py3/lib/python3.8/site-packages/fanstatic/publisher.py", line 224, in call
return self.app(environ, start_response)
File "/usr/lib/ckan/ckan-py3/lib/python3.8/site-packages/fanstatic/injector.py", line 64, in call
response = request.get_response(self.app)
File "/usr/lib/ckan/ckan-py3/lib/python3.8/site-packages/webob/request.py", line 1313, in send
status, headers, app_iter = self.call_application(
File "/usr/lib/ckan/ckan-py3/lib/python3.8/site-packages/webob/request.py", line 1278, in call_application
app_iter = application(self.environ, start_response)
File "/usr/lib/ckan/ckan-py3/lib/python3.8/site-packages/flask/app.py", line 2463, in call
return self.wsgi_app(environ, start_response)
File "/usr/lib/ckan/ckan-py3/lib/python3.8/site-packages/beaker/middleware.py", line 156, in call
return self.wrap_app(environ, session_start_response)
File "/usr/lib/ckan/ckan-py3/src/ckan/ckan/config/middleware/common_middleware.py", line 58, in call
return self.app(environ, start_response)
File "/usr/lib/ckan/ckan-py3/lib/python3.8/site-packages/flask/app.py", line 2453, in wsgi_app
return response(environ, start_response)
File "/usr/lib/ckan/ckan-py3/lib/python3.8/site-packages/werkzeug/wrappers/base_response.py", line 699, in call
start_response(status, headers)
File "/usr/lib/ckan/ckan-py3/lib/python3.8/site-packages/beaker/middleware.py", line 150, in session_start_response
session.persist()
File "/usr/lib/ckan/ckan-py3/lib/python3.8/site-packages/beaker/session.py", line 875, in persist
self._session().save()
File "/usr/lib/ckan/ckan-py3/lib/python3.8/site-packages/beaker/session.py", line 723, in save
self._create_cookie()
File "/usr/lib/ckan/ckan-py3/lib/python3.8/site-packages/beaker/session.py", line 737, in _create_cookie
val = self._encrypt_data()
File "/usr/lib/ckan/ckan-py3/lib/python3.8/site-packages/beaker/session.py", line 381, in _encrypt_data
data = self.serializer.dumps(session_data)
File "/usr/lib/ckan/ckan-py3/lib/python3.8/site-packages/beaker/util.py", line 469, in dumps
return zlib.compress(json.dumps(data).encode('utf-8'))
File "/usr/lib/python3.8/json/init.py", line 231, in dumps
return _default_encoder.encode(obj)
File "/usr/lib/python3.8/json/encoder.py", line 199, in encode
chunks = self.iterencode(o, _one_shot=True)
File "/usr/lib/python3.8/json/encoder.py", line 257, in iterencode
return _iterencode(o, 0)
File "/usr/lib/python3.8/json/encoder.py", line 179, in default
raise TypeError(f'Object of type {o.class.name} '
TypeError: Object of type NameID is not JSON serializable

[BUG] things continue to work with wrong mycert.pem

Describe the bug
ckanext.saml2auth.cert_file_path = /path/to/mycert.pem

The content of mycert.pem does not matter, at least in our setup. The file still need to be present, the content still need to look like a certificate, but it will work with content like this.

-----BEGIN CERTIFICATE-----
placeholder
-----END CERTIFICATE-----

ckanext-saml2auth version affected
v1.1.0

Expected behaviour
Something missing in the README for this behaviour?

Extensibility

This extension is great and a big improvement from previous versions of ckanext-saml2. One thing I would like to know more about is your plans regarding extensibility for it.

By extensibility I mean supporting custom business logic around the SAML2 authentication for specific projects. Here are some examples (all real from projects I've worked on):

  • Custom SAML config. pysaml has lots of configuration options and sometimes you need to tweak some of them, and it would be nice to not have to add CKAN config options to cover all cases
  • Adding custom fields (plugin extras) to created/updated users based on SAML2 claims
  • Adding users to organizations with different roles based on SAML2 claims
  • Prevent users from editing their details in CKAN

One of the problems with the old extension is that it included code to deal with several features like these that were sepcific to one or a small number of projects, and many times involving layers of code not directly related with authentication (actions, authorization, etc). This all made the code base unnecessarily complex. I think the approach of keeping this plugin lean and focus on the core functionality is the right one.

At the same time, it's good that other plugins can extend the functionality to support custom logic. Traditionally this has been done in CKAN using interfaces that plugins can implement. Here's a quick stub of how this interface could look like:

class ISaml2Auth(Interface):

    def sp_config(self, sp_config):
        """"
        Gets the config object generated by get_config() allowing plugins to tweak it
        """
        pass

    def before_user_update(self, user_dict, saml_claims):
        """
        Gets the user data dict before updating a user alongside all the claims
        contained in the SAML2 token (currently in auth_response.ava)
        """
        pass

    def before_user_create(self, user_dict, saml_claims):
        """
        Gets the user data dict before creating a user alongside all the claims
        contained in the SAML2 token
        """
        pass

    def after_login(self, resp, saml_claims):
        """
        Called once the user has been logged in, just before returning the request, and passing
        the request object, so plugins can issue redirects if needed. At this point they can use
        g.user to get the logged in user
        """
        pass

As I said I didn't put much thought into the actual methods and params passed but hopefully they give an idea of what I'm suggesting. Of course I'm also open to other approaches if you think there are better ones.

Let me know your thoughts. I'd be happy to contribute support for the interface if this sounds like a good way forward.

Recommend Projects

  • React photo React

    A declarative, efficient, and flexible JavaScript library for building user interfaces.

  • Vue.js photo Vue.js

    ๐Ÿ–– Vue.js is a progressive, incrementally-adoptable JavaScript framework for building UI on the web.

  • Typescript photo Typescript

    TypeScript is a superset of JavaScript that compiles to clean JavaScript output.

  • TensorFlow photo TensorFlow

    An Open Source Machine Learning Framework for Everyone

  • Django photo Django

    The Web framework for perfectionists with deadlines.

  • D3 photo D3

    Bring data to life with SVG, Canvas and HTML. ๐Ÿ“Š๐Ÿ“ˆ๐ŸŽ‰

Recommend Topics

  • javascript

    JavaScript (JS) is a lightweight interpreted programming language with first-class functions.

  • web

    Some thing interesting about web. New door for the world.

  • server

    A server is a program made to process requests and deliver data to clients.

  • Machine learning

    Machine learning is a way of modeling and interpreting data that allows a piece of software to respond intelligently.

  • Game

    Some thing interesting about game, make everyone happy.

Recommend Org

  • Facebook photo Facebook

    We are working to build community through open source technology. NB: members must have two-factor auth.

  • Microsoft photo Microsoft

    Open source projects and samples from Microsoft.

  • Google photo Google

    Google โค๏ธ Open Source for everyone.

  • D3 photo D3

    Data-Driven Documents codes.