// 1 when authenticated, 0 when not
public $loggedin = 0;
public $password; // not the actual password, but rather a MD5 hash
+ private $algorism = 'md5';
public $cookiekey; // value that should also be in the client cookie to allow authentication
public $canlogin = 0; // (either 0 or 1)
public $notes;
public $autosave = 1; // if the member use the autosave draft function
+ private $locale = '';
- /*
- * NOTE: $locale value obsoleted $language value since version 4.0
- */
+ /* NOTE: $locale value obsoleted $language value since version 4.0 */
public $language = '';
- public $locale = '';
/**
+ * MEMBER::__construct()
* Constructor for a member object
- */
- public function MEMBER()
+ *
+ * @param Void
+ * @return Void
+ *
+ */
+ public function __construct()
{
- // do nothing
+ /* secure cookie key settings (either 'none', 0, 8, 16, 24, or 32) */
+ if ( !array_key_exists('secureCookieKey', $CONF) )
+ {
+ $CONF['secureCookieKey'] = 24;
+ }
+
+ switch( $CONF['secureCookieKey'] )
+ {
+ case 8:
+ $CONF['secureCookieKeyIP'] = preg_replace('/\.[0-9]+\.[0-9]+\.[0-9]+$/','',serverVar('REMOTE_ADDR'));
+ break;
+ case 16:
+ $CONF['secureCookieKeyIP'] = preg_replace('/\.[0-9]+\.[0-9]+$/','',serverVar('REMOTE_ADDR'));
+ break;
+ case 24:
+ $CONF['secureCookieKeyIP'] = preg_replace('/\.[0-9]+$/','',serverVar('REMOTE_ADDR'));
+ break;
+ case 32:
+ $CONF['secureCookieKeyIP'] = serverVar('REMOTE_ADDR');
+ break;
+ default:
+ $CONF['secureCookieKeyIP'] = '';
+ }
+
return;
}
-
+
/**
+ * MEMBER::createFromName()
* Create a member object for a given displayname
*
- * @static
- */
+ * @static
+ * @param String $displayname login name
+ * @return Object member object
+ *
+ */
public static function &createFromName($displayname)
{
$mem = new MEMBER();
}
/**
+ * MEMBER::createFromID()
* Create a member object for a given ID
*
* @static
+ * @param Integer $id id for member
*/
public static function &createFromID($id)
{
return $mem;
}
+ /**
+ * MEMBER::readFromName()
+ * Read member table in database
+ *
+ * @param String $displayname login name
+ * @return Object SQL resource
+ *
+ */
public function readFromName($displayname)
{
return $this->read("mname='".sql_real_escape_string($displayname)."'");
}
+ /**
+ * MEMBER::readFromID()
+ * Read member table in database
+ *
+ * @param Integer $id id for member
+ * @return Object SQL resource
+ *
+ */
public function readFromID($id)
{
return $this->read("mnumber=" . intval($id));
}
- /*
+ /**
+ * MEMBER::hash()
+ * hash the target string
+ *
+ * @param String $string target string
+ * @return Void hashed string
+ */
+ public function hash($string)
+ {
+ switch ( $this->algorism )
+ {
+ case 'md5':
+ default:
+ $string = md5($string);
+ }
+
+ return $string;
+ }
+
+ /**
+ * MEMBER::login()
* Tries to login as a given user.
* Returns true when succeeded, returns false when failed
* 3.40 adds CustomLogin event
+ *
+ * @param String $login login name for member
+ * @param String $password password for member
+ * @param Integer $shared whether the user agent is shared or not
+ *
*/
- public function login($login, $password)
+ public function login($login, $password, $shared=1)
{
- global $manager;
+ global $CONF, $errormessage, $manager;
+ /* TODO: validation for $login, $password, $shared */
if ( $login == '' || $password == '' )
{
return 0;
}
+ /* limiting the length of password to avoid hash collision */
+ $password=i18n::substr($password, 0, 40);
$success = 0;
$allowlocal = 1;
{
$this->loggedin = ( $this->readFromName($login) && $this->checkPassword($password) );
}
+
+ /* login failed */
+ if ( !$this->loggedin )
+ {
+ $trimlogin = trim($login);
+ if ( empty($trimlogin) )
+ {
+ $errormessage = "Please enter a username.";
+ }
+ else
+ {
+ $errormessage = 'Login failed for ' . $login;
+ }
+ $manager->notify('LoginFailed', array('username' => $login) );
+ ACTIONLOG::add(INFO, $errormessage);
+ }
+ /* login success */
+ else
+ {
+ $this->newCookieKey();
+ $this->setCookies($shared);
+
+ if ( $CONF['secureCookieKey'] !== 'none' )
+ {
+ /* secure cookie key */
+ $this->setCookieKey($this->hash($this->getCookieKey().$CONF['secureCookieKeyIP']));
+ $this->write();
+ }
+
+ $errormessage = '';
+ $manager->notify('LoginSuccess', array('member' => &$member, 'username' => $login) );
+ ACTIONLOG::add(INFO, "Login successful for $login (sharedpc=$shared)");
+ }
+
return $this->loggedin;
}
- /*
+ /**
+ * MEMBER::cookielogin()
* Login using cookie key
+ *
+ * @param String $login not used
+ * @param String $cookiekey not used
+ * @return Boolean login or not
*/
- public function cookielogin($login, $cookiekey)
+ public function cookielogin($login='', $cookiekey='')
{
- $this->loggedin = ( $this->readFromName($login) && $this->checkCookieKey($cookiekey) );
+ global $CONF, $manager;
+
+ if ( !headers_sent() && cookieVar("{$CONF['CookiePrefix']}user") )
+ {
+ /* Cookie Authentication */
+ $ck = cookieVar("{$CONF['CookiePrefix']}loginkey");
+
+ /* TODO: validation for each cookie values */
+
+ /* limiting the length of password to avoid hash collision */
+ $ck = i18n::substr($ck,0,32);
+ if ( $CONF['secureCookieKey']!=='none' )
+ {
+ $ck = $this->hash("{$ck}{$CONF['secureCookieKeyIP']}");
+ }
+ $this->loggedin = ( $this->readFromName(cookieVar("{$CONF['CookiePrefix']}user")) && $this->checkCookieKey($ck) );
+ unset($ck);
+
+ /* renew cookies when not on a shared computer */
+ if ( $res && (cookieVar($CONF['CookiePrefix'] . 'sharedpc') != 1) )
+ {
+ $member->setCookieKey(cookieVar("{$CONF['CookiePrefix']}loginkey"));
+ $member->setCookies();
+ }
+ }
return $this->loggedin;
}
+ /**
+ * MEMBER::logout()
+ * logout and expire cookie
+ *
+ * @param Void
+ * @return Void
+ */
public function logout()
{
+ global $CONF, $manager;
+
+ if ( !headers_sent() && cookieVar("{$CONF['CookiePrefix']}user") )
+ {
+ /* remove cookies on logout */
+ setcookie("{$CONF['CookiePrefix']}user", '', (time() - 2592000), $CONF['CookiePath'], $CONF['CookieDomain'], $CONF['CookieSecure']);
+ setcookie("{$CONF['CookiePrefix']}loginkey", '', (time() - 2592000), $CONF['CookiePath'], $CONF['CookieDomain'], $CONF['CookieSecure']);
+ $manager->notify('Logout', array('username' => cookieVar("{$CONF['CookiePrefix']}user") ) );
+ }
+
$this->loggedin = 0;
return;
}
+ /**
+ * MEMBER::isLoggedIn()
+ * return member is loggedin or not
+ *
+ * @param Void
+ * @return Void
+ */
public function isLoggedIn()
{
return $this->loggedin;
}
- /*
+ /**
+ * MEMBER:read()
* Read member information from the database
+ *
+ * @param String $where where statement
+ * @return Resource SQL resource
+ *
*/
- public function read($where) {
+ public function read($where)
+ {
// read info
$query = 'SELECT * FROM '.sql_table('member') . ' WHERE ' . $where;
return sql_num_rows($res);
}
- /*
+ /**
+ * MEMBER::isBlogAdmin()
* Returns true if member is an admin for the given blog
* (returns false if not a team member)
+ *
+ * @param Integer $blogid weblog id
+ * @return Integer weblog admin or not
+ *
*/
public function isBlogAdmin($blogid)
{
public function checkPassword($pw)
{
- return (md5($pw) == $this->getPassword());
+ return ($this->hash($pw) == $this->getPassword());
}
public function getRealName()
public function setPassword($pwd)
{
- $this->password = md5($pwd);
+ $this->password = $this->hash($pwd);
}
public function getCookieKey()
public function newCookieKey()
{
mt_srand( (double) microtime() * 1000000);
- $this->cookiekey = md5(uniqid(mt_rand()));
+ $this->cookiekey = $this->hash(uniqid(mt_rand()));
$this->write();
return $this->cookiekey;
}
$name = sql_real_escape_string($name);
$realname = sql_real_escape_string($realname);
- $password = sql_real_escape_string(md5($password));
+ $password = sql_real_escape_string($this->hash($password));
$email = sql_real_escape_string($email);
$url = sql_real_escape_string($url);
$admin = intval($admin);
{
// generate a random key
srand((double)microtime()*1000000);
- $key = md5(uniqid(rand(), true));
+ $key = $this->hash(uniqid(rand(), true));
// attempt to add entry in database
// add in database as non-active
*/
/*
- * NOTE: this should be removed when releasing 4.0
- * switch URLMode back to normal when $CONF['Self'] ends in .php
- * this avoids urls like index.php/item/13/index.php/item/15
-if (!isset($CONF['URLMode']) || (($CONF['URLMode'] == 'pathinfo') && (substr($CONF['Self'], strlen($CONF['Self']) - 4) == '.php'))) {
- $CONF['URLMode'] = 'normal';
-}*/
-
-/*
* Set these to 1 to allow viewing of future items or draft items
* Should really never do this, but can be useful for some plugins that might need to
* Could cause some other issues if you use future posts otr drafts
*switch URLMode back to normal when $CONF['Self'] ends in .php
* this avoids urls like index.php/item/13/index.php/item/15
*/
-if ( !array_key_exists('URLMode', $CONF)
- || (($CONF['URLMode'] == 'pathinfo')
+if ( !array_key_exists('URLMode', $CONF) || (($CONF['URLMode'] == 'pathinfo')
&& (i18n::substr($CONF['Self'], i18n::strlen($CONF['Self']) - 4) == '.php')) )
{
$CONF['URLMode'] = 'normal';
$CONF['DisableJsTools'] = 2;
}
-/* login if cookies set*/
$member = new MEMBER();
-/* secure cookie key settings (either 'none', 0, 8, 16, 24, or 32) */
-if ( !array_key_exists('secureCookieKey', $CONF) )
-{
- $CONF['secureCookieKey'] = 24;
-}
-switch( $CONF['secureCookieKey'] )
-{
- case 8:
- $CONF['secureCookieKeyIP'] = preg_replace('/\.[0-9]+\.[0-9]+\.[0-9]+$/','',serverVar('REMOTE_ADDR'));
- break;
- case 16:
- $CONF['secureCookieKeyIP'] = preg_replace('/\.[0-9]+\.[0-9]+$/','',serverVar('REMOTE_ADDR'));
- break;
- case 24:
- $CONF['secureCookieKeyIP'] = preg_replace('/\.[0-9]+$/','',serverVar('REMOTE_ADDR'));
- break;
- case 32:
- $CONF['secureCookieKeyIP'] = serverVar('REMOTE_ADDR');
- break;
- default:
- $CONF['secureCookieKeyIP'] = '';
-}
-
-/*
- * login/logout when required or renew cookies
- * and decide locale on this session before plugin event generates
- */
if ( $action == 'login' )
{
- /* Form Authentication */
$login = postVar('login');
- $pw = postVar('password');
- /* shared computer or not */
+ $password = postVar('password');
$shared = intPostVar('shared');
- /* avoid md5 collision by using a long key */
- $pw=i18n::substr($pw,0,40);
-
- if ( $member->login($login, $pw) )
- {
- $member->newCookieKey();
- $member->setCookies($shared);
-
- if ( $CONF['secureCookieKey'] !== 'none' )
- {
- /* secure cookie key */
- $member->setCookieKey(md5($member->getCookieKey().$CONF['secureCookieKeyIP']));
- $member->write();
- }
-
- /* allows direct access to parts of the admin area after logging in */
- if ( $nextaction )
- {
- $action = $nextaction;
- }
-
- /* NOTE: include translation file and set locale */
- $locale = include_translation($locale, $member);
- i18n::set_current_locale($locale);
-
- $manager->notify('LoginSuccess', array('member' => &$member, 'username' => $login) );
- $errormessage = '';
- ACTIONLOG::add(INFO, "Login successful for $login (sharedpc=$shared)");
- }
- else
- {
- /* errormessage for [%errordiv%] */
- $trimlogin = trim($login);
- if ( empty($trimlogin) )
- {
- $errormessage = "Please enter a username.";
- }
- else
- {
- $errormessage = 'Login failed for ' . $login;
- }
-
- /* NOTE: include translation file and set locale */
- $locale = include_translation($locale);
- i18n::set_current_locale($locale);
-
- $manager->notify('LoginFailed', array('username' => $login) );
- ACTIONLOG::add(INFO, $errormessage);
- }
+ $member->login($login, $password, $shared);
}
-
-/*
- * TODO: this should be removed when releasing 4.0
-Backed out for now: See http://forum.nucleuscms.org/viewtopic.php?t=3684 for details
-elseif ( serverVar('PHP_AUTH_USER') && serverVar('PHP_AUTH_PW') )
+elseif ( ($action == 'logout') )
{
- // HTTP Authentication
- $login = serverVar('PHP_AUTH_USER');
- $pw = serverVar('PHP_AUTH_PW');
-
- if ( $member->login($login, $pw) )
- {
- $manager->notify('LoginSuccess',array('member' => &$member));
- ACTIONLOG::add(INFO, "HTTP authentication successful for $login");
- }
- else
- {
- $manager->notify('LoginFailed',array('username' => $login));
- ACTIONLOG::add(INFO, 'HTTP authentication failed for ' . $login);
-
- //Since bad credentials, generate an apropriate error page
- header("WWW-Authenticate: Basic realm=\"Nucleus CMS {$nucleus['version']}\"");
- header('HTTP/1.0 401 Unauthorized');
- echo 'Invalid username or password';
- exit;
- }
+ $member->logout();
}
-*/
-
-elseif ( ($action == 'logout')
- && (!headers_sent())
- && cookieVar($CONF['CookiePrefix'] . 'user') )
-{
- /* remove cookies on logout */
- setcookie($CONF['CookiePrefix'] . 'user', '', (time() - 2592000), $CONF['CookiePath'], $CONF['CookieDomain'], $CONF['CookieSecure']);
- setcookie($CONF['CookiePrefix'] . 'loginkey', '', (time() - 2592000), $CONF['CookiePath'], $CONF['CookieDomain'], $CONF['CookieSecure']);
-
- /* NOTE: include translation file and set locale */
- $locale = include_translation($locale);
- i18n::set_current_locale($locale);
-
- $manager->notify('Logout', array('username' => cookieVar($CONF['CookiePrefix'] . 'user') ) );
-}
-elseif ( cookieVar($CONF['CookiePrefix'] . 'user') )
+else
{
- /* Cookie Authentication */
- $ck=cookieVar($CONF['CookiePrefix'] . 'loginkey');
- /*
- * secure cookie key
- * avoid md5 collision by using a long key
- */
- $ck = i18n::substr($ck,0,32);
- if ( $CONF['secureCookieKey']!=='none' )
- {
- $ck = md5($ck.$CONF['secureCookieKeyIP']);
- }
- $res = $member->cookielogin(cookieVar($CONF['CookiePrefix'] . 'user'), $ck );
- unset($ck);
-
- /* renew cookies when not on a shared computer */
- if ( $res
- && (cookieVar($CONF['CookiePrefix'] . 'sharedpc') != 1)
- && (!headers_sent() ) )
- {
- $member->setCookieKey(cookieVar($CONF['CookiePrefix'] . 'loginkey'));
- $member->setCookies();
- }
-
- /* NOTE: include translation file and set locale */
- $locale = include_translation($locale, $member);
- i18n::set_current_locale($locale);
+ $member->cookielogin();
}
-else
+
+/* NOTE: include translation file and set locale */
+if ( $member->isLoggedIn() && !$member->getLocale())
{
- /* NOTE: include translation file and set locale */
- $locale = include_translation($locale);
- i18n::set_current_locale($locale);
+ $locale = $member->getLocale();
}
+include_translation($locale);
+i18n::set_current_locale($locale);
/* login completed */
$manager->notify('PostAuthentication', array('loggedIn' => $member->isLoggedIn() ) );
+/* next action */
+if ( $member->isLoggedIn() && $nextaction )
+{
+ $action = $nextaction;
+}
+
/*
* Release ticket for plugin
*/
}
}
-/*
-Backed out for now: See http://forum.nucleuscms.org/viewtopic.php?t=3684 for details
-
-// To remove after v2.5 is released and translation files have been updated.
-// Including this makes sure that translation files for v2.5beta can still be used for v2.5final
-// without having weird _SETTINGS_EXTAUTH string showing up in the admin area.
-if (!defined('_MEMBERS_BYPASS'))
-{
- define('_SETTINGS_EXTAUTH', 'Enable External Authentication');
- define('_WARNING_EXTAUTH', 'Warning: Enable only if needed.');
- define('_MEMBERS_BYPASS', 'Use External Authentication');
-}
-*/
-
-/* make sure the archivetype skinvar keeps working when _ARCHIVETYPE_XXX not defined */
if ( !defined('_ARCHIVETYPE_MONTH') )
{
define('_ARCHIVETYPE_DAY', 'day');
}
}
}
+
/*
* PostParseURL is a place to cleanup any of the path-related global variables before the selector function is run.
* It has 2 values in the data in case the original virtualpath is needed, but most the use will be in tweaking
/**
* This function decide which locale is used and include translation
* @param string $locale locale name referring to 'language tags' defined in RFC 5646
- * @param mixed $member member object
+ * @return Void
*/
- function include_translation($locale, $member = FALSE)
+ function include_translation($locale)
{
global $DIR_LOCALES;
- /*
- * 1. user's locale is used if set
- * 2. system default is used if it is not empty
- * 3. else 'en_Latn_US.ISO-8859-1.php' is included
- * because this translation file is expected to include only 7bit ASCII characters
- * which common in whole character coding scheme
- */
- if ( $member && $member->getLocale() )
- {
- $locale = $member->getLocale();
- }
$translation_file = $DIR_LOCALES . $locale . '.' . i18n::get_current_charset() . '.php';
if ( !file_exists($translation_file) )
{
$translation_file = $DIR_LOCALES . 'en_Latn_US.ISO-8859-1.php';
}
include($translation_file);
- return $locale;
+ return;
}
/**