Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

[Request] Create a configuration that allows to have 2 LDAP instances connected with Shibboleth at the same time #5

Open
davitol opened this issue Mar 10, 2020 · 4 comments

Comments

@davitol
Copy link

davitol commented Mar 10, 2020

This scenario is needed for testing purpose

https://github.com/owncloud/enterprise/issues/3691

@davitol
Copy link
Author

davitol commented Mar 12, 2020

Posible hints for this deplyoment:

https://simplesamlphp.org/docs/stable/ldap:ldap

ldap:LDAPMulti
    Allow the user to chose one LDAP server to authenticate against.

@davitol
Copy link
Author

davitol commented Mar 20, 2020

Should authsources.php look like this for multildap aprameter? Any big issue seen? Feedback is welcome

// Example of an LDAPMulti authentication source.
    'ldapmulti' => array(
        'ldap:LDAPMulti',

        // Give the user an option to save their username for future login attempts
        // And when enabled, what should the default be, to save the username or not
        //'remember.username.enabled' => FALSE,
        //'remember.username.checked' => FALSE,

        // The way the organization as part of the username should be handled.
        // Three possible values:
        // - 'none':   No handling of the organization. Allows '@' to be part
        //             of the username.
        // - 'allow':  Will allow users to type 'username@organization'.
        // - 'force':  Force users to type 'username@organization'. The dropdown
        //             list will be hidden.
        //
        // The default is 'none'.
        'username_organization_method' => 'none',

        // Whether the organization should be included as part of the username
        // when authenticating. If this is set to TRUE, the username will be on
        // the form <username>@<organization identifier>. If this is FALSE, the
        // username will be used as the user enters it.
        //
        // The default is FALSE.
        'include_organization_in_username' => FALSE,

        // A list of available LDAP servers.
        //
        // The index is an identifier for the organization/group. When
        // 'username_organization_method' is set to something other than 'none',
        // the organization-part of the username is matched against the index.
        //
        // The value of each element is an array in the same format as an LDAP
        // authentication source.
        'employees' => array(
            // A short name/description for this group. Will be shown in a dropdown list
            // when the user logs on.
            //
            // This option can be a string or an array with language => text mappings.
        // The hostname of the LDAP server.

        // Whether SSL/TLS should be used when contacting the LDAP server.
        'enable_tls' => FALSE,

        // Whether debug output from the LDAP library should be enabled.
        // Default is FALSE.
        'debug' => FALSE,

        // The timeout for accessing the LDAP server, in seconds.
        // The default is 0, which means no timeout.
        'timeout' => 0,

        // Set whether to follow referrals. AD Controllers may require FALSE to function.
        'referrals' => TRUE,

        // Which attributes should be retrieved from the LDAP server.
        // This can be an array of attribute names, or NULL, in which case
        // all attributes are fetched.
        'attributes' => NULL,

        // The pattern which should be used to create the users DN given the username.
        // %username% in this pattern will be replaced with the users username.
        //
        // This option is not used if the search.enable option is set to TRUE.

        // As an alternative to specifying a pattern for the users DN, it is possible to
        // search for the username in a set of attributes. This is enabled by this option.
        'search.enable' => FALSE,

        // The DN which will be used as a base for the search.
        // This can be a single string, in which case only that DN is searched, or an
        // array of strings, in which case they will be searched in the order given.
        'search.base' => 'dc=owncloudqa,dc=com',

        // The attribute(s) the username should match against.
        //
        // This is an array with one or more attribute names. Any of the attributes in
        // the array may match the value the username.
        'search.attributes' => array('uid', 'mail'),

        // The username & password the simpleSAMLphp should bind to before searching. If
        // this is left as NULL, no bind will be performed before searching.
        'search.username' => 'admin',
        'search.password' => 'owncloud123',

        // If the directory uses privilege separation,
        // the authenticated user may not be able to retrieve
        // all required attribures, a privileged entity is required
        // to get them. This is enabled with this option.
        'priv.read' => FALSE,

        // The DN & password the simpleSAMLphp should bind to before
        // retrieving attributes. These options are required if
        // 'priv.read' is set to TRUE.
        'priv.username' => NULL,
        'priv.password' => NULL,
            'description' => 'Employees',

            // The rest of the options are the same as those available for
            // the LDAP authentication source.
            'hostname' => 'openldap1',
            'dnpattern' => 'uid=%username%,ou=people,dc=owncloudqa,dc=com',
        ),

        'students' => array(
            'description' => 'Students',
                    // The hostname of the LDAP server.

        // Whether SSL/TLS should be used when contacting the LDAP server.
        'enable_tls' => FALSE,

        // Whether debug output from the LDAP library should be enabled.
        // Default is FALSE.
        'debug' => FALSE,

        // The timeout for accessing the LDAP server, in seconds.
        // The default is 0, which means no timeout.
        'timeout' => 0,

        // Set whether to follow referrals. AD Controllers may require FALSE to function.
        'referrals' => TRUE,

        // Which attributes should be retrieved from the LDAP server.
        // This can be an array of attribute names, or NULL, in which case
        // all attributes are fetched.
        'attributes' => NULL,

        // The pattern which should be used to create the users DN given the username.
        // %username% in this pattern will be replaced with the users username.
        //

        // As an alternative to specifying a pattern for the users DN, it is possible to
        // search for the username in a set of attributes. This is enabled by this option.
        'search.enable' => FALSE,

        // The DN which will be used as a base for the search.
        // This can be a single string, in which case only that DN is searched, or an
        // array of strings, in which case they will be searched in the order given.
        'search.base' => 'dc=owncloudqa,dc=com',

        // The attribute(s) the username should match against.
        //
        // This is an array with one or more attribute names. Any of the attributes in
        // the array may match the value the username.
        'search.attributes' => array('uid', 'mail'),

        // The username & password the simpleSAMLphp should bind to before searching. If
        // this is left as NULL, no bind will be performed before searching.
        'search.username' => 'admin',
        'search.password' => 'owncloud123',

        // If the directory uses privilege separation,
        // the authenticated user may not be able to retrieve
        // all required attribures, a privileged entity is required
        // to get them. This is enabled with this option.
        'priv.read' => FALSE,

        // The DN & password the simpleSAMLphp should bind to before
        // retrieving attributes. These options are required if
        // 'priv.read' is set to TRUE.
        'priv.username' => NULL,
        'priv.password' => NULL,
            'hostname' => 'openldap2',
            'dnpattern' => 'uid=%username%,ou=people,dc=owncloudqa,dc=com',
        ),

    ),
    

);

@davitol
Copy link
Author

davitol commented Mar 20, 2020

Single .yml file launched for that purpose contains:

version: '3.4'

services:
  owncloud:
    image: owncloudci/base:${PHP_VERSION:-7.1}
    depends_on:
      - openldap1
      - openldap2
      - idp
    volumes:
      - ${OWNCLOUD_FOLDER:-./owncloud}:/var/www/owncloud
      - ${LDAP_AUTOCONFIG_FILE:-./ldap/ldap.sh}:/etc/pre_server.d/10-ldap.sh
      - ./idp/idp-shib-install.sh:/etc/pre_install.d/idp-shib-install.sh
      - ./idp/idp-start-shibd.sh:/etc/pre_server.d/idp-start-shibd.sh
      - ./idp/simplesaml-shibboleth2.xml:/etc/shibboleth/shibboleth2.xml
      - ./idp/idp-configure-sso.sh:/etc/pre_server.d/idp-configure.sh
      - ./idp/apache-aliases.conf:/root/owncloud/toppath.conf
    environment:
      - OWNCLOUD_DOMAIN
      - OWNCLOUD_ADMIN_USERNAME
      - OWNCLOUD_ADMIN_PASSWORD
      - OWNCLOUD_CROND_ENABLED
      - OWNCLOUD_APPS_ENABLE
      - OWNCLOUD_LICENSE_KEY=XXX
      - OWNCLOUD_MARKETPLACE_APIKEY=XXX
      - OWNCLOUD_APPS_INSTALL=enterprise_key,user_ldap,user_shibboleth
    ports:
      - ${OWNCLOUD_HTTP_PORT:-19680}:80

  openldap1:
    image: osixia/openldap:1.1.10
    environment:
      LDAP_LOG_LEVEL: "256"
      LDAP_ORGANISATION: "ownCloud Inc."
      LDAP_DOMAIN: "owncloudqa.com"
      LDAP_BASE_DN: "dc=owncloudqa,dc=com"
      LDAP_ADMIN_PASSWORD: "owncloud123"
      LDAP_CONFIG_PASSWORD: "config"
      LDAP_READONLY_USER: "false"
      #LDAP_READONLY_USER_USERNAME: "readonly"
      #LDAP_READONLY_USER_PASSWORD: "readonly"
      LDAP_RFC2307BIS_SCHEMA: "false"
      LDAP_BACKEND: "hdb"
      LDAP_TLS: "true"
      LDAP_TLS_CRT_FILENAME: "ldap.crt"
      LDAP_TLS_KEY_FILENAME: "ldap.key"
      LDAP_TLS_CA_CRT_FILENAME: "ca.crt"
      LDAP_TLS_ENFORCE: "false"
      LDAP_TLS_CIPHER_SUITE: "SECURE256:-VERS-SSL3.0"
      LDAP_TLS_PROTOCOL_MIN: "3.1"
      LDAP_TLS_VERIFY_CLIENT: "demand"
      LDAP_REPLICATION: "false"
      #LDAP_REPLICATION_CONFIG_SYNCPROV: "binddn="cn=admin,cn=config" bindmethod=simple credentials=$LDAP_CONFIG_PASSWORD searchbase="cn=config" type=refreshAndPersist retry="60 +" timeout=1 starttls=critical"
      #LDAP_REPLICATION_DB_SYNCPROV: "binddn="cn=admin,$LDAP_BASE_DN" bindmethod=simple credentials=$LDAP_ADMIN_PASSWORD searchbase="$LDAP_BASE_DN" type=refreshAndPersist interval=00:00:00:10 retry="60 +" timeout=1 starttls=critical"
      #LDAP_REPLICATION_HOSTS: "#PYTHON2BASH:['ldap://ldap.example.org','ldap://ldap2.example.org']"
      KEEP_EXISTING_CONFIG: "false"
      LDAP_REMOVE_CONFIG_AFTER_SETUP: "true"
      LDAP_SSL_HELPER_PREFIX: "ldap"
    command: "--copy-service"
    volumes:
      - ${LDIF_FILE:-./ldap/openldap-ldif/base.ldif}:/container/service/slapd/assets/config/bootstrap/ldif/custom/10-base.ldif


  openldap2:
    image: osixia/openldap:1.1.10
    environment:
      LDAP_LOG_LEVEL: "256"
      LDAP_ORGANISATION: "ownCloud Inc."
      LDAP_DOMAIN: "owncloudqa.com"
      LDAP_BASE_DN: "dc=owncloudqa,dc=com"
      LDAP_ADMIN_PASSWORD: "owncloud123"
      LDAP_CONFIG_PASSWORD: "config"
      LDAP_READONLY_USER: "false"
      #LDAP_READONLY_USER_USERNAME: "readonly"
      #LDAP_READONLY_USER_PASSWORD: "readonly"
      LDAP_RFC2307BIS_SCHEMA: "false"
      LDAP_BACKEND: "hdb"
      LDAP_TLS: "true"
      LDAP_TLS_CRT_FILENAME: "ldap.crt"
      LDAP_TLS_KEY_FILENAME: "ldap.key"
      LDAP_TLS_CA_CRT_FILENAME: "ca.crt"
      LDAP_TLS_ENFORCE: "false"
      LDAP_TLS_CIPHER_SUITE: "SECURE256:-VERS-SSL3.0"
      LDAP_TLS_PROTOCOL_MIN: "3.1"
      LDAP_TLS_VERIFY_CLIENT: "demand"
      LDAP_REPLICATION: "false"
      #LDAP_REPLICATION_CONFIG_SYNCPROV: "binddn="cn=admin,cn=config" bindmethod=simple credentials=$LDAP_CONFIG_PASSWORD searchbase="cn=config" type=refreshAndPersist retry="60 +" timeout=1 starttls=critical"
      #LDAP_REPLICATION_DB_SYNCPROV: "binddn="cn=admin,$LDAP_BASE_DN" bindmethod=simple credentials=$LDAP_ADMIN_PASSWORD searchbase="$LDAP_BASE_DN" type=refreshAndPersist interval=00:00:00:10 retry="60 +" timeout=1 starttls=critical"
      #LDAP_REPLICATION_HOSTS: "#PYTHON2BASH:['ldap://ldap.example.org','ldap://ldap2.example.org']"
      KEEP_EXISTING_CONFIG: "false"
      LDAP_REMOVE_CONFIG_AFTER_SETUP: "true"
      LDAP_SSL_HELPER_PREFIX: "ldap"
    command: "--copy-service"
    volumes:
      - ${LDIF_FILE:-./ldap/openldap-ldif/base2.ldif}:/container/service/slapd/assets/config/bootstrap/ldif/custom/10-base.ldif


  idp:
    image: jnyryan/simplesamlphp:${SIMPLESAML_CONTAINER_TAG:-latest}
    ports:
      - 20080:80
      - 20443:443
    volumes:
      - ./idp/simplesamlphp/config/config.php:/var/simplesamlphp/config/config.php
      - ./idp/simplesamlphp/config/authsources.php:/var/simplesamlphp/config/authsources.php
      - ./idp/simplesamlphp/metadata/saml20-sp-remote.php:/var/simplesamlphp/metadata/saml20-sp-remote.php
      - ./idp/simplesamlphp/cert:/var/simplesamlphp/cert
      - ./idp/simplesamlphp/enabled:/var/simplesamlphp/modules/ldap/enable
      - ./idp/simplesamlphp/metadata/saml20-idp-hosted-ldap.php:/var/simplesamlphp/metadata/saml20-idp-hosted.php

@davitol
Copy link
Author

davitol commented Mar 24, 2020

As spotted by @jvillafanez using the "jnyryan/simplesamlphp" docker image as idp for saml: the "ldapmulti" support is broken in that image. The image loads the code from github.com/simplesamlphp/simplesamlphp.git repo, master branch, probably from 3 years ago, which seems to have that support broken. It's recommended to enter the container and change the branch to the v1.14.9 version (and update the composer file) to fix this problem
git checkout v1.14.9 && ./composer.phar install (inside the idp container)
latest version seems to be 1.18.5, in case someone wants to provide a more up-to-date image

Tried these steps and worked for me

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

No branches or pull requests

1 participant