ILIAS  release_5-4 Revision v5.4.26-12-gabc799a52e6
class.ilAuthFrontend.php
Go to the documentation of this file.
1 <?php
2 
3 /* Copyright (c) 1998-2010 ILIAS open source, Extended GPL, see docs/LICENSE */
4 
12 {
13  const MIG_EXTERNAL_ACCOUNT = 'mig_ext_account';
14  const MIG_TRIGGER_AUTHMODE = 'mig_trigger_auth_mode';
15  const MIG_DESIRED_AUTHMODE = 'mig_desired_auth_mode';
16 
17  private $logger = null;
18  private $credentials = null;
19  private $status = null;
20  private $providers = array();
21  private $auth_session = null;
22 
23  private $authenticated = false;
24 
31  {
32  $this->logger = ilLoggerFactory::getLogger('auth');
33 
34  $this->auth_session = $session;
35  $this->credentials = $credentials;
36  $this->status = $status;
37  $this->providers = $providers;
38  }
39 
44  public function getAuthSession()
45  {
46  return $this->auth_session;
47  }
48 
53  public function getCredentials()
54  {
55  return $this->credentials;
56  }
57 
62  public function getProviders()
63  {
64  return $this->providers;
65  }
66 
70  public function getStatus()
71  {
72  return $this->status;
73  }
74 
78  public function resetStatus()
79  {
80  $this->getStatus()->setStatus(ilAuthStatus::STATUS_UNDEFINED);
81  $this->getStatus()->setReason('');
82  $this->getStatus()->setAuthenticatedUserId(0);
83  }
84 
89  public function getLogger()
90  {
91  return $this->logger;
92  }
93 
103  {
104  if (!$session->isAuthenticated()) {
105  $this->getLogger()->warning('Desired user account is not authenticated');
106  return false;
107  }
108  include_once './Services/Object/classes/class.ilObjectFactory.php';
109  $user_factory = new ilObjectFactory();
110  $user = $user_factory->getInstanceByObjId($session->getUserId(), false);
111 
112  if (!$user instanceof ilObjUser) {
113  $this->getLogger()->info('Cannot instantiate user account for account migration: ' . $session->getUserId());
114  return false;
115  }
116 
117  $user->setAuthMode(ilSession::get(static::MIG_DESIRED_AUTHMODE));
118 
119  $this->getLogger()->debug('new auth mode is: ' . ilSession::get(self::MIG_DESIRED_AUTHMODE));
120 
121  $user->setExternalAccount(ilSession::get(static::MIG_EXTERNAL_ACCOUNT));
122  $user->update();
123 
124  foreach ($this->getProviders() as $provider) {
125  if (!$provider instanceof ilAuthProviderAccountMigrationInterface) {
126  $this->logger->warning('Provider: ' . get_class($provider) . ' does not support account migration.');
127  throw new InvalidArgumentException('Invalid auth provider given.');
128  }
129  $this->getCredentials()->setUsername(ilSession::get(static::MIG_EXTERNAL_ACCOUNT));
130  $provider->migrateAccount($this->getStatus());
131  switch ($this->getStatus()->getStatus()) {
133  return $this->handleAuthenticationSuccess($provider);
134 
135  }
136  }
137  return $this->handleAuthenticationFail();
138  }
139 
143  public function migrateAccountNew()
144  {
145  foreach ($this->providers as $provider) {
146  if (!$provider instanceof ilAuthProviderAccountMigrationInterface) {
147  $this->logger->warning('Provider: ' . get_class($provider) . ' does not support account migration.');
148  throw new InvalidArgumentException('Invalid auth provider given.');
149  }
150  $provider->createNewAccount($this->getStatus());
151 
152  switch ($this->getStatus()->getStatus()) {
154  return $this->handleAuthenticationSuccess($provider);
155 
156  }
157  }
158  return $this->handleAuthenticationFail();
159  }
160 
161 
162 
166  public function authenticate()
167  {
168  foreach ($this->getProviders() as $provider) {
169  $this->resetStatus();
170 
171  $this->getLogger()->debug('Trying authentication against: ' . get_class($provider));
172 
173  $provider->doAuthentication($this->getStatus());
174 
175  $this->getLogger()->debug('Authentication user id: ' . $this->getStatus()->getAuthenticatedUserId());
176 
177  switch ($this->getStatus()->getStatus()) {
179  return $this->handleAuthenticationSuccess($provider);
180 
182  $this->getLogger()->notice("Account migration required.");
183  return $this->handleAccountMigration($provider);
184 
186  default:
187  $this->getLogger()->debug('Authentication failed against: ' . get_class($provider));
188  break;
189  }
190  }
191  return $this->handleAuthenticationFail();
192  }
193 
199  {
200  $this->getLogger()->debug('Trigger auth mode: ' . $provider->getTriggerAuthMode());
201  $this->getLogger()->debug('Desired auth mode: ' . $provider->getUserAuthModeName());
202  $this->getLogger()->debug('External account: ' . $provider->getExternalAccountName());
203 
204  $this->getStatus()->setAuthenticatedUserId(ANONYMOUS_USER_ID);
205  #$this->getStatus()->setStatus(ilAuthStatus::STATUS_AUTHENTICATED);
206 
207  ilSession::set(static::MIG_TRIGGER_AUTHMODE, $provider->getTriggerAuthMode());
208  ilSession::set(static::MIG_DESIRED_AUTHMODE, $provider->getUserAuthModeName());
209  ilSession::set(static::MIG_EXTERNAL_ACCOUNT, $provider->getExternalAccountName());
210 
211  $this->getLogger()->dump($_SESSION, ilLogLevel::DEBUG);
212 
213  return true;
214  }
215 
221  {
222  include_once './Services/Object/classes/class.ilObjectFactory.php';
223  $factory = new ilObjectFactory();
224  $user = $factory->getInstanceByObjId($this->getStatus()->getAuthenticatedUserId(), false);
225 
226  // reset expired status
227  $this->getAuthSession()->setExpired(false);
228 
229  if (!$user instanceof ilObjUser) {
230  $this->getLogger()->error('Cannot instantiate user account with id: ' . $this->getStatus()->getAuthenticatedUserId());
232  $this->getStatus()->setAuthenticatedUserId(0);
233  $this->getStatus()->setReason('auth_err_invalid_user_account');
234  return false;
235  }
236 
237  if (!$this->checkExceededLoginAttempts($user)) {
238  $this->getLogger()->info('Authentication failed for inactive user with id and too may login attempts: ' . $this->getStatus()->getAuthenticatedUserId());
240  $this->getStatus()->setAuthenticatedUserId(0);
241  $this->getStatus()->setReason('auth_err_login_attempts_deactivation');
242  return false;
243  }
244 
245  if (!$this->checkActivation($user)) {
246  $this->getLogger()->info('Authentication failed for inactive user with id: ' . $this->getStatus()->getAuthenticatedUserId());
248  $this->getStatus()->setAuthenticatedUserId(0);
249  $this->getStatus()->setReason('err_inactive');
250  return false;
251  }
252 
253  // time limit
254  if (!$this->checkTimeLimit($user)) {
255  $this->getLogger()->info('Authentication failed (time limit restriction) for user with id: ' . $this->getStatus()->getAuthenticatedUserId());
256 
257  if ($GLOBALS['DIC']['ilSetting']->get('user_reactivate_code')) {
258  $this->getLogger()->debug('Accout reactivation codes are active');
260  } else {
261  $this->getLogger()->debug('Accout reactivation codes are inactive');
263  $this->getStatus()->setAuthenticatedUserId(0);
264  }
265  $this->getStatus()->setReason('time_limit_reached');
266  return false;
267  }
268 
269  // ip check
270  if (!$this->checkIp($user)) {
271  $this->getLogger()->info('Authentication failed (wrong ip) for user with id: ' . $this->getStatus()->getAuthenticatedUserId());
273  $this->getStatus()->setAuthenticatedUserId(0);
274 
275  $this->getStatus()->setTranslatedReason(
276  sprintf(
277  $GLOBALS['DIC']->language()->txt('wrong_ip_detected'),
278  $_SERVER['REMOTE_ADDR']
279  )
280  );
281  return false;
282  }
283 
284  // check simultaneos logins
285  $this->getLogger()->debug('Check simutaneous login');
286  if (!$this->checkSimultaneousLogins($user)) {
287  $this->getLogger()->info('Authentication failed: simultaneous logins forbidden for user: ' . $this->getStatus()->getAuthenticatedUserId());
289  $this->getStatus()->setAuthenticatedUserId(0);
290  $this->getStatus()->setReason('simultaneous_login_detected');
291  return false;
292  }
293 
294  // check if profile is complete
295  include_once "Services/User/classes/class.ilUserProfile.php";
296  include_once './Services/Context/classes/class.ilContext.php';
297  if (
301  ) {
302  ilLoggerFactory::getLogger('auth')->info('User profile is incomplete.');
303  $user->setProfileIncomplete(true);
304  $user->update();
305  }
306 
307  // redirects in case of error (session pool limit reached)
309 
310 
311  // @todo move to event handling
312  include_once 'Services/Tracking/classes/class.ilOnlineTracking.php';
313  ilOnlineTracking::addUser($user->getId());
314 
315  // @todo move to event handling
316  include_once 'Modules/Forum/classes/class.ilObjForum.php';
318 
319  require_once 'Services/PrivacySecurity/classes/class.ilSecuritySettings.php';
320  $security_settings = ilSecuritySettings::_getInstance();
321 
322  // determine first login of user for setting an indicator
323  // which still is available in PersonalDesktop, Repository, ...
324  // (last login date is set to current date in next step)
325  if (
326  $security_settings->isPasswordChangeOnFirstLoginEnabled() &&
327  $user->getLastLogin() == null
328  ) {
329  $user->resetLastPasswordChange();
330  }
331  $user->refreshLogin();
332 
333  // reset counter for failed logins
335 
336 
337  $this->getLogger()->info('Successfully authenticated: ' . ilObjUser::_lookupLogin($this->getStatus()->getAuthenticatedUserId()));
338  $this->getAuthSession()->setAuthenticated(true, $this->getStatus()->getAuthenticatedUserId());
339 
340  include_once './Services/Init/classes/class.ilInitialisation.php';
341  ilInitialisation::initUserAccount();
342 
343  ilSession::set('orig_request_target', '');
344  $user->hasToAcceptTermsOfServiceInSession(true);
345 
346 
347  // --- anonymous/registered user
348  $this->getLogger()->info(
349  'logged in as ' . $user->getLogin() .
350  ', remote:' . $_SERVER['REMOTE_ADDR'] . ':' . $_SERVER['REMOTE_PORT'] .
351  ', server:' . $_SERVER['SERVER_ADDR'] . ':' . $_SERVER['SERVER_PORT']
352  );
353 
354  // finally raise event
355  global $DIC;
356 
357  $ilAppEventHandler = $DIC['ilAppEventHandler'];
358  $ilAppEventHandler->raise(
359  'Services/Authentication',
360  'afterLogin',
361  array(
362  'username' => $user->getLogin())
363  );
364 
365  return true;
366  }
367 
372  protected function checkActivation(ilObjUser $user)
373  {
374  return $user->getActive();
375  }
376 
382  {
383  if (in_array($user->getId(), array(ANONYMOUS_USER_ID))) {
384  return true;
385  }
386 
387  $isInactive = !$user->getActive();
388  if (!$isInactive) {
389  return true;
390  }
391 
392  require_once 'Services/PrivacySecurity/classes/class.ilSecuritySettings.php';
393  $security = ilSecuritySettings::_getInstance();
394  $maxLoginAttempts = $security->getLoginMaxAttempts();
395 
396  if (!(int) $maxLoginAttempts) {
397  return true;
398  }
399 
400  $numLoginAttempts = \ilObjUser::_getLoginAttempts($user->getId());
401 
402  return $numLoginAttempts < $maxLoginAttempts;
403  }
404 
410  protected function checkTimeLimit(ilObjUser $user)
411  {
412  return $user->checkTimeLimit();
413  }
414 
418  protected function checkIp(ilObjUser $user)
419  {
420  $clientip = $user->getClientIP();
421  if (trim($clientip) != "") {
422  $clientip = preg_replace("/[^0-9.?*,:]+/", "", $clientip);
423  $clientip = str_replace(".", "\\.", $clientip);
424  $clientip = str_replace(array("?","*",","), array("[0-9]","[0-9]*","|"), $clientip);
425 
426  ilLoggerFactory::getLogger('auth')->debug('Check ip ' . $clientip . ' against ' . $_SERVER['REMOTE_ADDR']);
427 
428  if (!preg_match("/^" . $clientip . "$/", $_SERVER["REMOTE_ADDR"])) {
429  return false;
430  }
431  }
432  return true;
433  }
434 
440  {
441  $this->getLogger()->debug('Setting prevent simultaneous session is: ' . (string) $GLOBALS['DIC']['ilSetting']->get('ps_prevent_simultaneous_logins'));
442  if (
443  $GLOBALS['DIC']['ilSetting']->get('ps_prevent_simultaneous_logins') &&
444  ilObjUser::hasActiveSession($user->getId(), $this->getAuthSession()->getId())
445  ) {
446  return false;
447  }
448  return true;
449  }
450 
454  protected function handleAuthenticationFail()
455  {
456  $this->getLogger()->debug('Authentication failed for all authentication methods.');
457 
458  $user_id = ilObjUser::_lookupId($this->getCredentials()->getUsername());
459  if (!in_array($user_id, array(ANONYMOUS_USER_ID))) {
461  $login_attempts = ilObjUser::_getLoginAttempts($user_id);
462 
463  $this->getLogger()->notice('Increased login attempts for user: ' . $this->getCredentials()->getUsername());
464 
465  include_once './Services/PrivacySecurity/classes/class.ilSecuritySettings.php';
466  $security = ilSecuritySettings::_getInstance();
467  $max_attempts = $security->getLoginMaxAttempts();
468 
469  if ((int) $max_attempts && $login_attempts >= $max_attempts) {
470  $this->getStatus()->setReason('auth_err_login_attempts_deactivation');
471  $this->getLogger()->warning('User account set to inactive due to exceeded login attempts.');
472  ilObjUser::_setUserInactive($user_id);
473  }
474  }
475  }
476 }
static _lookupLogin($a_user_id)
lookup login
static isProfileIncomplete($a_user, $a_include_udf=true, $a_personal_data_only=true)
Check if all required personal data fields are set.
migrateAccount(ilAuthSession $session)
Migrate Account to existing user account.
if((!isset($_SERVER['DOCUMENT_ROOT'])) OR(empty($_SERVER['DOCUMENT_ROOT']))) $_SERVER['DOCUMENT_ROOT']
Class ilObjectFactory.
getProviders()
Get providers.
getActive()
get user active state public
checkIp(ilObjUser $user)
Check ip.
Interface of auth credentials.
$_SESSION["AccountId"]
Description of class class.
static hasActiveSession($a_user_id, $a_session_id)
Check for simultaneous login.
global $DIC
Definition: saml.php:7
checkExceededLoginAttempts(\ilObjUser $user)
const STATUS_AUTHENTICATION_FAILED
handleAuthenticationSuccess(ilAuthProviderInterface $provider)
Handle successful authentication.
$session
static _incrementLoginAttempts($a_usr_id)
$factory
Definition: metadata.php:43
static get($a_var)
Get a value.
checkSimultaneousLogins(ilObjUser $user)
Check simultaneous logins.
static set($a_var, $a_val)
Set a value.
const CONTEXT_LTI_PROVIDER
isAuthenticated()
Check if session is authenticated.
static _lookupId($a_user_str)
Lookup id by login.
handleAccountMigration(ilAuthProviderAccountMigrationInterface $provider)
Handle account migration.
resetStatus()
Reset status.
static _resetLoginAttempts($a_usr_id)
getCredentials()
Get auth credentials.
static _getLoginAttempts($a_usr_id)
getLogger()
Get logger.
migrateAccountNew()
Create new user account.
getUserId()
Get authenticated user id.
Standard interface for auth provider implementations.
authenticate()
Try to authenticate user.
checkTimeLimit(ilObjUser $user)
Check time limit.
handleAuthenticationFail()
Handle failed authenication.
getId()
get object id public
checkActivation(ilObjUser $user)
Check activation.
getTriggerAuthMode()
Get auth mode which triggered the account migration 2_1 for ldap account migration with server id 1 1...
static _updateOldAccess($a_usr_id)
$user
Definition: migrateto20.php:57
static _setUserInactive($a_usr_id)
const STATUS_CODE_ACTIVATION_REQUIRED
__construct(ilAuthSession $session, ilAuthStatus $status, ilAuthCredentials $credentials, array $providers)
Constructor.
static getLogger($a_component_id)
Get component logger.
static getType()
Get context type.
getAuthSession()
Get auth session.
getClientIP()
get client ip number public
static handleLoginEvent($a_login, ilAuthSession $auth_session)
when current session is allowed to be created it marks it with type regarding to the sessions user co...
getExternalAccountName()
Get external account name.
Auth status implementation.
static _getInstance()
Get instance of ilSecuritySettings.
const STATUS_ACCOUNT_MIGRATION_REQUIRED
getUserAuthModeName()
Get user auth mode name ldap_1 for ldap account migration with server id 1 apache for apache auth...
$GLOBALS['JPEG_Segment_Names']
Global Variable: XMP_tag_captions.