261 lines
7.5 KiB
PHP
261 lines
7.5 KiB
PHP
<?php defined('SYSPATH') or die('No direct access allowed.');
|
|
|
|
/**
|
|
* Kohana ORM LDAP Extension
|
|
*
|
|
* @package Kohana/ORM
|
|
* @author Deon George
|
|
* @copyright (c) 2013 phpLDAPadmin Development Team
|
|
* @license http://dev.phpldapadmin.org/license.html
|
|
*/
|
|
abstract class Kohana_ORM_LDAP extends ORM {
|
|
protected $_disable_wild_select = TRUE;
|
|
protected $_disable_join_table_name = TRUE;
|
|
protected $_primary_key = 'dn';
|
|
protected $_sub_items = array();
|
|
// protected $_db_group = 'default';
|
|
|
|
public function __construct($id = NULL) {
|
|
// We'll process our $id
|
|
parent::__construct(NULL);
|
|
|
|
if (empty($this->_cast_data) AND $id) {
|
|
if (is_array($id)) {
|
|
// Passing an array of column => values
|
|
foreach ($id as $column => $value)
|
|
$this->where($column, '=', $value);
|
|
|
|
$this->limit(1);
|
|
$this->scope('sub');
|
|
$this->find();
|
|
|
|
} else {
|
|
// Passing the primary key
|
|
$this->base($id)->find();
|
|
}
|
|
}
|
|
}
|
|
|
|
public function __get($column) {
|
|
$x = parent::__get($column);
|
|
|
|
return (! is_object($x) AND is_object(LDAP::factory('schema')->schema()->attribute($column)) AND LDAP::factory('schema')->schema()->attribute($column)->getIsSingleValue()) ? $x[0] : $x;
|
|
}
|
|
|
|
/**
|
|
* Initializes the Database Builder to given query type
|
|
*
|
|
* @param integer $type Type of Database query
|
|
* @return ORM
|
|
*/
|
|
protected function _build($type) {
|
|
// Construct new builder object based on query type
|
|
switch ($type) {
|
|
case Database::SELECT:
|
|
$this->_db_builder = new Database_LDAP_Search($this->_db,NULL);
|
|
break;
|
|
|
|
default:
|
|
throw HTTP_Exception::factory(501,'Unknown type :type',array(':type'=>$type));
|
|
}
|
|
|
|
// Process pending database method calls
|
|
foreach ($this->_db_pending as $method) {
|
|
$name = $method['name'];
|
|
$args = $method['args'];
|
|
|
|
$this->_db_applied[$name] = $name;
|
|
|
|
call_user_func_array(array($this->_db_builder, $name), $args);
|
|
}
|
|
|
|
return $this;
|
|
}
|
|
|
|
protected function _initialize() {
|
|
parent::_initialize();
|
|
|
|
// Check if this model has already been initialized
|
|
if ($init = Arr::get(ORM::$_init_cache, $this->_object_name, FALSE)) {
|
|
|
|
// We need to make sure that our _db is an LDAP DB source.
|
|
if ( ! is_object($this->_db) OR ! $this->_db instanceof LDAP) {
|
|
// Get database instance
|
|
$init['_db'] = LDAP::factory('user',NULL,$this->_db_group);
|
|
}
|
|
|
|
ORM::$_init_cache[$this->_object_name] = $init;
|
|
$this->_db = $init['_db'];
|
|
}
|
|
}
|
|
|
|
// During authentication, is this user activated
|
|
// @todo This should probably query a group membership, etc
|
|
public function activated() {
|
|
return TRUE;
|
|
}
|
|
|
|
public function base($value) {
|
|
// Add pending database call which is executed after query type is determined
|
|
$this->_db_pending[] = array(
|
|
'name' => 'base',
|
|
'args' => array(array($value)),
|
|
);
|
|
|
|
return $this;
|
|
}
|
|
|
|
/**
|
|
* Handles getting of column
|
|
* We override Kohana's get() to allow for LDAP symantics.
|
|
*
|
|
* @param string $column Column name
|
|
* @throws Kohana_Exception
|
|
* @return mixed
|
|
*/
|
|
public function get($column)
|
|
{
|
|
if (array_key_exists($column, $this->_object))
|
|
{
|
|
return (in_array($column, $this->_serialize_columns))
|
|
? $this->_unserialize_value($this->_object[$column])
|
|
: $this->_object[$column];
|
|
}
|
|
elseif (isset($this->_related[$column]))
|
|
{
|
|
// Return related model that has already been fetched
|
|
return $this->_related[$column];
|
|
}
|
|
elseif (isset($this->_belongs_to[$column]))
|
|
{
|
|
$model = $this->_related($column);
|
|
|
|
// Use this model's column and foreign model's primary key
|
|
$col = ($this->_disable_join_table_name ? '' : $model->_object_name.'.').$model->_primary_key;
|
|
$val = $this->_object[$this->_belongs_to[$column]['foreign_key']];
|
|
|
|
// Make sure we don't run WHERE "AUTO_INCREMENT column" = NULL queries. This would
|
|
// return the last inserted record instead of an empty result.
|
|
// See: http://mysql.localhost.net.ar/doc/refman/5.1/en/server-session-variables.html#sysvar_sql_auto_is_null
|
|
if ($val !== NULL)
|
|
{
|
|
$model->where($col, '=', $val)->find();
|
|
}
|
|
|
|
return $this->_related[$column] = $model;
|
|
}
|
|
elseif (isset($this->_has_one[$column]))
|
|
{
|
|
$model = $this->_related($column);
|
|
|
|
if (! is_array($this->_has_one[$column]['foreign_key']))
|
|
{
|
|
// Use this model's primary key value and foreign model's column
|
|
$col = ($this->_disable_join_table_name ? '' : $model->_object_name.'.').$this->_has_one[$column]['foreign_key'];
|
|
$val = $this->_object[$this->_has_one[$column]['far_key']];
|
|
$val = array_pop($val);
|
|
}
|
|
else
|
|
{
|
|
foreach ($this->_has_one[$column]['foreign_key'] as $fk)
|
|
{
|
|
// Simple has_many relationship, search where target model's foreign key is this model's primary key
|
|
$col = ($this->_disable_join_table_name ? '' : $model->_object_name.'.').$fk;
|
|
$val = $this->_object[$fk];
|
|
|
|
$model = $model->where($col, '=', $val);
|
|
}
|
|
}
|
|
|
|
if ($col == 'dn' AND $val)
|
|
$model->base($val)->find();
|
|
else
|
|
$model->where($col, '=', $val)->find();
|
|
|
|
return $this->_related[$column] = $model;
|
|
}
|
|
elseif (isset($this->_has_many[$column]))
|
|
{
|
|
$model = ORM::factory($this->_has_many[$column]['model']);
|
|
|
|
if (! is_array($this->_has_many[$column]['foreign_key']))
|
|
{
|
|
if (isset($this->_has_many[$column]['through']))
|
|
{
|
|
// Grab has_many "through" relationship table
|
|
$through = $this->_has_many[$column]['through'];
|
|
|
|
// Join on through model's target foreign key (far_key) and target model's primary key
|
|
$join_col1 = ($this->_disable_join_table_name ? '' : $through.'.').$this->_has_many[$column]['far_key'];
|
|
$join_col2 = ($this->_disable_join_table_name ? '' : $model->_object_name.'.').$model->_primary_key;
|
|
|
|
$model->join($through)->on($join_col1, '=', $join_col2)
|
|
->on(($this->_disable_join_table_name ? '' : $through.'.').'site_id', '=', ($this->_disable_join_table_name ? '' : $model->_object_name.'.').'site_id');
|
|
|
|
// Through table's source foreign key (foreign_key) should be this model's primary key
|
|
$col = ($this->_disable_join_table_name ? '' : $through.'.').$this->_has_many[$column]['foreign_key'];
|
|
$val = $this->pk();
|
|
}
|
|
else
|
|
{
|
|
// Simple has_many relationship, search where target model's foreign key is this model's primary key
|
|
$col = ($this->_disable_join_table_name ? '' : $model->_object_name.'.').$this->_has_many[$column]['foreign_key'];
|
|
$val = $this->_object[$this->_has_many[$column]['far_key']];
|
|
}
|
|
|
|
return $model->where($col, '=', $val);
|
|
}
|
|
else
|
|
{
|
|
foreach ($this->_has_many[$column]['foreign_key'] as $mk => $fk)
|
|
{
|
|
if (isset($this->_has_many[$column]['through']))
|
|
{
|
|
throw new Kohana_Exception('This code hasnt been written yet!');
|
|
}
|
|
else
|
|
{
|
|
// Simple has_many relationship, search where target model's foreign key is this model's primary key
|
|
$col = ($this->_disable_join_table_name ? '' : $model->_object_name.'.').$fk;
|
|
$val = $this->_object[$mk];
|
|
}
|
|
|
|
$model = $model->where($col, '=', $val);
|
|
}
|
|
|
|
return $model;
|
|
}
|
|
}
|
|
else
|
|
{
|
|
// The item doesnt exist.
|
|
return NULL;
|
|
}
|
|
}
|
|
|
|
public function result_load_values(array $values) {
|
|
$this->clear();
|
|
$this->_load_values($values);
|
|
|
|
return $this;
|
|
}
|
|
|
|
// @todo Taken into account the schema definition
|
|
public function resolve($key) {
|
|
eval("\$x = \$this->get_first('$key');");
|
|
|
|
return $x;
|
|
}
|
|
|
|
public function scope($scope) {
|
|
// Add pending database call which is executed after query type is determined
|
|
$this->_db_pending[] = array(
|
|
'name' => 'scope',
|
|
'args' => array($scope),
|
|
);
|
|
|
|
return $this;
|
|
}
|
|
}
|
|
?>
|