Merge pull request #19 from nextcloud/add-users-in-db

Add SAML users to DB
This commit is contained in:
Lukas Reschke 2016-07-04 14:17:13 +02:00 committed by GitHub
commit d57c221ada
6 changed files with 136 additions and 20 deletions

View File

@ -34,7 +34,6 @@ $samlSettings = new \OCA\User_SAML\SAMLSettings(
$userBackend = new \OCA\User_SAML\UserBackend(
\OC::$server->getConfig(),
\OC::$server->getLogger(),
\OC::$server->getURLGenerator(),
\OC::$server->getSession(),
\OC::$server->getDb()

View File

@ -6,6 +6,27 @@
<overwrite>false</overwrite>
<charset>utf8</charset>
<table>
<name>*dbprefix*user_saml_users</name>
<declaration>
<field>
<name>uid</name>
<type>text</type>
<default></default>
<notnull>true</notnull>
<length>64</length>
</field>
<field>
<name>displayname</name>
<type>text</type>
<default></default>
<notnull>true</notnull>
<length>255</length>
</field>
</declaration>
</table>
<table>
<!-- Copied table from core: Nextcloud 9 does not support application
specific passwords and so we -->

View File

@ -5,7 +5,7 @@
<description>Authenticates user against a SAML backend, such as Shibboleth.</description>
<licence>AGPL</licence>
<author>Nextcloud</author>
<version>1.0.0</version>
<version>1.0.1</version>
<dependencies>
<owncloud min-version="9.0" max-version="9.0" />
</dependencies>

View File

@ -25,6 +25,7 @@ use OCA\User_SAML\Controller\AuthSettingsController;
use OCA\User_SAML\Controller\SAMLController;
use OCA\User_SAML\Controller\SettingsController;
use OCA\User_SAML\SAMLSettings;
use OCA\User_SAML\UserBackend;
use OCP\AppFramework\App;
use OCP\AppFramework\IAppContainer;
@ -66,7 +67,13 @@ class Application extends App {
$server->getRequest(),
$server->getSession(),
$server->getUserSession(),
new SAMLSettings($server->getURLGenerator(), $server->getConfig())
new SAMLSettings($server->getURLGenerator(), $server->getConfig()),
new UserBackend(
$server->getConfig(),
$server->getURLGenerator(),
$server->getSession(),
$server->getDb()
)
);
});
}

View File

@ -22,6 +22,7 @@
namespace OCA\User_SAML\Controller;
use OCA\User_SAML\SAMLSettings;
use OCA\User_SAML\UserBackend;
use OCP\AppFramework\Controller;
use OCP\AppFramework\Http;
use OCP\IRequest;
@ -35,6 +36,8 @@ class SAMLController extends Controller {
private $userSession;
/** @var SAMLSettings */
private $SAMLSettings;
/** @var UserBackend */
private $userBackend;
/**
* @param string $appName
@ -42,16 +45,19 @@ class SAMLController extends Controller {
* @param ISession $session
* @param IUserSession $userSession
* @param SAMLSettings $SAMLSettings
* @param UserBackend $userBackend
*/
public function __construct($appName,
IRequest $request,
ISession $session,
IUserSession $userSession,
SAMLSettings $SAMLSettings) {
SAMLSettings $SAMLSettings,
UserBackend $userBackend) {
parent::__construct($appName, $request);
$this->session = $session;
$this->userSession = $userSession;
$this->SAMLSettings = $SAMLSettings;
$this->userBackend = $userBackend;
}
/**
@ -114,8 +120,10 @@ class SAMLController extends Controller {
if(isset($auth->getAttributes()[$uidMapping])) {
$uid = $auth->getAttributes()[$uidMapping][0];
$userExists = \OC::$server->getUserManager()->userExists($uid);
if(!$userExists) {
if(!$userExists && !$this->userBackend->autoprovisionAllowed()) {
return new Http\RedirectResponse(\OC::$server->getURLGenerator()->linkToRouteAbsolute('user_saml.SAML.notProvisioned'));
} elseif(!$userExists && $this->userBackend->autoprovisionAllowed()) {
$this->userBackend->createUserIfNotExists($uid);
}
}

View File

@ -27,15 +27,12 @@ use OCP\IDb;
use OCP\UserInterface;
use OCP\IUserBackend;
use OCP\IConfig;
use OCP\ILogger;
use OCP\IURLGenerator;
use OCP\ISession;
class UserBackend implements IApacheBackend, UserInterface, IUserBackend {
/** @var IConfig */
private $config;
/** @var ILogger */
private $logger;
/** @var IURLGenerator */
private $urlGenerator;
/** @var ISession */
@ -47,23 +44,61 @@ class UserBackend implements IApacheBackend, UserInterface, IUserBackend {
/**
* @param IConfig $config
* @param ILogger $logger
* @param IURLGenerator $urlGenerator
* @param ISession $session
* @param IDb $db
*/
public function __construct(IConfig $config,
ILogger $logger,
IURLGenerator $urlGenerator,
ISession $session,
IDb $db) {
$this->config = $config;
$this->logger = $logger;
$this->urlGenerator = $urlGenerator;
$this->session = $session;
$this->db = $db;
}
/**
* Whether $uid exists in the database
*
* @param string $uid
* @return bool
*/
private function userExistsInDatabase($uid) {
/* @var $qb IQueryBuilder */
$qb = $this->db->getQueryBuilder();
$qb->select('token')
->from('user_saml_users')
->where($qb->expr()->eq('uid', $qb->createNamedParameter($uid)))
->setMaxResults(1);
$result = $qb->execute();
$users = $result->fetchAll();
$result->closeCursor();
return !empty($users);
}
/**
* Creates an user if it does not exists
*
* @param string $uid
*/
public function createUserIfNotExists($uid) {
if(!$this->userExistsInDatabase($uid)) {
$values = [
'uid' => $uid,
];
/* @var $qb IQueryBuilder */
$qb = $this->db->getQueryBuilder();
$qb->insert('user_saml_users');
foreach($values as $column => $value) {
$qb->setValue($column, $qb->createNamedParameter($value));
}
$qb->execute();
}
}
/**
* Check if backend implements actions
* @param int $actions bitwise-or'ed actions
@ -107,7 +142,6 @@ class UserBackend implements IApacheBackend, UserInterface, IUserBackend {
return false;
}
/**
* delete a user
* @param string $uid The username of the user to delete
@ -115,6 +149,14 @@ class UserBackend implements IApacheBackend, UserInterface, IUserBackend {
* @since 4.5.0
*/
public function deleteUser($uid) {
if($this->userExistsInDatabase($uid)) {
/* @var $qb IQueryBuilder */
$qb = $this->db->getQueryBuilder();
$qb->delete('user_saml_users')
->where($qb->expr()->eq('uid', $qb->createNamedParameter($uid)))
->execute();
return true;
}
return false;
}
@ -128,7 +170,27 @@ class UserBackend implements IApacheBackend, UserInterface, IUserBackend {
* @since 4.5.0
*/
public function getUsers($search = '', $limit = null, $offset = null) {
return false;
/* @var $qb IQueryBuilder */
$qb = $this->db->getQueryBuilder();
$qb->select('uid', 'displayname')
->from('user_saml_users')
->where(
$qb->expr()->iLike('uid', $qb->createNamedParameter('%' . $this->db->escapeLikeParameter($search) . '%'))
)
->setMaxResults($limit);
if($offset !== null) {
$qb->setFirstResult($offset);
}
$result = $qb->execute();
$users = $result->fetchAll();
$result->closeCursor();
$uids = [];
foreach($users as $user) {
$uids[] = $user['uid'];
}
return $uids;
}
/**
@ -140,12 +202,8 @@ class UserBackend implements IApacheBackend, UserInterface, IUserBackend {
public function userExists($uid) {
if($backend = $this->getActualUserBackend($uid)) {
return $backend->userExists($uid);
}
if($this->autoprovisionAllowed()) {
return true;
} else {
return false;
return $this->userExistsInDatabase($uid);
}
}
@ -169,7 +227,26 @@ class UserBackend implements IApacheBackend, UserInterface, IUserBackend {
* @since 4.5.0
*/
public function getDisplayNames($search = '', $limit = null, $offset = null) {
return [];
$qb = $this->db->getQueryBuilder();
$qb->select('uid', 'displayname')
->from('user_saml_users')
->where(
$qb->expr()->iLike('uid', $qb->createNamedParameter('%' . $this->db->escapeLikeParameter($search) . '%'))
)
->setMaxResults($limit);
if($offset !== null) {
$qb->setFirstResult($offset);
}
$result = $qb->execute();
$users = $result->fetchAll();
$result->closeCursor();
$uids = [];
foreach($users as $user) {
$uids[$user['uid']] = $user['displayname'];
}
return $uids;
}
/**
@ -178,6 +255,10 @@ class UserBackend implements IApacheBackend, UserInterface, IUserBackend {
* @since 4.5.0
*/
public function hasUserListings() {
if($this->autoprovisionAllowed()) {
return true;
}
return false;
}
@ -244,7 +325,7 @@ class UserBackend implements IApacheBackend, UserInterface, IUserBackend {
*
* @return bool
*/
private function autoprovisionAllowed() {
public function autoprovisionAllowed() {
return $this->config->getAppValue('user_saml', 'general-require_provisioned_account', '0') === '0';
}