Jakmile jsem začal používat Zend Framework, vyvstala potřeba autentizace a autorizace uživatelů. U jednoduchých systémů (např. Tomto blogu) jsou všichni uživatelé aktivní a je jim umožněno přihlášení. Postupem času jsem ale narazil na nutnost mít v systému uživatele, kterým ale přihlášení nebude umožněno.
Nikde jsem nenašel zmínku o přímé podpoře v Zend_Auth, tak jsem si ji jednoduše připsal. Celý fígl je v tom, že u uživatele krom klasického loginu a hesla uchovávám ještě příznak povolení. Do dotazu pro výběr uživatele se pak přidá filtr podle tohoto příznaku. Já si na to napsal následující jednoduchý adaptér:
<?php
/**
* Podpora pro Zakazane a povolene uzivatele v Zend_Auth
*
* Obcas je potreba, aby system dokazal odlisit nejen existujici/neexistujici uzivatele
* ale zaroven i povolene/zakazane uzivatele. Jelikoz to neumi zakladni Zend_Auth, musel
* jsem jej takto rozsirit. Rozhodne se imho jedna o lepsi opatreni nez s Zend_Acl, akort
* pokud uzivatele maji pouze jednu roli.
*
* @author Ondrej Flidr, Sniper's Softworks
* @version 1.0
* @copyright Sniper's Softworks, 2008
*/
class SS_Auth_Adapter_DbTableWithEnabled extends Zend_Auth_Adapter_DbTable {
/**
* Sloupec s priznakem, zda je dany zaznam aktivni
*
* @var string
*/
protected $_enabledColumn = null;
/**
* Hodnota, ktera znamena, ze dany zaznam je aktivni. Vychozi je pgSQL true
*
* @var string
*/
protected $_enabledValue = "t";
/**
* __construct() - Sets configuration options
*
* Mirne upraveny konstruktor rodice
*
* @param Zend_Db_Adapter_Abstract $zendDb
* @param string $tableName
* @param string $identityColumn
* @param string $credentialColumn
* @param string $credentialTreatment
* @param string $enabledColumn
* @param string $enabledValue
* @return void
*/
public function __construct(Zend_Db_Adapter_Abstract $zendDb, $tableName = null, $identityColumn = null,
$credentialColumn = null, $credentialTreatment = null, $enabledColumn = null,
$enabledValue = null)
{
$this->_zendDb = $zendDb;
if (null !== $tableName) {
$this->setTableName($tableName);
}
if (null !== $identityColumn) {
$this->setIdentityColumn($identityColumn);
}
if (null !== $credentialColumn) {
$this->setCredentialColumn($credentialColumn);
}
if (null !== $credentialTreatment) {
$this->setCredentialTreatment($credentialTreatment);
}
if (null !== $enabledColumn) {
$this->setEnabledColumn($enabledColumn);
}
if (null !== $enabledValue) {
$this->setEnabledValue($enabledValue);
}
}
/**
* Nastavi hodnotu, ktera znamena, ze dany uzivatel je aktivni/povoleny
* @param string $enabledValue
* @return Honey_Auth_Adapter_DbTableWithEnabled
*/
public function setEnabledValue($enabledValue = "t")
{
$this->_enabledValue = (string)$enabledValue;
return $this;
}
/**
* Nastavi sloupec s priznakem pro povolene/zakazane uzivatele
* @param string $enabledColumn
* @return Honey_Auth_Adapter_DbTableWithEnabled
*/
public function setEnabledColumn($enabledColumn)
{
$this->_enabledColumn = (string)$enabledColumn;
return $this;
}
/**
* _authenticateCreateSelect() - This method creates a Zend_Db_Select object that
* is completely configured to be queried against the database.
*
* Mirne upravene sestavovani selectu z rodice
*
* @return Zend_Db_Select
*/
protected function _authenticateCreateSelect()
{
// build credential expression
if (empty($this->_credentialTreatment) || (strpos($this->_credentialTreatment, "?") === false)) {
$this->_credentialTreatment = '?';
}
$credentialExpression = new Zend_Db_Expr(
'(CASE WHEN ' .
$this->_zendDb->quoteInto(
$this->_zendDb->quoteIdentifier($this->_credentialColumn, true)
. ' = ' . $this->_credentialTreatment, $this->_credential
)
. ' THEN 1 ELSE 0 END) AS '
. $this->_zendDb->quoteIdentifier('zend_auth_credential_match')
);
// get select
$dbSelect = $this->_zendDb->select();
$dbSelect->from($this->_tableName, array('*', $credentialExpression))
->where($this->_zendDb->quoteIdentifier($this->_identityColumn, true) . ' = ?', $this->_identity);
if (!is_null($this->_enabledColumn)) // pokud je nastaven sloupec s enable priznakem, pouzije se. Jinak se adapter chova jako normalni dbTable
$dbSelect->where($this->_zendDb->quoteIdentifier($this->_enabledColumn, true) . ' = ?', $this->_enabledValue);
return $dbSelect;
}
/**
* Abych mohl pouzit dbSelect z teto metody, musim v ni pretizit i authenticate :(
* @return Zend_Auth_Result
*/
public function authenticate() { return parent::authenticate(); }
}
Použití je stejné jako normální Zendí adaptéry.
Jo a abych nezapomněl: PF09 :)