Add LDAP authentication
This commit is contained in:
81
models/ldap.php
Normal file
81
models/ldap.php
Normal file
@@ -0,0 +1,81 @@
|
||||
<?php
|
||||
|
||||
namespace Model;
|
||||
|
||||
require_once __DIR__.'/base.php';
|
||||
|
||||
/**
|
||||
* LDAP model
|
||||
*
|
||||
* @package model
|
||||
* @author Frederic Guillot
|
||||
*/
|
||||
class Ldap extends Base
|
||||
{
|
||||
/**
|
||||
* Authenticate a user
|
||||
*
|
||||
* @access public
|
||||
* @param string $username Username
|
||||
* @param string $password Password
|
||||
* @return bool
|
||||
*/
|
||||
public function authenticate($username, $password)
|
||||
{
|
||||
if (! function_exists('ldap_connect')) {
|
||||
die('The PHP LDAP extension is required');
|
||||
}
|
||||
|
||||
$ldap = ldap_connect(LDAP_SERVER, LDAP_PORT);
|
||||
|
||||
if (! is_resource($ldap)) {
|
||||
die('Unable to connect to the LDAP server: "'.LDAP_SERVER.'"');
|
||||
}
|
||||
|
||||
ldap_set_option($ldap, LDAP_OPT_PROTOCOL_VERSION, 3);
|
||||
ldap_set_option($ldap, LDAP_OPT_REFERRALS, 0);
|
||||
|
||||
if (@ldap_bind($ldap, sprintf(LDAP_USER_DN, $username), $password)) {
|
||||
return $this->create($username);
|
||||
}
|
||||
|
||||
return false;
|
||||
}
|
||||
|
||||
/**
|
||||
* Create automatically a new local user after the LDAP authentication
|
||||
*
|
||||
* @access public
|
||||
* @param string $username Username
|
||||
* @return bool
|
||||
*/
|
||||
public function create($username)
|
||||
{
|
||||
$userModel = new User($this->db, $this->event);
|
||||
$user = $userModel->getByUsername($username);
|
||||
|
||||
// There is an existing user account
|
||||
if ($user) {
|
||||
|
||||
if ($user['is_ldap_user'] == 1) {
|
||||
|
||||
// LDAP user already created
|
||||
return true;
|
||||
}
|
||||
else {
|
||||
|
||||
// There is already a local user with that username
|
||||
return false;
|
||||
}
|
||||
}
|
||||
|
||||
// Create a LDAP user
|
||||
$values = array(
|
||||
'username' => $username,
|
||||
'is_admin' => 0,
|
||||
'is_ldap_user' => 1,
|
||||
);
|
||||
|
||||
return $userModel->create($values);
|
||||
}
|
||||
}
|
||||
@@ -57,7 +57,7 @@ class User extends Base
|
||||
return $this->db
|
||||
->table(self::TABLE)
|
||||
->asc('username')
|
||||
->columns('id', 'username', 'is_admin', 'default_project_id')
|
||||
->columns('id', 'username', 'is_admin', 'default_project_id', 'is_ldap_user')
|
||||
->findAll();
|
||||
}
|
||||
|
||||
@@ -81,8 +81,13 @@ class User extends Base
|
||||
*/
|
||||
public function create(array $values)
|
||||
{
|
||||
if (isset($values['confirmation'])) unset($values['confirmation']);
|
||||
$values['password'] = \password_hash($values['password'], PASSWORD_BCRYPT);
|
||||
if (isset($values['confirmation'])) {
|
||||
unset($values['confirmation']);
|
||||
}
|
||||
|
||||
if (isset($values['password'])) {
|
||||
$values['password'] = \password_hash($values['password'], PASSWORD_BCRYPT);
|
||||
}
|
||||
|
||||
return $this->db->table(self::TABLE)->save($values);
|
||||
}
|
||||
@@ -154,6 +159,7 @@ class User extends Base
|
||||
$user['id'] = (int) $user['id'];
|
||||
$user['default_project_id'] = (int) $user['default_project_id'];
|
||||
$user['is_admin'] = (bool) $user['is_admin'];
|
||||
$user['is_ldap_user'] = (bool) $user['is_ldap_user'];
|
||||
|
||||
$_SESSION['user'] = $user;
|
||||
}
|
||||
@@ -242,9 +248,9 @@ class User extends Base
|
||||
if ($v->execute()) {
|
||||
|
||||
// Check password
|
||||
$user = $this->getById($_SESSION['user']['id']);
|
||||
list($authenticated,) = $this->authenticate($_SESSION['user']['username'], $values['current_password']);
|
||||
|
||||
if ($user !== false && \password_verify($values['current_password'], $user['password'])) {
|
||||
if ($authenticated) {
|
||||
return array(true, array());
|
||||
}
|
||||
else {
|
||||
@@ -275,13 +281,23 @@ class User extends Base
|
||||
|
||||
if ($result) {
|
||||
|
||||
$user = $this->getByUsername($values['username']);
|
||||
list($authenticated, $method) = $this->authenticate($values['username'], $values['password']);
|
||||
|
||||
if ($user !== false && \password_verify($values['password'], $user['password'])) {
|
||||
if ($authenticated === true) {
|
||||
|
||||
// Create the user session
|
||||
$user = $this->getByUsername($values['username']);
|
||||
$this->updateSession($user);
|
||||
|
||||
// Update login history
|
||||
$lastLogin = new LastLogin($this->db, $this->event);
|
||||
$lastLogin->create(
|
||||
$method,
|
||||
$user['id'],
|
||||
$this->getIpAddress(),
|
||||
$this->getUserAgent()
|
||||
);
|
||||
|
||||
// Setup the remember me feature
|
||||
if (! empty($values['remember_me'])) {
|
||||
$rememberMe = new RememberMe($this->db, $this->event);
|
||||
@@ -301,6 +317,32 @@ class User extends Base
|
||||
);
|
||||
}
|
||||
|
||||
/**
|
||||
* Authenticate a user
|
||||
*
|
||||
* @access public
|
||||
* @param string $username Username
|
||||
* @param string $password Password
|
||||
* @return array
|
||||
*/
|
||||
public function authenticate($username, $password)
|
||||
{
|
||||
// Database authentication
|
||||
$user = $this->db->table(self::TABLE)->eq('username', $username)->eq('is_ldap_user', 0)->findOne();
|
||||
$authenticated = $user && \password_verify($password, $user['password']);
|
||||
$method = LastLogin::AUTH_DATABASE;
|
||||
|
||||
// LDAP authentication
|
||||
if (! $authenticated && LDAP_AUTH) {
|
||||
require __DIR__.'/ldap.php';
|
||||
$ldap = new Ldap($this->db, $this->event);
|
||||
$authenticated = $ldap->authenticate($username, $password);
|
||||
$method = LastLogin::AUTH_LDAP;
|
||||
}
|
||||
|
||||
return array($authenticated, $method);
|
||||
}
|
||||
|
||||
/**
|
||||
* Get the user agent of the connected user
|
||||
*
|
||||
|
||||
Reference in New Issue
Block a user