From 0c1eaf3a311c0ba1eb2edeabf9667ce81580ce44 Mon Sep 17 00:00:00 2001 From: Crivaledaz Date: Thu, 2 May 2019 14:51:50 +0200 Subject: [PATCH] Refresh project and Readme Adapt vars name for consistency Add a light CSS design --- Docker/oauth/files/config_db.php | 14 +- Docker/oauth/files/config_ldap.php | 14 +- LICENSE | 2 +- .../templates/config_db.php.erb | 14 +- .../templates/config_ldap.php.erb | 14 +- README.md | 180 +++++++++--------- oauth/LDAP/LDAP.php | 80 ++++---- oauth/LDAP/LDAPInterface.php | 24 +-- oauth/LDAP/config_ldap.php.example | 14 +- oauth/authorize.php | 2 +- oauth/config_db.php.example | 14 +- oauth/connexion.php | 4 +- oauth/images/ButtonGreen.png | Bin 0 -> 977 bytes oauth/images/login.png | Bin 0 -> 39758 bytes oauth/index.php | 68 ++++++- oauth/resource.php | 4 +- oauth/server.php | 2 +- oauth/style.css | 57 ++++++ 18 files changed, 302 insertions(+), 205 deletions(-) create mode 100644 oauth/images/ButtonGreen.png create mode 100644 oauth/images/login.png create mode 100644 oauth/style.css diff --git a/Docker/oauth/files/config_db.php b/Docker/oauth/files/config_db.php index 36a5da8..4da57f3 100644 --- a/Docker/oauth/files/config_db.php +++ b/Docker/oauth/files/config_db.php @@ -1,12 +1,12 @@ "; -$host = "<%= @db_host %>"; -$name = "<%= @db_name %>"; -$type = "<%= @db_type %>"; -$username = "<%= @db_user %>"; -$password = "<%= @db_pass %>"; -$dsn = $type . ":dbname=" . $name . ";host=" . $host . ";port=" . $port; +$db_port = "<%= @db_port %>"; +$db_host = "<%= @db_host %>"; +$db_name = "<%= @db_name %>"; +$db_type = "<%= @db_type %>"; +$db_user = "<%= @db_user %>"; +$db_pass = "<%= @db_pass %>"; +$dsn = $type . ":dbname=" . $name . ";host=" . $host . ";port=" . $port; //Set date.timezone to avoid E.Notice raise by strtotime() (in Pdo.php) //If date.timezone is not defined, Mattermost will return a bad token request error diff --git a/Puppet/mattermostldap/templates/config_ldap.php.erb b/Puppet/mattermostldap/templates/config_ldap.php.erb index c08c4db..0bfc8a7 100755 --- a/Puppet/mattermostldap/templates/config_ldap.php.erb +++ b/Puppet/mattermostldap/templates/config_ldap.php.erb @@ -1,17 +1,17 @@ "; -$port = <%= @ldap_port %>; +$ldap_host = "<%= @ldap_uri %>"; +$ldap_port = <%= @ldap_port %>; // Attribute use to identify user on LDAP (used in connexion.php, replace $rdn_suffix) - ex : uid, mail, sAMAccountName -$search_attribute = "<%= @ldap_attribute %>"; +$ldap_search_attribute = "<%= @ldap_attribute %>"; // Base directory name of the LDAP -$base = "<%= @ldap_base %>"; +$ldap_base_dn = "<%= @ldap_base %>"; // An optional filter to search in LDAP - ex : objectClass=person -$filter = "<%= @ldap_filter %>"; +$ldap_filter = "<%= @ldap_filter %>"; // ldap service user to allow search in ldap -$bind_dn = "<%= @ldap_bind_dn %>"; -$bind_pass = "<%= @ldap_bind_pass %>"; \ No newline at end of file +$ldap_bind_dn = "<%= @ldap_bind_dn %>"; +$ldap_bind_pass = "<%= @ldap_bind_pass %>"; \ No newline at end of file diff --git a/README.md b/README.md index 07c0bf5..059f82d 100755 --- a/README.md +++ b/README.md @@ -35,33 +35,35 @@ Obviously, you must have a Mattermost Server installed and be administrator on i Install required packages : * For Centos 7, RHEL 7 and Fedora : -``` +```bash #For PostgreSQL sudo yum -y --nogpgcheck install httpd php postgresql-server postgresql php-ldap php-pdo php-pgsql git #For MySQL sudo yum -y --nogpgcheck install httpd php mariadb-server mariadb php-ldap php-pdo php-mysql git ``` + * For Debian, ubuntu, Mint : -``` +```bash #For PostgreSQL sudo apt-get -y install httpd php postgresql-server postgresql php-ldap php-pdo php-pgsql git #For MySQL sudo apt-get -y install httpd php mariadb-server mariadb php-ldap php-pdo php-mysql git ``` + Setup your SQL server with the following command : -``` +```bash #For PostgreSQL (create a new database cluster) sudo postgresql-setup initdb #For MySQL (optional configuration for a secure MySQL server) sudo mysql_secure_installation ``` -By default, PostgreSQL does not allow client authentication on the server or a database. So we need to enable it by editing pg_hba.conf file (in /var/lib/pgsql). Open this file and replace 'ident' by 'md5' on the first three lines (local, host 127.0.0.1 and host ::1/128). It's recommended to backup the original file before editing it. +By default, PostgreSQL does not allow client authentication on the server or a database. So we need to enable it by editing pg_hba.conf file (in `/var/lib/pgsql`). Open this file and replace `ident` by `md5` on the first three lines (local, host 127.0.0.1 and host ::1/128). It's recommended to backup the original file before editing it. Then, start and enable service for Apache and Database (for all distribution using systemd): -``` +```bash #For PostgreSQL sudo systemctl start httpd sudo systemctl start postgresql @@ -78,10 +80,9 @@ sudo systemctl enable mariadb Your system is ready to install and run Mattermost-LDAP module. - ## Install -Clone (or download and extract) this repository in your /var/www/html (or your httpd root directory) : -``` +Clone (or download and extract) this repository in your `/var/www/html` (or your httpd root directory) : +```bash cd ~ git clone https://github.com/crivaledaz/Mattermost-LDAP.git cd Mattermost-LDAP @@ -89,137 +90,128 @@ cp -r oauth/ /var/www/html/ ``` You need to create a database for the oauth server. For this purpose, you can use the script "init_postgres.sh" or "init_mysql.sh". These scripts try to configure your database automatically, by creating a new user and a new database associated for the oauth server. Scripts also create all tables necessary for the module. If script failed, please report here, and try to configure manually your database by adapting command in scripts. Before running the script you can change the default settings by editing the config_init.sh file and modifying configuration variables. For postgresql, you can copy and paste following lines : -``` +```bash nano config_init.sh ./init_postgres.sh ``` This script will automatically create and add a new client in the oauth server, returning a client id and a client secret. You need to keep these two token to configure Mattermost. Please be sure the client secret remained secret. The redirect url in the script must comply with the hostname of your Mattermost server, else Mattermost could not get data from the Oauth server. - ## Configuration Configuration files are provided with examples and default values. Each config file has an ".example" extension, so you need to copy and to rename them without this extension. You can find a detailed description of each parameters available below. -* Init script configuration : -#### oauth_user -Oauth user in the database. This user must have right on the oauth database to store oauth tokens. By default : oauth -#### oauth_pass -Oauth user password in the database. By default, oauth_secure-pass -#### ip -Hostname or IP address of the database. By default : 127.0.0.1 -#### port -The port to connect to the database. By default : 5432 (postgres) -#### oauth_db_name -Database name for oauth server. By default : oauth_db -#### client_id -The application ID shared with mattermost. This ID should be a random token. You can use openssl to generate this token (openssl rand -hex 32). By default, this variable contain the openssl command, which use the openssl package. The token will be printed at the end of the script. -#### client_secret -The application secret shared with mattermost. This secret should be a random token. You can use openssl to generate this token (openssl rand -hex 32). By default, this variable contain the openssl command, which use the openssl package. The token will be printed at the end of the script. Secret must be different of the client ID. -#### redirect_uri -The callback address where oauth will send tokens to Mattermost. Normally it should be http://mattermost.company.com/signup/gitlab/complete -#### grant_types -The type of authentification use by Mattermost. It should be "authorization_code". -#### scope -The scope of authentification use by Mattermost. It should be "api". -#### user_id -The username of the user who create the Mattermost client in Oauth. This field has no impact, and could be used as a commentary field. By default this field is empty. - -* Mattermost : -Active Gitlab authentication in system console > Gitlab (or config.json on server) and fill application id and secret with the two token got during install section. For the next fields use this : +### Init script parameters + +| Parameter | Description | Default value | +|---------------|-----------------------------------------------------------------------|-------------------------------------------------------| +| oauth_user | Oauth user in the database. | oauth | +| oauth_pass | Oauth user password in the database. | oauth_secure-pass | +| ip | Hostname or IP address of the database. | 127.0.0.1 | +| port | The port to connect to the database. | 5432 (Postgres) | +| oauth_db_name | Database name for oauth server. | oauth_db | +| client_id | The application ID shared with mattermost. | `openssl rand -hex 32` | +| client_secret | The application secret shared with mattermost. | `openssl rand -hex 32` | +| redirect_uri | The callback address where oauth will send tokens to Mattermost. | http://mattermost.company.com/signup/gitlab/complete | +| grant_types | The type of authentification use by Mattermost. | authorization_code | +| scope | The scope of authentification use by Mattermost. | api | +| user_id | The username of the user who create the Mattermost client in Oauth. | | + +Note : The 'oauth_user' must have all privilege on the oauth database to manage oauth tokens. + +The 'client_id' and 'client_secret' should be different and random tokens. You can use openssl to generate these tokens (`openssl rand -hex 32`). By default, these variables contain the `openssl` command, which use the openssl package. Tokens will be generated and printed at the end of the script. + +The var 'user_id' has no impact, and could be used as a commentary field. By default this field is empty. + + +### Mattermost + +Active Gitlab authentication in `System Console > Gitlab` (or `config.json`) and fill application id and secret with the two tokens got during install section. For the next fields use this : ``` User API Endpoint : http://HOSTNAME/oauth/resource.php Auth Endpoint: http://HOSTNAME/oauth/authorize.php Token Endpoint: http://HOSTNAME/oauth/token.php ``` -Change HOSTNAME by hostname or ip of the server where you have installed Mattermost-LDAP module. - -In Mattermost 4.9, these fields are disable in admin panel, so you need to edit directly the configuration file config.json. - -* Database credentials -Edit oauth/config_db.php and adapt, with your settings, to set up database in PHP. - -#### $host -Hostname or IP address of the database. (ex : localhost) -#### $port -The port of your database to connect. (ex : 5432 for postgres) -#### $name -Database name for oauth server. If you use init script make sure to use the same database name. (ex : oauth_db) -#### $type -Database type to adapt PDO to your database server. Should be mysql or pgsql. -#### $username -Oauth user in the database. This user must have right on the oauth database to store oauth tokens. If you use init script make sure to use the same database user. (ex : oauth) -#### $password -Oauth user password in the database. If you use init script make sure to use the same database user. (ex : oauth_secure-pass) - -* LDAP config -Edit oauth/LDAP/config_ldap.php : -1. Provide your ldap address, port and version. -2. Change the base directory name ($base) and the filter ($filter) to comply with your LDAP configuration. -3. Change the user ID attribute ($ldap_attribute) to comply with your LDAP configuration (uid, sAMAccountName, email, cn ..). -4. If necessary, you can provide a LDAP account to allow search in LDAP (only restrictive LDAP). - -#### $hostname -Your LDAP hostname or LDAP IP, to connect to the LDAP server. -#### $port -Your LDAP port, to connect to the LDAP server. By default : 389. -#### $ldap_version -Your LDAP version, or protocol version used by your server. By default : 3. This parameter avoid LDAP blind error with LDAP 3 (issue #14) -#### $search_attribute -The attribute used to identify user on your LDAP. Should be uid, email, cn or sAMAccountName. -#### $base -The base directory name of your LDAP server. (ex : ou=People,o=Company) -#### $filter -Additional filters to search in LDAP (used to get user informations). (ex : objectClass=person) -#### $bind_dn -The LDAP Directory Name of an service account to allow LDAP search. This ption is required if your LDAP is restrictive, else put an empty string (""). (ex : cn=mattermost_ldap,dc=Example,dc=com) -#### $bind_pass -The password associated to the service account to allow LDAP search. This ption is required if your LDAP you provide an bind user, else put an empty string (""). - - - -To try your configuration you can use ldap.php available at the root of this project which use the LDAP library for PHP or you can use ldapsearch command in a shell. +Change `HOSTNAME` by hostname or ip of the server where you have installed Mattermost-LDAP module. + +Since Mattermost 4.9, these fields are disabled in admin panel, so you need to edit directly the configuration file `config.json`. + +### Database credentials +Edit `oauth/config_db.php` and adapt, with your settings, to set up database in PHP. + +| Parameter | Description | Default value | +|------------|----------------------------------------------------------------------|--------------------| +| db_host | Hostname or IP address of the database server | 127.0.0.1 | +| db_port | The port of your database to connect | 5432 | +| db_type | Database type to adapt PDO. Should be pgsql or mysql. | pgsql | +| db_user | User who manages oauth database | oauth | +| db_pass | User's password to manage oauth database | oauth_secure-pass | +| db_name | Database name for oauth server | oauth_db | + +If you use the init script, make sure to use the same values for database parameters : 'oauth_user' = 'db_user', 'oauth_pass' = 'db_pass', 'oauth_db_name' = 'db_name'. + +Note : The 'db_user' must have all privilege on the oauth database to manage oauth tokens. + +### LDAP configuration + +Edit `oauth/LDAP/config_ldap.php` and adapt prameters with your LDAP configuration : + +| Parameter | Description | Default value | +|-----------------------|-----------------------------------------------------------------------|--------------------------| +| ldap_host | URL or IP to connect LDAP server | ldap://ldap.company.com/ | +| ldap_port | Port used to connect LDAP server | 389 | +| ldap_version | LDAP version or protocol version used by LDAP server | 3 | +| ldap_search_attribute | Attribute used to identify a user on the LDAP | uid | +| ldap_filter | Additional filter for LDAP search | objectClass=* | +| ldap_base_dn | The base directory name of your LDAP server | ou=People,o=Company | +| ldap_bind_dn | The LDAP Directory Name of an service account to allow LDAP search | | +| ldap_bind_pass | The password associated to the service account to allow LDAP search | | + +For openLDAP server, the 'ldap_search_attribute' should be `uid`, and for AD server this must be `sAMAccountName`. Nevertheless, 'email' or 'cn' could be used, this depends on your LDAP configuration. + +Parameters 'ldap_bind_dn' and 'ldap_bind_pass' are required if your LDAP is restrictive, else put an empty string (""). + +Note : 'ldap_version' avoid LDAP blind error with LDAP 3 (issue #14) + +To try your configuration you can use `ldap.php` available at the root of this project which use the LDAP library for PHP or you can use `ldapsearch` command in a shell. Configure LDAP is certainly the most difficult step. ## Usage If you have succeeded previous step you only have to go to the login page of your Mattermost server and click on the Gitlab Button. You will be redirected to a form asking for your LDAP credentials. If your credentials are valid, you will be asked to authorize Oauth to give your information to Mattermost. After authorizing you should be redirected on Mattermost connected with your account. -Keep in mind this will create a new account on your Mattermost server with information from LDAP. The process will fail if an existing user already use your LDAP email. To bind a user to the LDAP authentication, sign in mattermost with this user account, go in account settings > security > sign-in method and "switch to using Gitlab SSO". - +Keep in mind this will create a new account on your Mattermost server with information from LDAP. The process will fail if an existing user already use your LDAP email. To bind an existing user to the LDAP authentication, sign in mattermost with this user account, go in `account settings > security > sign-in method and "switch to using Gitlab SSO"`. ## Limitation -This module has been tested on Centos 7, Fedora and Ubuntu with PostgreSQL and Mattermost Community Edition version 4.1, 4.9 and 5.0.1. Mattermost-LDAP is compliant with Mattermost Team Edition 4.x.x and 5.x.x. +This module has been tested on Centos 7, Fedora and Ubuntu with PostgreSQL and Mattermost Community Edition version 4.1, 4.9, 5.0.1 and 5.10. Mattermost-LDAP is compliant with Mattermost Team Edition 4.x.x and 5.x.x. Others operating systems has not been tested yet but should work fine. MySQL has not really been tested so it is possible there is some bugs with. - ## To do list - * Gathering LDAP config + * HTTPS support * Add CSS to make a beautiful interface for Oauth server - * Create an associated Puppet module * Change Gitlab button * Security audit ## Thanks -I wish to thank my company and my colleagues for their help and support. Also, I thank Brent Shaffer for his Oauth-server-php project and its documentation. - +I wish to thank CS SI and my colleagues for their help and support. Also, I thank Brent Shaffer for his Oauth-server-php project and its documentation. ## Known issues + * LDAP authentication failed Try to restart httpd service. If this persists verify your LDAP configuration or your credentials. * PHP date timezone error - Edit php.ini to set up date.timezone option and restart httpd service, or use the date_default_timezone_set() function in config_db.php + Edit `php.ini` to set up date.timezone option and restart httpd service, or use the `date_default_timezone_set()` function in `config_db.php` * Token request failed - Try to add a new rule in your firewall (or use iptables -F on both Mattermost server and Oauth server) + Try to add a new rule in your firewall (or use `iptables -F` on both Mattermost server and Oauth server) * .htaccess does not work - Add following lines to your httpd.conf and restart httpd service. + Add following lines to your `httpd.conf` and restart httpd service. ``` AllowOverride All diff --git a/oauth/LDAP/LDAP.php b/oauth/LDAP/LDAP.php index 3adf148..30ecca8 100755 --- a/oauth/LDAP/LDAP.php +++ b/oauth/LDAP/LDAP.php @@ -16,28 +16,28 @@ class LDAP implements LDAPInterface /** * LDAP Resource * - * @param string @hostname + * @param string @ldap_host * Either a hostname or, with OpenLDAP 2.x.x and later, a full LDAP URI - * @param int @port + * @param int @ldap_port * An optional int to specify ldap server port, by default : 389 * @param int @ldap_version * An optional int to specify ldap version, by default LDAP V3 protocol is used * * Initiate LDAP connection by creating an associated resource */ - public function __construct($hostname, $port = 389, $ldap_version = 3) + public function __construct($ldap_host, $ldap_port = 389, $ldap_version = 3) { - if (!is_string($hostname)) + if (!is_string($ldap_host)) { throw new InvalidArgumentException('First argument to LDAP must be the hostname of a ldap server (string). Ex: ldap//example.com/ '); } - if (!is_int($port)) + if (!is_int($ldap_port)) { throw new InvalidArgumentException('Second argument to LDAP must be the ldap server port (int). Ex : 389'); } - $ldap = ldap_connect($hostname, $port) + $ldap = ldap_connect($ldap_host, $ldap_port) or die("Unable to connect to the ldap server : $ldaphost ! Please check your configuration."); // Support LDAP V3 since many users have encountered difficulties with LDAP V3. @@ -58,22 +58,22 @@ public function __construct($hostname, $port = 389, $ldap_version = 3) * A ldap username or email or sAMAccountName * @param string @password * An optional password linked to the user, if not provided an anonymous bind is attempted - * @param string @search_attribute + * @param string @ldap_search_attribute * The attribute used on your LDAP to identify user (uid, email, cn, sAMAccountName) - * @param string @filter + * @param string @ldap_filter * An optional filter to search in LDAP (ex : objectClass = person). - * @param string @base_dn + * @param string @ldap_base_dn * The LDAP base DN. - * @param string @bind_dn + * @param string @ldap_bind_dn * The directory name of a service user to bind before search. Must be a user with read permission on LDAP. - * @param string @bind_pass + * @param string @ldap_bind_pass * The password associated to the service user to bind before search. * * @return * TRUE if the user is identified and can access to the LDAP server * and FALSE if it isn't */ - public function checkLogin($user, $password = null, $search_attribute, $filter = null, $base_dn,$bind_dn, $bind_pass) { + public function checkLogin($user, $password = null, $ldap_search_attribute, $ldap_filter = null, $ldap_base_dn,$ldap_bind_dn, $ldap_bind_pass) { if (!is_string($user)) { throw new InvalidArgumentException('First argument to LDAP/checkLogin must be the username or email of a ldap user (string). Ex: jdupont or jdupont@company.com'); @@ -82,31 +82,31 @@ public function checkLogin($user, $password = null, $search_attribute, $filter = { throw new InvalidArgumentException('Second argument to LDAP/checkLogin must be the password associated to the relative directory name (string).'); } - if (!is_string($search_attribute)) + if (!is_string($ldap_search_attribute)) { throw new InvalidArgumentException('Third argument to LDAP/checkLogin must be the attribute to identify users (ex : uid, email, sAMAccountName) (string).'); } - if (!is_string($filter) && $filter != null) + if (!is_string($ldap_filter) && $ldap_filter != null) { throw new InvalidArgumentException('Fourth argument to LDAP/checkLogin must be an optional filter to search in LDAP (string).'); } - if (!is_string($base_dn)) + if (!is_string($ldap_base_dn)) { throw new InvalidArgumentException('Fifth argument to LDAP/checkLogin must be the ldap base directory name (string). Ex: o=Company'); } - if (!is_string($bind_dn) && $bind_dn != null) + if (!is_string($ldap_bind_dn) && $ldap_bind_dn != null) { throw new InvalidArgumentException('Sixth argument to LDAP/checkLogin must be an optional service account on restrictive LDAP (string).'); } - if (!is_string($bind_pass) && $bind_pass != null) + if (!is_string($ldap_bind_pass) && $ldap_bind_pass != null) { throw new InvalidArgumentException('Seventh argument to LDAP/checkLogin must be an optional password for the service account on restrictive LDAP (string).'); } // If LDAP service account for search is specified, do an ldap_bind with this account - if ($bind_dn != '' && $bind_dn != null) + if ($ldap_bind_dn != '' && $ldap_bind_dn != null) { - $bind_result=ldap_bind($this->ldap_server,$bind_dn,$bind_pass); + $bind_result=ldap_bind($this->ldap_server,$ldap_bind_dn,$ldap_bind_pass); // If authentification failed, throw an exception if (!$bind_result) @@ -114,17 +114,17 @@ public function checkLogin($user, $password = null, $search_attribute, $filter = throw new Exception('An error has occured during ldap_bind execution. Please check parameter of LDAP/checkLogin, and make sure that user provided have read permission on LDAP.'); } } - if ($filter!="" && $filter != null) + if ($ldap_filter!="" && $ldap_filter != null) { - $search_filter = '(&(' . $search_attribute . '=' . $user . ')(' . $filter .'))'; + $search_filter = '(&(' . $ldap_search_attribute . '=' . $user . ')(' . $ldap_filter .'))'; } else { - $search_filter = $search_attribute . '=' . $user; + $search_filter = $ldap_search_attribute . '=' . $user; } - $result = ldap_search($this->ldap_server, $base_dn, $search_filter, array(), 0, 1, 500); + $result = ldap_search($this->ldap_server, $ldap_base_dn, $search_filter, array(), 0, 1, 500); if (!$result) { @@ -146,15 +146,15 @@ public function checkLogin($user, $password = null, $search_attribute, $filter = } /** - * @param string @base_dn + * @param string @ldap_base_dn * The LDAP base DN. - * @param string @filter + * @param string @ldap_filter * A filter to get relevant data. Often the user id in ldap (uid or sAMAccountName). - * @param string @bind_dn + * @param string @ldap_bind_dn * The directory name of a service user to bind before search. Must be a user with read permission on LDAP. - * @param string @bind_pass + * @param string @ldap_bind_pass * The password associated to the service user to bind before search. - * @param string @search_attribute + * @param string @ldap_search_attribute * The attribute used on your LDAP to identify user (uid, email, cn, sAMAccountName) * @param string @user * A ldap username or email or sAMAccountName @@ -162,27 +162,27 @@ public function checkLogin($user, $password = null, $search_attribute, $filter = * @return * An array with the user's mail, complete name and directory name. */ - public function getDataForMattermost($base_dn, $filter, $bind_dn, $bind_pass, $search_attribute, $user) { + public function getDataForMattermost($ldap_base_dn, $ldap_filter, $ldap_bind_dn, $ldap_bind_pass, $ldap_search_attribute, $user) { $attribute=array("cn","mail"); - if (!is_string($base_dn)) + if (!is_string($ldap_base_dn)) { throw new InvalidArgumentException('First argument to LDAP/getData must be the ldap base directory name (string). Ex: o=Company'); } - if (!is_string($filter)) + if (!is_string($ldap_filter)) { throw new InvalidArgumentException('Second argument to LDAP/getData must be a filter to get relevant data. Often is the user id in ldap (string). Ex : uid=jdupont'); } - if (!is_string($bind_dn) && $bind_dn != null) + if (!is_string($ldap_bind_dn) && $ldap_bind_dn != null) { throw new InvalidArgumentException('Third argument to LDAP/getData must be an optional service account on restrictive LDAP (string).'); } - if (!is_string($bind_pass) && $bind_pass != null) + if (!is_string($ldap_bind_pass) && $ldap_bind_pass != null) { throw new InvalidArgumentException('Fourth argument to LDAP/getData must be an optional password for the service account on restrictive LDAP (string).'); } - if (!is_string($search_attribute)) + if (!is_string($ldap_search_attribute)) { throw new InvalidArgumentException('Fifth argument to LDAP/getData must be the attribute to identify users (ex : uid, email, sAMAccountName) (string).'); } @@ -192,9 +192,9 @@ public function getDataForMattermost($base_dn, $filter, $bind_dn, $bind_pass, $s } // If LDAP service account for search is specified, do an ldap_bind with this account - if ($bind_dn != '' && $bind_dn != null) + if ($ldap_bind_dn != '' && $ldap_bind_dn != null) { - $bind_result=ldap_bind($this->ldap_server,$bind_dn,$bind_pass); + $bind_result=ldap_bind($this->ldap_server,$ldap_bind_dn,$ldap_bind_pass); // If authentification failed, throw an exception if (!$bind_result) @@ -203,16 +203,16 @@ public function getDataForMattermost($base_dn, $filter, $bind_dn, $bind_pass, $s } } - if ($filter!="" && $filter != null) + if ($ldap_filter!="" && $ldap_filter != null) { - $search_filter = '(&(' . $search_attribute . '=' . $user . ')(' . $filter .'))'; + $search_filter = '(&(' . $ldap_search_attribute . '=' . $user . ')(' . $ldap_filter .'))'; } else { - $search_filter = $search_attribute . '=' . $user; + $search_filter = $ldap_search_attribute . '=' . $user; } - $result = ldap_search($this->ldap_server, $base_dn, $search_filter, array(), 0, 1, 500); + $result = ldap_search($this->ldap_server, $ldap_base_dn, $search_filter, array(), 0, 1, 500); if (!$result) { diff --git a/oauth/LDAP/LDAPInterface.php b/oauth/LDAP/LDAPInterface.php index f050989..09e4f25 100755 --- a/oauth/LDAP/LDAPInterface.php +++ b/oauth/LDAP/LDAPInterface.php @@ -12,33 +12,33 @@ interface LDAPInterface * A ldap username or email or sAMAccountName * @param string @password * An optional password linked to the user, if not provided an anonymous bind is attempted - * @param string @search_attribute + * @param string @ldap_search_attribute * The attribute used on your LDAP to identify user (uid, email, cn, sAMAccountName) - * @param string @filter + * @param string @ldap_filter * An optional filter to search in LDAP (ex : objectClass = person). - * @param string @base_dn + * @param string @ldap_base_dn * The LDAP base DN. - * @param string @bind_dn + * @param string @ldap_bind_dn * The directory name of a service user to bind before search. Must be a user with read permission on LDAP. - * @param string @bind_pass + * @param string @ldap_bind_pass * The password associated to the service user to bind before search. * * @return * TRUE if the user is identified and can access to the LDAP server * and FALSE if it isn't */ - public function checkLogin($user,$password = null,$search_attribute,$filter = null,$base_dn,$bind_dn,$bind_pass); + public function checkLogin($user,$password = null,$ldap_search_attribute,$ldap_filter = null,$ldap_base_dn,$ldap_bind_dn,$ldap_bind_pass); /** - * @param string @base_dn + * @param string @ldap_base_dn * The LDAP base DN. - * @param string @filter + * @param string @ldap_filter * A filter to get relevant data. Often the user id in ldap (uid or sAMAccountName). - * @param string @bind_dn + * @param string @ldap_bind_dn * The directory name of a service user to bind before search. Must be a user with read permission on LDAP. - * @param string @bind_pass + * @param string @ldap_bind_pass * The password associated to the service user to bind before search. - * @param string @search_attribute + * @param string @ldap_search_attribute * The attribute used on your LDAP to identify user (uid, email, cn, sAMAccountName) * @param string @user * A ldap username or email or sAMAccountName @@ -46,5 +46,5 @@ public function checkLogin($user,$password = null,$search_attribute,$filter = nu * @return * An array with the user's mail, complete name and directory name. */ - public function getDataForMattermost($base_dn, $filter, $bind_dn, $bind_pass, $search_attribute, $user); + public function getDataForMattermost($ldap_base_dn, $ldap_filter, $ldap_bind_dn, $ldap_bind_pass, $ldap_search_attribute, $user); } diff --git a/oauth/LDAP/config_ldap.php.example b/oauth/LDAP/config_ldap.php.example index 47cd54e..cc35997 100755 --- a/oauth/LDAP/config_ldap.php.example +++ b/oauth/LDAP/config_ldap.php.example @@ -1,16 +1,16 @@ - +
diff --git a/oauth/config_db.php.example b/oauth/config_db.php.example index f161fe3..0132c42 100755 --- a/oauth/config_db.php.example +++ b/oauth/config_db.php.example @@ -1,12 +1,12 @@ checkLogin($user,$password,$search_attribute,$filter,$base,$bind_dn,$bind_pass); + $authenticated = $ldap->checkLogin($user,$password,$ldap_search_attribute,$ldap_filter,$ldap_base_dn,$ldap_bind_dn,$ldap_bind_pass); } catch (Exception $e) { diff --git a/oauth/images/ButtonGreen.png b/oauth/images/ButtonGreen.png new file mode 100644 index 0000000000000000000000000000000000000000..9a88c41cff45532c3f4d2d9c61ce1fa5a0d661f2 GIT binary patch literal 977 zcmeAS@N?(olHy`uVBq!ia0vp^Ahr|-GmzYAWh(-t7>k44ofy`glX(f`u%tWsIx;Y9 z?C1WI$jZRL%n;xc;%d}bW873{(o%2Q)@at=WZv0g-qmK=)n?J%Zq?In+0$Xw+iBh3 zWiz42c4DvHq(1v8{SH$nI8K}BG<_1#%uz5J0z*0kcJ|HE1A2h7z$3Dlfr0NZ2s0kf zUy%Y7lq_+LC<)F_D=AMbN@WO0%*-p%^K%VRC^ObG)id?%`tty&$kfxtF+?MH?ZM-W z4GIhg4s@_)YVG*H?vD{;dCViRNRdES;r@!F>boQ!iF@ZNb;Qa%5(!lCHM+~5`%zk7 Q3upj?r>mdKI;Vst08N`!`~Uy| literal 0 HcmV?d00001 diff --git a/oauth/images/login.png b/oauth/images/login.png new file mode 100644 index 0000000000000000000000000000000000000000..6034af08cc871120f1e38d66ca43225f4538b14e GIT binary patch literal 39758 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

0{nm_#O@j3O&cPTE>|#iwd9g-TC2HG1v^A6) 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 literal 0 HcmV?d00001 diff --git a/oauth/index.php b/oauth/index.php index 67e60e5..11190e7 100644 --- a/oauth/index.php +++ b/oauth/index.php @@ -5,20 +5,68 @@ + LDAP Connection Interface -
-

- Connection -

-
- -

-
+
+
 
+ + + + + +
  + -

- + + + +
+
LDAP Authentification
+ + +
+ + + + + + + + + + + + + + + + + + + +
+ +
+ +
+   +
+ Username:  + + +
+ Password:  + + +
 
+
+ +
+ +
+ \ No newline at end of file diff --git a/oauth/resource.php b/oauth/resource.php index 40247cc..59af40e 100755 --- a/oauth/resource.php +++ b/oauth/resource.php @@ -27,12 +27,12 @@ $assoc_id = intval($info_oauth["assoc_id"]); // Open a LDAP connection -$ldap = new LDAP($hostname,$port,$ldap_version); +$ldap = new LDAP($ldap_host,$ldap_port,$ldap_version); // Try to get user data on the LDAP try { - $data = $ldap->getDataForMattermost($base,$filter,$bind_dn,$bind_pass,$search_attribute,$user); + $data = $ldap->getDataForMattermost($ldap_base_dn,$ldap_filter,$ldap_bind_dn,$ldap_bind_pass,$ldap_search_attribute,$user); // Here is the patch for Mattermost 4.4 and older. Gitlab has changed the JSON output of oauth service. Many data are not used by Mattermost, but there is a stack error if we delete them. That's the reason why date and many parameters are null or empty. $resp = array("id" => $assoc_id,"name" => $data['cn'],"username" => $user,"state" => "active","avatar_url" => "","web_url" => "","created_at" => "0000-00-00T00:00:00.000Z","bio" => null,"location" => null,"skype" => "","linkedin" => "","twitter" => "","website_url" => "","organization" => null,"last_sign_in_at" => "0000-00-00T00:00:00.000Z","confirmed_at" => "0000-00-00T00:00:00.000Z","last_activity_on" => null,"email" => $data['mail'],"theme_id" => 1,"color_scheme_id" => 1,"projects_limit" => 100000,"current_sign_in_at" => "0000-00-00T00:00:00.000Z","identities" => array(array("provider" => "ldapmain","extern_uid" => $data['dn'])),"can_create_group" => true,"can_create_project" => true,"two_factor_enabled" => false,"external" => false,"shared_runners_minutes_limit" => null); diff --git a/oauth/server.php b/oauth/server.php index 76be9f8..0aa284f 100644 --- a/oauth/server.php +++ b/oauth/server.php @@ -11,7 +11,7 @@ OAuth2\Autoloader::register(); //$dsn is the Data Source Name for your database, for exmaple "mysql:dbname=my_oauth2_db;host=localhost" -$storage = new OAuth2\Storage\Pdo(array('dsn' => $dsn, 'username' => $username, 'password' => $password)); +$storage = new OAuth2\Storage\Pdo(array('dsn' => $dsn, 'username' => $db_user, 'password' => $db_pass)); // Pass a storage object or array of storage objects to the OAuth2 server class $server = new OAuth2\Server($storage); diff --git a/oauth/style.css b/oauth/style.css new file mode 100644 index 0000000..8b3765c --- /dev/null +++ b/oauth/style.css @@ -0,0 +1,57 @@ +html +{ + height: 100%; + margin: 0; +} + +body { + font-family:"Tahoma","Arial", serif; + font-size:8px; + font-weight: normal; + color: black; + text-decoration:none; + background-color: white; + height: 100%; + margin: 0; +} + + +.LoginTitle { + color: #000000; + font-family : "Tahoma","Arial", serif; + font-size : 18pt; + font-weight: normal; +} + +.LoginUsername { + color: #000000; + font-family : "Tahoma","Arial", serif; + font-size : 14pt; + font-weight: normal; +} + +.LoginComment { + color: #000000; + font-family : "Tahoma","Arial", serif; + font-size : 8pt; + font-weight: normal; +} + +.GreenButton +{ + color: white; + font-family : "Tahoma", "Arial", serif; + font-size : 10pt; + font-weight: normal; + height: 28px; + background: transparent url(images/ButtonGreen.png) repeat-x left top; + border: solid 1px #50B4AE; + font-weight: bold; +} + +.messageLogin { + color: Yellow; + font-family : "Tahoma", "Arial", serif; + font-size : 8pt; + font-weight: bold; +}