Allow multiple type of objects in LSselect & LSattr_html :: select_object and globally rework and improve LSrelation consequently

This commit is contained in:
Benjamin Renard 2020-05-19 17:55:55 +02:00
parent 3cf053cf26
commit e8095636b5
15 changed files with 1829 additions and 662 deletions

View file

@ -42,3 +42,29 @@ div.LSselect_search {
div.LSobject-select {
width: 620px;
}
/*
* Selectable object types tabs
*/
ul.LSselect_selectable_object_types {
list-style-type: none;
padding: 0 0 4px 0;
margin: 1em;
margin-bottom: 0;
border-bottom: 1px solid #52BCE5;
}
ul.LSselect_selectable_object_types li {
color: #fff;
background-color: #52BCE5;
-moz-border-radius: 3px 3px 0px 0px;
border-radius: 3px 3px 0px 0px;
padding: 4px;
display: inline;
margin-right: 1px;
cursor: pointer;
}
ul.LSselect_selectable_object_types li.current {
background-color: #0072B8;
}

View file

@ -54,7 +54,6 @@ class LSattr_html_select_object extends LSattr_html{
$element -> setValue($values);
}
}
$element -> setSelectableObject($this -> getConfig('html_options.selectable_object.object_type'));
return $element;
}
@ -73,146 +72,312 @@ class LSattr_html_select_object extends LSattr_html{
}
/**
* Retourne un tableau des valeurs de l'attribut à partir des valeurs du formulaire
* Check and return selectable objects configuration and eventually instanciate
* it if &instanciate
*
* @param[in] mixed Tableau des valeurs du formulaire
* @param[in] boolean &$instanciated_objects reference If this reference point to an array, each valid
* selectable object type will be instanciated in this
* array with object type name as key.
*
* @author Benjamin Renard <brenard@easter-eggs.com>
*
* @retval array Tableau des valeurs de l'attribut
* @retval array|false Selectable objects configuration or False on error.
*/
public function getValuesFromFormValues($values=NULL) {
$conf = $this -> getConfig('html_options.selectable_object');
if (is_array($conf) && is_array($values)) {
$retValues = array();
public function getSelectableObjectsConfig(&$instanciated_objects) {
$confs = $this -> getConfig('html_options.selectable_object');
if (!is_array($confs)) {
self :: log_debug('getSelectableObjectsConfig(): html_options.selectable_object not properly configured');
return false;
}
// Make sure we have an array or configured selectable objects
if (isset($confs['object_type'])) {
$confs = array($confs);
}
// Return confs
$ret_confs = array();
// For each configured object types:
// - check we have the minimal configuration (object_type & value_attribute)
// - check we to not have multiple conf for the same object type
// - load object type
// - implement an object of this type (if is_array($instanciated_objects))
// - if value are from attributes, check this attribute exists
foreach ($confs as $conf) {
if (!isset($conf['object_type'])) {
LSerror :: addErrorCode('LSattr_html_select_object_01',$this -> name);
return;
LSerror :: addErrorCode(
'LSattr_html_select_object_01',
array(
'attr' => $this -> name,
'parameter' => 'object_type',
)
);
return false;
}
if (!isset($conf['value_attribute'])) {
LSerror :: addErrorCode('LSattr_html_select_object_02',$this -> name);
return;
LSerror :: addErrorCode(
'LSattr_html_select_object_01',
array(
'attr' => $this -> name,
'parameter' => 'value_attribute',
)
);
return false;
}
if (!LSsession :: loadLSobject($conf['object_type'])) {
return;
if (array_key_exists($conf['object_type'], $ret_confs)) {
LSerror :: addErrorCode('LSattr_html_select_object_04', array('type' => $conf['object_type'], 'attr' => $this -> name));
return false;
}
$object_type = $conf['object_type'];
$obj=new $conf['object_type']();
foreach($values as $dn => $name) {
if ($obj -> loadData($dn)) {
$val = '';
if(($conf['value_attribute']=='dn')||($conf['value_attribute']=='%{dn}')) {
$val = $dn;
}
else {
if (!isset($obj->attrs[$conf['value_attribute']])) {
LSerror :: addErrorCode('LSattr_html_select_object_02',$this -> name);
return;
}
$val = $obj -> getValue($conf['value_attribute']);
$val = $val[0];
}
if (empty($val)) {
continue;
}
$retValues[] = $val;
if (!LSsession :: loadLSobject($object_type))
return false;
if (is_array($instanciated_objects))
$instanciated_objects[$object_type] = new $object_type();
if (!($conf['value_attribute']=='dn') && !($conf['value_attribute']=='%{dn}')) {
if (!$object_type :: hasAttr($conf['value_attribute'])) {
LSerror :: addErrorCode(
'LSattr_html_select_object_02',
array(
'attr' => $this -> name,
'object_type' => $conf['object_type'],
'value_attribute' => $conf['value_attribute'],
)
);
return false;
}
}
return $retValues;
// Handle other parameters
$conf['display_name_format'] = LSconfig :: get('display_name_format', null, null, $conf);
$conf['onlyAccessible'] = LSconfig :: get('onlyAccessible', false, 'bool', $conf);
$conf['filter'] = LSconfig :: get('filter', null, null, $conf);
$ret_confs[$object_type] = $conf;
}
return;
return $ret_confs;
}
/**
* Return an array of selected objects with DN as key and as value, an array with object name (key name)
* and type (key object_type).
*
* @param[in] mixed $values array|null Array of the input values ()
* @param[in] boolean $fromDNs boolean If true, considered provided values as DNs (default: false)
* @param[in] boolean $retreiveAttrValues boolean If true, attribute values will be returned instead
* of selected objects info (default: false)
*
* @author Benjamin Renard <brenard@easter-eggs.com>
*
* @retval array|false Array of selected objects with DN as key and object info as value or array
* of attribute values if $retreiveAttrValues==true or False on error.
*/
public function getFormValues($values=NULL, $fromDNs=false, $retreiveAttrValues=false) {
self :: log_debug("getFormValues(): input values=".varDump($values));
// Check parameters consistency
if ($retreiveAttrValues && !$fromDNs) {
self :: log_fatal('getFormValues(): $fromDNs must be true if $retreiveAttrValues==true');
return false;
}
if (!is_array($values)) {
self :: log_warning('getFormValues(): $values is not array');
return false;
}
// Retreive/check selectable objects config
$objs = array();
$confs = $this -> getSelectableObjectsConfig($objs);
if (!is_array($confs) || empty($confs)) {
self :: log_warning('getFormValues(): invalid selectable objects config');
return false;
}
$selected_objects = array();
$unrecognizedValues = array();
$found_values = array();
foreach ($confs as $conf) {
foreach($values as $value) {
// If we already mark its value as unrecognized, pass
if (in_array($value, $unrecognizedValues))
continue;
// Ignore empty value
if (empty($value))
continue;
// Determine value attribute: DN/attribute valued (or force form DNs)
if(($conf['value_attribute']=='dn') || ($conf['value_attribute']=='%{dn}') || $fromDNs) {
// Construct resulting list from DN values
if ($conf['onlyAccessible']) {
if (!LSsession :: canAccess($conf['object_type'], $value)) {
self :: log_debug("getFormValues(): ".$conf['object_type']."($value): not accessible, pass");
continue;
}
}
// Load object data (with custom filter if defined)
if(!$objs[$conf['object_type']] -> loadData($value, $conf['filter'])) {
self :: log_debug("getFormValues(): ".$conf['object_type']."($value): not found, pass");
continue;
}
self :: log_debug("getFormValues(): ".$conf['object_type']."($value): found");
// Check if it's the first this value match with an object
if (isset($found_values[$value])) {
// DN match with multiple object type
LSerror :: addErrorCode('LSattr_html_select_object_03',array('val' => $value, 'attribute' => $this -> name));
$unrecognizedValues[] = $value;
unset($selected_objects[$found_values[$value]]);
break;
}
$found_values[$value] = $value;
if ($retreiveAttrValues) {
// Retreive attribute value case: $selected_objects[dn] = attribute value
if(($conf['value_attribute']=='dn') || ($conf['value_attribute']=='%{dn}')) {
$selected_objects[$value] = $value;
}
else {
$val = $objs[$conf['object_type']] -> getValue($conf['value_attribute']);
if (!empty($val)) {
$selected_objects[$value] = $val[0];
}
else {
LSerror :: addErrorCode(
'LSattr_html_select_object_06',
array(
'name' => $objs[$conf['object_type']] -> getDisplayName($conf['display_name_format']),
'attr' => $this -> name
)
);
}
}
}
else {
// General case: $selected_objects[dn] = array(name + object_type)
$selected_objects[$value] = array(
'name' => $objs[$conf['object_type']] -> getDisplayName($conf['display_name_format']),
'object_type' => $conf['object_type'],
);
self :: log_debug("getFormValues(): ".$conf['object_type']."($value): ".varDump($selected_objects[$value]));
}
}
else {
// Construct resulting list from attributes values
$filter = Net_LDAP2_Filter::create($conf['value_attribute'], 'equals', $value);
if (isset($conf['filter']))
$filter = LSldap::combineFilters('and', array($filter, $conf['filter']));
$sparams = array();
$sparams['onlyAccessible'] = $conf['onlyAccessible'];
$listobj = $objs[$conf['object_type']] -> listObjectsName(
$filter,
NULL,
$sparams,
$conf['display_name_format']
);
if (count($listobj)==1) {
if (isset($found_values[$value])) {
// Value match with multiple object type
LSerror :: addErrorCode('LSattr_html_select_object_03',array('val' => $value, 'attribute' => $this -> name));
$unrecognizedValues[] = $value;
unset($selected_objects[$found_values[$value]]);
break;
}
$dn = key($listobj);
$selected_objects[$dn] = array(
'name' => $listobj[$dn],
'object_type' => $conf['object_type'],
);
$found_values[$value] = $dn;
}
else if(count($listobj) > 1) {
LSerror :: addErrorCode('LSattr_html_select_object_03',array('val' => $value, 'attribute' => $this -> name));
if (!in_array($value, $unrecognizedValues))
$unrecognizedValues[] = $value;
break;
}
}
}
}
// Check if all values have been found (or already considered as unrecognized)
foreach ($values as $value) {
if (!isset($found_values[$value]) && !in_array($value, $unrecognizedValues)) {
self :: log_debug("getFormValues(): value '$value' not recognized");
$unrecognizedValues[] = $value;
}
}
// Retreive attribute values case: return forged array values (list of attribute values)
if ($retreiveAttrValues)
return array_values($selected_objects);
// General case
self :: log_debug("getFormValues(): unrecognizedValues=".varDump($unrecognizedValues));
$this -> unrecognizedValues = $unrecognizedValues;
self :: log_debug("getFormValues(): final values=".varDump($selected_objects));
return $selected_objects;
}
/**
* Retourne un tableau des objects selectionnés
* Get LSselect ID for this attribute
*
* @param[in] mixed $values Tableau des valeurs de l'attribut
* @param[in] boolean $fromDNs True si les valeurs passées en paramètre sont des DNs
* @return string The LSselect ID for this attribute
*/
public function getLSselectId() {
$id = "";
if ($this -> attribute -> ldapObject -> isNew())
$id .= $this -> attribute -> ldapObject -> getType();
else
$id .= $this -> attribute -> ldapObject -> getDn();
$id .= "|".$this -> name;
return $id;
}
/**
* Return array of atttribute values form array of form values
*
* @param[in] mixed Array of form values
*
* @author Benjamin Renard <brenard@easter-eggs.com>
*
* @retval array Tableau associatif des objects selectionés avec en clé
* le DN et en valeur ce qui sera affiché.
* @retval array|false Array of attribute values or False on error.
*/
public function getFormValues($values=NULL, $fromDNs=false) {
$conf = $this -> getConfig('html_options.selectable_object');
if (is_array($conf) && is_array($values)) {
if (!isset($conf['object_type'])) {
LSerror :: addErrorCode('LSattr_html_select_object_01',$this -> name);
return;
}
if (!isset($conf['value_attribute'])) {
LSerror :: addErrorCode('LSattr_html_select_object_02',$this -> name);
return;
}
if (!LSsession :: loadLSobject($conf['object_type'])) {
return;
}
$retInfos = array();
$DNs=array();
$obj = new $conf['object_type']();
if(($conf['value_attribute']=='dn')||($conf['value_attribute']=='%{dn}')||$fromDNs) {
$DNs=$values;
foreach($DNs as $dn) {
if($obj -> loadData($dn)) {
$retInfos[$dn] = $obj -> getDisplayName((isset($conf['display_name_format'])?$conf['display_name_format']:null));
}
}
}
else {
if (!is_array(LSconfig::get('LSobjects.'.$conf['object_type'].'.attrs.'.$conf['value_attribute']))) {
LSerror :: addErrorCode('LSattr_html_select_object_02', $this -> name);
return;
}
$unrecognizedValues=array();
foreach($values as $val) {
if (!empty($val)) {
$filter=Net_LDAP2_Filter::create($conf['value_attribute'],'equals',$val);
if (isset($conf['filter'])) $filter = LSldap::combineFilters('and',array($filter,$conf['filter']));
$sparams=array();
$sparams['onlyAccessible'] = (isset($conf['onlyAccessible'])?$conf['onlyAccessible']:False);
$listobj = $obj -> listObjectsName($filter, NULL, $sparams, (isset($conf['display_name_format'])?$conf['display_name_format']:false));
if (count($listobj)==1) {
foreach($listobj as $dn => $name) {
$DNs[]=$dn;
$retInfos[$dn] = $name;
}
}
else {
$unrecognizedValues[]=$val;
if(count($listobj)>1) {
LSerror :: addErrorCode('LSattr_html_select_object_03',array('val' => $val, 'attribute' => $this -> name));
}
}
}
}
$this -> unrecognizedValues=$unrecognizedValues;
}
$_SESSION['LSselect'][$conf['object_type']] = $DNs;
return $retInfos;
public function getValuesFromFormValues($values=NULL) {
if (is_array($values)) {
return $this -> getFormValues(array_keys($values), true, true);
}
return false;
}
/**
* Retourne un tableau des valeurs de l'attribut à partir de la variable session
* Return an array of selected objects with DN as key and display name as value
* from LSselect
*
* @author Benjamin Renard <brenard@easter-eggs.com>
*
* @retval array Tableau associatif des objects selectionnés avec en clé
* le DN et en valeur ce qui sera affiché.
*/
public function getValuesFromSession() {
$obj_type = $this -> getConfig('html_options.selectable_object.object_type');
if ( $obj_type && is_array($_SESSION['LSselect'][$obj_type]) ) {
return $this -> getFormValues($_SESSION['LSselect'][$obj_type], true);
public function getValuesFromLSselect() {
$LSselect_id = $this -> getLSselectId();
if (LSsession :: loadLSclass('LSselect', null, true) && LSselect :: exists($LSselect_id)) {
$selected_objects = LSselect :: getSelectedObjects($LSselect_id);
self :: log_debug("getValuesFromLSselect(): selected objects retreived from LSselect '$LSselect_id' = ".varDump($selected_objects));
if (is_array($selected_objects)) {
return $this -> getFormValues(
array_keys($selected_objects),
true
);
}
}
return false;
}
@ -234,11 +399,20 @@ class LSattr_html_select_object extends LSattr_html{
* Error Codes
*/
LSerror :: defineError('LSattr_html_select_object_01',
_("LSattr_html_select_object : LSobject type is undefined (attribute : %{attr}).")
_("LSattr_html_select_object : parameter '%{parameter}' is missing (attribute : %{attr}).")
);
LSerror :: defineError('LSattr_html_select_object_02',
_("LSattr_html_select_object : the value of the parameter value_attribute in the configuration of the attribute %{attrs} is incorrect. This attribute does not exists.")
_("LSattr_html_select_object : the value of the parameter value_attribute in the configuration of the attribute %{attrs} is incorrect. Object %{object_type} have no attribute %{value_attribute}.")
);
LSerror :: defineError('LSattr_html_select_object_03',
_("LSattr_html_select_object : more than one object returned corresponding to value %{val} of attribute %{attr}.")
);
LSerror :: defineError('LSattr_html_select_object_04',
_("LSattr_html_select_object : selection of object type %{type} is configured multiple time for attribute %{attr}.")
);
LSerror :: defineError('LSattr_html_select_object_05',
_("LSattr_html_select_object : the value '%{value}' seem to be duplicated in values of the attribute %{attr}.")
);
LSerror :: defineError('LSattr_html_select_object_06',
_("LSattr_html_select_object : selected object %{name} has no attribute %{attr} value, you can't select it.")
);

View file

@ -56,7 +56,7 @@ class LSformElement_select_object extends LSformElement {
public function getDisplay($refresh=NULL){
LSsession :: addCssFile('LSformElement_select_object.css');
if ($refresh) {
$this -> values = $this -> getValuesFromSession();
$this -> values = $this -> getValuesFromLSselect();
}
$return = $this -> getLabelInfos();
@ -64,7 +64,7 @@ class LSformElement_select_object extends LSformElement {
LSsession :: addJSconfigParam(
$this -> name,
array(
'object_type' => $this -> selectableObject,
'LSselect_id' => $this -> attr_html -> getLSselectId(),
'addBtn' => _('Modify'),
'deleteBtns' => _('Delete'),
'up_label' => _('Move up'),
@ -88,23 +88,57 @@ class LSformElement_select_object extends LSformElement {
LSsession :: addJSscript('LSformElement_select_object_field.js');
LSsession :: addJSscript('LSformElement_select_object.js');
if (LSsession :: loadLSclass('LSselect')) {
if (LSsession :: loadLSclass('LSselect') && $this -> initLSselect()) {
LSselect :: loadDependenciesDisplay();
}
}
if ($this -> getParam('html_options.sort', true) && !$this -> getParam('html_options.ordered', false, 'bool')) {
uasort($this -> values,array($this,'_sortTwoValues'));
uasort($this -> values, array($this, '_sortTwoValues'));
}
$return['html'] = $this -> fetchTemplate(NULL,array(
'selectableObject' => $this -> selectableObject,
'unrecognizedValues' => $this -> attr_html -> unrecognizedValues,
'unrecognizedValueLabel' => _("%{value} (unrecognized value)")
));
return $return;
}
/**
* Init LSselect
*
* @retval boolean True if LSselect is initialized, false otherwise
*/
private function initLSselect() {
// Retreive selectable objects configuratio from HTML attr
$objs = null;
$confs = $this -> attr_html -> getSelectableObjectsConfig($objs);
if (!is_array($confs)) {
self :: log_warning($this -> name.": html_options.selectable_object not defined");
return false;
}
// Build selectable objects type list as required by LSselect
$select_conf = array();
foreach ($confs as $obj_type => $conf) {
$select_conf[$obj_type] = array(
'object_type' => $conf['object_type'],
'display_name_format' => $conf['display_name_format'],
'filter' => $conf['filter'],
'onlyAccessible' => $conf['onlyAccessible'],
);
}
// Init LSselect
LSselect :: init(
$this -> attr_html -> getLSselectId(),
$select_conf,
boolval($this -> getParam('multiple', 0, 'int')),
$this -> values
);
return True;
}
/**
* Function use with uasort to sort two values
*
@ -121,26 +155,15 @@ class LSformElement_select_object extends LSformElement {
$dir=1;
}
if ($va == $vb) return 0;
$val = strcoll(strtolower($va), strtolower($vb));
$val = strcoll(strtolower($va['name']), strtolower($vb['name']));
return $val*$dir;
}
/*
* Return the values of the object form the session variable
*/
public function getValuesFromSession() {
return $this -> attr_html -> getValuesFromSession();
}
/**
* Defined the type of object witch is selectionable
*
* @param[in] $object string The type of object
*
* @retval void
**/
public function setSelectableObject($object) {
$this -> selectableObject = $object;
public function getValuesFromLSselect() {
return $this -> attr_html -> getValuesFromLSselect();
}
/**
@ -163,8 +186,10 @@ class LSformElement_select_object extends LSformElement {
* @retval boolean Return True
*/
public function setValueFromPostData($data) {
LSformElement::setValueFromPostData($data);
$this -> values = $this -> attr_html -> refreshForm($this -> values,true);
parent :: setValueFromPostData($data);
self :: log_debug("setValueFromPostData(): input values=".varDump($this -> values));
$this -> values = $this -> attr_html -> refreshForm($this -> values, true);
self :: log_debug("setValueFromPostData(): final values=".varDump($this -> values));
return true;
}
@ -175,33 +200,43 @@ class LSformElement_select_object extends LSformElement {
*
* @retval array(dn -> displayName) Found objects
*/
public function searchAdd ($pattern) {
if ($this -> getParam('html_options.selectable_object')) {
public function searchAdd($pattern) {
$objs = array();
$confs = $this -> attr_html -> getSelectableObjectsConfig($objs);
if (!is_array($confs))
return;
$selectable_objects = array();
foreach($confs as $object_type => $conf) {
$obj_type = $this -> getParam('html_options.selectable_object.object_type');
if (LSsession :: loadLSobject($obj_type)) {
$obj = new $obj_type();
$sparams = array();
$sparams['onlyAccessible'] = $this -> getParam('html_options.selectable_object.onlyAccessible', false, 'bool');
$ret = $obj -> getSelectArray(
$pattern,
NULL,
$this -> getParam('html_options.selectable_object.display_name_format'),
false,
true,
$this -> getParam('html_options.selectable_object.filter'),
$sparams
$sparams = array();
$sparams['onlyAccessible'] = $conf['onlyAccessible'];
$objects = $objs[$object_type] -> getSelectArray(
$pattern,
NULL,
$conf['display_name_format'],
false,
true,
$conf['filter'],
$sparams
);
self :: log_debug($objects);
if (!is_array($objects)) {
self :: log_warning("searchAdd($pattern): error occured looking for matching $object_type objects");
continue;
}
foreach($objects as $dn => $name) {
$selectable_objects[$dn] = array (
'object_type' => $object_type,
'name' => $name,
);
if (is_array($ret)) {
return $ret;
}
}
}
return array();
return $selectable_objects;
}
/**
* This ajax method is used to refresh the value display
* in the form element after the modify window is closed.
* in the form element after the modify LSselect window is closed.
*
* @param[in] $data The address to the array of data witch will be return by the ajax request
*
@ -211,13 +246,15 @@ class LSformElement_select_object extends LSformElement {
if ((isset($_REQUEST['attribute'])) && (isset($_REQUEST['objecttype'])) && (isset($_REQUEST['objectdn'])) && (isset($_REQUEST['idform'])) ) {
if (LSsession ::loadLSobject($_REQUEST['objecttype'])) {
$object = new $_REQUEST['objecttype']();
$form = $object -> getForm($_REQUEST['idform']);
$field=$form -> getElement($_REQUEST['attribute']);
$val = $field -> getValuesFromSession();
if ( $val ) {
$data = array(
'objects' => $val
);
if ($object -> loadData($_REQUEST['objectdn'])) {
$form = $object -> getForm($_REQUEST['idform']);
$field=$form -> getElement($_REQUEST['attribute']);
$val = $field -> getValuesFromLSselect();
if ( $val ) {
$data = array(
'objects' => $val
);
}
}
}
}

View file

@ -79,20 +79,30 @@ class LSldapObject extends LSlog_staticLoggerClass {
}
/**
* Charge les données de l'objet
* Load object data from LDAP
*
* Cette methode définis le DN de l'objet et charge les valeurs de attributs de l'objet
* à partir de l'annuaire.
* This method set object DN and load its data from LDAP
*
* @author Benjamin Renard <brenard@easter-eggs.com>
*
* @param[in] $dn string Le DN de l'objet.
* @param[in] $dn string The object DN
* @param[in] $additional_filter string|Net_LDAP2_Filter|null A custom LDAP filter that LDAP object
* must respect to permit its data loading
*
* @retval boolean true si la chargement a réussi, false sinon.
* @retval boolean True if object data loaded, false otherwise
*/
public function loadData($dn) {
public function loadData($dn, $additional_filter=null) {
$this -> dn = $dn;
$data = LSldap :: getAttrs($dn, $this -> getObjectFilter());
$filter = $this -> getObjectFilter();
if ($additional_filter) {
if (!is_a($additional_filter, Net_LDAP2_Filter))
$additional_filter = Net_LDAP2_Filter :: parse($additional_filter);
$filter = Net_LDAP2_Filter :: combine(
'and',
array ($filter, $additional_filter)
);
}
$data = LSldap :: getAttrs($dn, $filter);
if(is_array($data) && !empty($data)) {
foreach($this -> attrs as $attr_name => $attr) {
if( !$this -> attrs[$attr_name] -> loadData( (isset($data[$attr_name])?$data[$attr_name]:NULL) ) )
@ -1821,6 +1831,18 @@ class LSldapObject extends LSlog_staticLoggerClass {
}
}
/**
* Check if object type have a specified attribute
*
* @param[in] $attr_name string The attribute name
*
* @teval boolean True if object type have a attribute of this name, False otherwise
*/
public static function hasAttr($attr_name) {
return array_key_exists($attr_name, LSconfig :: get('LSobjects.'.get_called_class().'.attrs', array()));
}
/**
* List IOformats of this object type
*

File diff suppressed because it is too large Load diff

View file

@ -190,14 +190,6 @@ class LSsearchEntry extends LSlog_staticLoggerClass {
$this -> LSsearch -> addResultToCache();
return $this -> cache['actions'];
}
elseif ($key=='LSselect') {
if (is_array($_SESSION['LSselect'][$this -> LSobject])) {
if(in_array($this -> dn,$_SESSION['LSselect'][$this -> LSobject])) {
return true;
}
}
return;
}
elseif (is_array($this->LSsearch->extraDisplayedColumns) && array_key_exists($key,$this->LSsearch->extraDisplayedColumns)) {
if(isset($this -> cache[$key])) {
return $this -> cache[$key];

View file

@ -20,7 +20,9 @@
******************************************************************************/
class LSselect {
LSsession :: loadLSclass('LSlog_staticLoggerClass');
class LSselect extends LSlog_staticLoggerClass {
/*
* Méthode chargeant les dépendances d'affichage
@ -35,47 +37,371 @@ class LSselect {
LSsession :: addCssFile('LSselect.css');
}
public static function ajax_addItem(&$data) {
if ((isset($_REQUEST['objecttype'])) && (isset($_REQUEST['objectdn'])) && (isset($_REQUEST['multiple']))) {
if (!$_REQUEST['multiple']) {
$_SESSION['LSselect'][$_REQUEST['objecttype']]=array($_REQUEST['objectdn']);
}
else if (is_array($_SESSION['LSselect'][$_REQUEST['objecttype']])) {
if (!in_array($_REQUEST['objectdn'],$_SESSION['LSselect'][$_REQUEST['objecttype']])) {
$_SESSION['LSselect'][$_REQUEST['objecttype']][]=$_REQUEST['objectdn'];
}
/**
* Init a LSobjects selection
* @param[in] $id string The LSselect ID
* @param[in] $LSobjects array Selectable LSobject types configuration. Must be an array
* with object type as key and configuration as value with the
* following info:
* - object_type: the LSobject type (same as key, required)
* - display_name_format: display name LSformat (optional, default: object type default)
* - filter: LDAP filter string for selectable objects (optional, default: no filter)
* - onlyAccessible: filter on only accessible objects (optional, default: false)
* - editableAttr: attribute name of object that must be writable to the object be selectable (optional)
* @param[in] $multiple boolean True if this selection permit to select more than one object, False otherwise (optional,
* default: false)
* @param[in] $current_selected_objects array|null Array of current selected objects (optional, see setSelectedObjects for format specification)
* @return void
*/
public static function init($id, $LSobjects, $multiple=false, $current_selected_objects=null) {
if ( !isset($_SESSION['LSselect']) || !is_array($_SESSION['LSselect']))
$_SESSION['LSselect'] = array();
$_SESSION['LSselect'][$id] = array (
'LSobjects' => $LSobjects,
'multiple' => $multiple,
'selected_objects' => array(),
);
if (is_array($current_selected_objects))
self :: setSelectedObjects($id, $current_selected_objects);
self :: log_debug("Initialized with id=$id: multiple=".($multiple?'yes':'no')." ".count($_SESSION['LSselect'][$id]['selected_objects'])." selected object(s).");
}
/**
* Check a LSselect exist by ID
*
* @param[in] $id string The LSselect ID
*
* @retval boolean
*/
public static function exists($id) {
if (isset($_SESSION['LSselect']) && is_array($_SESSION['LSselect']) &&
isset($_SESSION['LSselect'][$id]) && is_array($_SESSION['LSselect'][$id]))
return true;
return false;
}
/**
* Return a configuration parameter (or default value)
*
* @param[] $id string The LSselect ID
* @param[] $param string The configuration parameter
* @param[] $default mixed The default value (optional, default : null)
* @param[] $cast Cast string|null resulting value in specific type (optional, default : null=disabled)
*
* @retval mixed The configuration parameter value or default value if not set
**/
public static function getConfig($id, $key, $default=null, $cast=null) {
if (!self :: exists($id))
return false;
return LSconfig :: get($key, $default, $cast, $_SESSION['LSselect'][$id]);
}
/**
* Check if LSselect exist and is multiple
*
* @param[in] $id string The LSselect ID
*
* @retval boolean
*/
public static function isMultiple($id) {
return self :: getConfig($id, 'multiple', false, 'bool');
}
/**
* Get LSsearch object corresponding to the specified selection
*
* @param[in] $id string The LSselect ID
* @param[in] $object_type string|null The object type of the search (optional,
* default: first one object type configured)
*
* @retval LSsearch|false The LSsearch object, or false in case of error
*/
public static function &getSearch($id, $object_type=null) {
// Check parameters
if (!self :: exists($id)) {
self :: log_debug("getSearch($id): does not exists.");
return false;
}
if (is_null($object_type))
$object_type = array_keys($_SESSION['LSselect'][$id]['LSobjects'])[0];
elseif (!array_key_exists($object_type, $_SESSION['LSselect'][$id]['LSobjects'])) {
self :: log_debug("getSearch($id): this selection does not joined '$object_type' objects.");
return false;
}
// Load LSobject type & LSsearch
if ( !LSsession :: loadLSobject($object_type) || !LSsession :: loadLSclass('LSsearch', null, true) ) {
self :: log_debug("getSearch($id): fail to load $object_type object type or LSsearch class");
return false;
}
// Instanciate object
$search = new LSsearch($object_type, "LSselect::$id");
/*
* Set parameters from config
*/
// filter (optional)
$filter = self :: getConfig($id, "LSobjects.$object_type.filter");
if ($filter) $search -> setParam('filter', $filter);
// display_name_format (optional)
$display_name_format = self :: getConfig($id, "LSobjects.$object_type.display_name_format");
if ($display_name_format) $search -> setParam('displayFormat', $display_name_format);
// onlyAccessible (default: false)
$search -> setParam(
'onlyAccessible',
self :: getConfig($id, "LSobjects.$object_type.onlyAccessible", false, 'bool')
);
// Add LSsearchEntry customInfos
$search -> setParam('customInfos', array (
'selectable' => array (
'function' => array('LSselect', 'selectable'),
'args' => $id,
),
'selected' => array (
'function' => array('LSselect', 'selected'),
'args' => $id,
'cache' => false,
),
));
return $search;
}
/**
* Get selectable object types
*
* @param[in] $id string The LSselect ID
*
* @retval array|false Array of selectable object types with name as key
* and label as value, or false if LSselect doesn't exists.
*/
public static function getSelectableObjectTypes($id) {
if (!self :: exists($id))
return false;
$selectable_objects = array();
foreach ($_SESSION['LSselect'][$id]['LSobjects'] as $type => $conf)
if (LSsession :: loadLSobject($type))
$selectable_objects[$type] = LSldapObject :: getLabel($type);
return $selectable_objects;
}
/**
* Get selectable objects info
*
* @param[in] $id string The LSselect ID
*
* @retval array|false Array of selectable object info with objects's DN as key
* and array of object's info as value. Objects's info returned
* currently contains only the object type (object_type). if
* LSselect specified doesn't exists, this method return false.
*/
public static function getSelectedObjects($id) {
if (!self :: exists($id))
return false;
if (is_array($_SESSION['LSselect'][$id]['selected_objects']))
return $_SESSION['LSselect'][$id]['selected_objects'];
return false;
}
/**
* Set selectable objects info
*
* @param[in] $id string The LSselect ID
* @param[in] $selected_objects array Array of selectable object info with objects's DN
* as key and array of object's info as value. Objects's
* info currently contains only the object type (key=object_type).
*
* @retval array|false Array of selectable object info with objects's DN as key
* and array of object's info as value. Objects's info returned
* currently contains only the object type (object_type). if
* LSselect specified doesn't exists, this method return false.
*
* @retval void
*/
public static function setSelectedObjects($id, $selected_objects) {
if (!self :: exists($id))
return;
if (!is_array($selected_objects))
return;
$_SESSION['LSselect'][$id]['selected_objects'] = array();
foreach($selected_objects as $dn => $info) {
if (!is_array($info) || !isset($info['object_type'])) {
self :: log_warning("setSelectedObjects($id): invalid object info for dn='$dn'");
continue;
}
if (self :: checkObjectIsSelectable($id, $info['object_type'], $dn))
$_SESSION['LSselect'][$id]['selected_objects'][$dn] = $info;
else {
$_SESSION['LSselect'][$_REQUEST['objecttype']][]=$_REQUEST['objectdn'];
self :: log_warning("setSelectedObjects($id): object type='".$info['object_type']."' and dn='$dn' is not selectable".varDump($_SESSION['LSselect'][$id]));
}
}
self :: log_debug("id=$id: updated with ".count($_SESSION['LSselect'][$id]['selected_objects'])." selected object(s).");
}
public static function ajax_dropItem(&$data) {
if ((isset($_REQUEST['objecttype'])) && (isset($_REQUEST['objectdn']))) {
if (is_array($_SESSION['LSselect'][$_REQUEST['objecttype']])) {
$result=array();
foreach ($_SESSION['LSselect'][$_REQUEST['objecttype']] as $val) {
if ($val!=$_REQUEST['objectdn']) {
$result[]=$val;
}
}
$_SESSION['LSselect'][$_REQUEST['objecttype']]=$result;
/**
* Check if an object is selectable
*
* @param[in] $id string The LSselect ID
* @param[in] $object_type string The object type
* @param[in] $object_dn string The object DN
*
* @retval boolean True if object is selectable, false otherwise
*/
public static function checkObjectIsSelectable($id, $object_type, $object_dn) {
if (!self :: exists($id)) {
self :: log_warning("checkObjectIsSelectable($id, $object_type, $object_dn): LSselect $id doesn't exists");
return false;
}
if (!array_key_exists($object_type, $_SESSION['LSselect'][$id]['LSobjects'])) {
self :: log_warning("checkObjectIsSelectable($id, $object_type, $object_dn): object type $object_type not selectabled");
return false;
}
// Load LSobject type
if ( !LSsession :: loadLSobject($object_type) ) {
self :: log_warning("checkObjectIsSelectable($id, $object_type, $object_dn): fail to load object type $object_type");
return false;
}
// Instanciate object and load object data from DN
$object = new $object_type();
if (!$object -> loadData($object_dn, self :: getConfig($id, "LSobjects.$object_type.filter", null))) {
self :: log_warning("checkObjectIsSelectable($id, $object_type, $object_dn): object $object_dn not found (or does not match with selection filter)");
return false;
}
// Handle onlyAccessible parameter
if (self :: getConfig($id, "LSobjects.$object_type.onlyAccessible", false, 'bool')) {
if (!LSsession :: canAccess($object_type, $object_dn)) {
self :: log_warning("checkObjectIsSelectable($id, $object_type, $object_dn): object $object_dn not accessible");
return false;
}
}
self :: log_debug("checkObjectIsSelectable($id, $object_type, $object_dn): object selectable");
return true;
}
public static function ajax_refreshSession(&$data) {
if ((isset($_REQUEST['objecttype'])) && (isset($_REQUEST['values'])) ) {
$_SESSION['LSselect'][$_REQUEST['objecttype']]=array();
$values=json_decode($_REQUEST['values'],false);
if (is_array($values)) {
foreach($values as $val) {
$_SESSION['LSselect'][$_REQUEST['objecttype']][]=$val;
}
/*
* AJAX methods
*/
/**
* Add a selected object to selection
*
* Request parameters:
* - LSselect_id: The LSselect ID
* - object_type: The selected object type
* - object_dn: The selected object DN
*
* Data in answer:
* - success: True if object added to selection, false otherwise
*
* @param[in] &$data Reference to returned data array
*
* @retval void
*/
public static function ajax_addSelectedObject(&$data) {
$data['success'] = false;
if (!isset($_REQUEST['LSselect_id']) || !isset($_REQUEST['object_type']) || !isset($_REQUEST['object_dn'])) {
self :: log_warning('ajax_addSelectedObject(): missing parameter.');
LSerror :: addErrorCode('LSsession_12');
return;
}
$id = $_REQUEST['LSselect_id'];
$dn = $_REQUEST['object_dn'];
$type = $_REQUEST['object_type'];
if (!self :: checkObjectIsSelectable($id, $type, $dn)) {
self :: log_warning("ajax_addSelectedObject($id): object type='$type' dn='$dn' is not selectable.");
return;
}
self :: log_debug("id=$id: add $type '$dn'");
if (!$_SESSION['LSselect'][$id]['multiple']) {
$_SESSION['LSselect'][$id]['selected_objects'] = array(
$dn => array('object_type' => $type),
);
self :: log_debug("ajax_addSelectedObject($id): $dn replace current selected object.");
}
else if (!array_key_exists($dn, $_SESSION['LSselect'][$id]['selected_objects'])) {
$_SESSION['LSselect'][$id]['selected_objects'][$dn] = array('object_type' => $type);
self :: log_debug("ajax_addSelectedObject($id): $dn added to current selected objects.");
}
else {
self :: log_warning("ajax_addSelectedObject($id): $dn already present in selected objects.");
}
$data['success'] = true;
}
/**
* Drop a selected object in selection
*
* Request parameters:
* - LSselect_id: The LSselect ID
* - object_dn: The selected object DN
*
* Data in answer:
* - success: True if object added to selection, false otherwise
*
* @param[in] &$data Reference to returned data array
*
* @retval void
*/
public static function ajax_dropSelectedObject(&$data) {
$data['success'] = false;
if (!isset($_REQUEST['LSselect_id']) || !isset($_REQUEST['object_dn'])) {
self :: log_warning('ajax_dropSelectedObject(): missing parameter.');
LSerror :: addErrorCode('LSsession_12');
return;
}
$id = $_REQUEST['LSselect_id'];
$dn = $_REQUEST['object_dn'];
if (!self :: exists($id)) {
self :: log_warning("ajax_dropSelectedObject($id): invalid LSselect ID '$id'.");
return;
}
self :: log_debug("id=$id: remove '$dn'");
if (array_key_exists($dn, $_SESSION['LSselect'][$id]['selected_objects'])) {
unset($_SESSION['LSselect'][$id]['selected_objects'][$dn]);
self :: log_debug("ajax_dropSelectedObject($id): $dn removed from selected objects.");
}
else {
self :: log_warning("ajax_dropSelectedObject($id): $dn not present in selected objects.");
}
$data['success'] = true;
}
/**
* Update selected objects of the selection
*
* Request parameters:
* - LSselect_id: The LSselect ID
* - selected_objects: Array of selected object info (see setSelectedObjects for format)
*
* Data in answer: any
*
* @param[in] &$data Reference to returned data array
*
* @retval void
*/
public static function ajax_updateSelectedObjects(&$data) {
if (isset($_REQUEST['LSselect_id']) && isset($_REQUEST['selected_objects']) ) {
$selected_objects = json_decode($_REQUEST['selected_objects'], true);
if (is_array($selected_objects)) {
self :: log_debug('ajax_updateSelectedObjects(): set selected objects: '.varDump($selected_objects));
self :: setSelectedObjects($_REQUEST['LSselect_id'], $selected_objects);
}
$data=array(
'values' => $values
else
self :: log_warning('ajax_updateSelectedObjects(): fail to decode JSON values.');
$data = array(
'selected_objects' => $selected_objects
);
}
else {
@ -83,8 +409,66 @@ class LSselect {
}
}
public static function selectablly($obj,$args) {
return (LSsession::canEdit($obj->type,$obj->dn,$args))?1:0;
/**
* Get selected objects of the selection
*
* Request parameters:
* - LSselect_id: The LSselect ID
*
* Data in answer:
* - objects: The selected objects info (see getSelectedObjects for format)
*
* @param[in] &$data Reference to returned data array
*
* @retval void
*/
public static function ajax_getSelectedObjects(&$data) {
if (isset($_REQUEST['LSselect_id'])) {
$data=array(
'objects' => self :: getSelectedObjects($_REQUEST['LSselect_id'])
);
}
else {
LSerror :: addErrorCode('LSsession_12');
}
}
/*
* LSsearchEntry customInfos helpers
*/
/**
* LSsearchEntry selectable customInfos method : check if object is selectable
*
* @param[in] $obj LSsearchEntry The LSsearchEntry object
* @param[in] $id string The LSselect ID
*
* @retval boolean True if object is selectable, False otherwise
*/
public static function selectable($obj, $id) {
$editableAttr = self :: getConfig($id, "LSobjects.".$obj->type.".editableAttr");
if (!$editableAttr)
return true;
if ($editableAttr && $obj->type :: hasAttr($editableAttr)) {
return (LSsession::canEdit($obj->type, $obj->dn, $editableAttr))?1:0;
}
return false;
}
/**
* LSsearchEntry selected customInfos method : check if object is selected
*
* @param[in] $obj LSsearchEntry The LSsearchEntry object
* @param[in] $id string The LSselect ID
*
* @retval boolean True if object is selected, False otherwise
*/
public static function selected($obj, $id) {
if (self :: exists($id) &&
is_array($_SESSION['LSselect'][$id]['selected_objects']) &&
array_key_exists($obj->dn, $_SESSION['LSselect'][$id]['selected_objects']))
return true;
return false;
}
}

View file

@ -123,21 +123,23 @@ var LSformElement_select_object_field = new Class({
onAddBtnClick: function(event) {
new Event(event).stop();
values = new Array();
selected_objects = {};
var inputname=this.name+'[]';
this.ul.getElements('input.LSformElement_select_object').each(function(el) {
if (el.name==inputname) {
values.push(el.getProperty('value'));
selected_objects[el.getProperty('value')] = {
'object_type': el.getProperty('data-object-type'),
};
}
}, this);
var data = {
objecttype: this.params['object_type'],
values: JSON.encode(values)
LSselect_id: this.params['LSselect_id'],
selected_objects: JSON.encode(selected_objects)
};
data.imgload=varLSdefault.loadingImgDisplay(this.addBtn,'inside');
new Request({url: 'ajax/class/LSselect/refreshSession', data: data, onSuccess: this.onAddBtnClickComplete.bind(this)}).send();
data.imgload = varLSdefault.loadingImgDisplay(this.addBtn, 'inside');
new Request({url: 'ajax/class/LSselect/updateSelectedObjects', data: data, onSuccess: this.onAddBtnClickComplete.bind(this)}).send();
},
onAddBtnClickComplete: function(responseText, responseXML) {
@ -146,17 +148,7 @@ var LSformElement_select_object_field = new Class({
varLSsmoothbox.asNew();
varLSsmoothbox.addEvent('valid',this.onLSsmoothboxValid.bind(this));
varLSsmoothbox.displayValidBtn();
var url='object/'+this.params['object_type']+'/select';
var params = [];
if (this.params['multiple']) {
params.push('multiple=1');
}
if (this.params['filter64']) {
params.push('filter64='+this.params['filter64']);
}
if (params) {
url=url+'?'+params.join('&');
}
var url='object/select/'+this.params['LSselect_id'];
varLSsmoothbox.openURL(url, {width: 635});
}
},
@ -207,7 +199,7 @@ var LSformElement_select_object_field = new Class({
}
},
addLi: function(name,dn) {
addLi: function(info, dn) {
if (this.params.multiple) { // Multiple
var current = 0;
this.ul.getElements("input[type=hidden]").each(function(input){
@ -224,15 +216,16 @@ var LSformElement_select_object_field = new Class({
var a = new Element('a');
a.addClass('LSformElement_select_object');
a.href="object/"+this.params['object_type']+"/"+dn;
a.set('html',name);
a.href="object/"+info['object_type']+"/"+dn;
a.set('html', info['name']);
a.injectInside(li);
var input = new Element('input');
input.setProperties({
type: 'hidden',
value: dn,
name: this.name+'[]'
'type': 'hidden',
'value': dn,
'name': this.name+'[]',
'data-object-type': info['object_type'],
});
input.addClass('LSformElement_select_object');
input.injectAfter(a);
@ -245,14 +238,15 @@ var LSformElement_select_object_field = new Class({
else { // Non Multiple
var a = this.ul.getElement('a');
if ($type(a)) { // Deja initialise
a.href="object/"+this.params['object_type']+"/"+dn;
a.set('html',name);
a.href="object/"+info['object_type']+"/"+dn;
a.set('html',info['name']);
a.removeClass('LSformElement_select_object_deleted');
var input = this.ul.getElement('input');
input.setProperties({
value: dn,
name: this.name+'[]'
'value': dn,
'name': this.name+'[]',
'data-object-type': info['object_type'],
});
}
else { // Non initialise (No Value)
@ -261,15 +255,16 @@ var LSformElement_select_object_field = new Class({
var a = new Element('a');
a.addClass('LSformElement_select_object');
a.href="object/"+this.params['object_type']+"/"+dn;
a.set('html',name);
a.href="object/"+info['object_type']+"/"+dn;
a.set('html',info['name']);
a.injectInside(li);
var input = new Element('input');
input.setProperties({
type: 'hidden',
value: dn,
name: this.name+'[]'
'type': 'hidden',
'value': dn,
'name': this.name+'[]',
'data-object-type': info['object_type'],
});
input.addClass('LSformElement_select_object');
input.injectAfter(a);
@ -398,7 +393,7 @@ var LSformElement_select_object_field = new Class({
}
},
addSearchAddLi: function(name,dn) {
addSearchAddLi: function(info, dn) {
var current = 0;
this.ul.getElements("input[type=hidden]").each(function(input){
if ((input.value==dn)&&(input.name == this.name+'[]')) {
@ -409,7 +404,11 @@ var LSformElement_select_object_field = new Class({
var li = new Element('li');
li.addClass('LSformElement_select_object_searchAdd');
li.id = dn;
li.set('html',name);
li.set('html',info['name']);
li.setProperties({
'data-dn': dn,
'data-object-type': info['object_type'],
});
li.addEvent('mouseenter',this.onSearchAddLiMouseEnter.bind(this,li));
li.addEvent('mouseleave',this.onSearchAddLiMouseLeave.bind(this,li));
if (current) {
@ -440,7 +439,13 @@ var LSformElement_select_object_field = new Class({
onSearchAddLiClick: function(li) {
this.clearUlIfNoValue();
this.addLi(li.innerHTML,li.id);
this.addLi(
{
object_type: li.getProperty('data-object-type'),
name: li.innerHTML,
},
li.getProperty('data-dn')
);
},
closeIfOpenSearchAdd: function(event) {

View file

@ -75,7 +75,7 @@ var LSrelation = new Class({
deleteFromImgComplete: function(responseText, responseXML) {
var data = JSON.decode(responseText);
if ( varLSdefault.checkAjaxReturn(data) ) {
if ( varLSdefault.checkAjaxReturn(data) && data['success']) {
try {
var ul=$('LSrelation_ul_'+data.id);
var li = $('LSrelation_'+data.id+'_'+data.dn).getParent();
@ -107,14 +107,14 @@ var LSrelation = new Class({
LSdebug(data);
this.refreshRelation=a.id;
data.imgload=varLSdefault.loadingImgDisplay('LSrelation_title_'+a.id,'inside');
new Request({url: 'ajax/class/LSrelation/refreshSession', data: data, onSuccess: this.onLSrelationModifyBtnClickComplete.bind(this)}).send();
new Request({url: 'ajax/class/LSrelation/initSelection', data: data, onSuccess: this.onLSrelationModifyBtnClickComplete.bind(this)}).send();
},
onLSrelationModifyBtnClickComplete: function(responseText, responseXML) {
var data = JSON.decode(responseText);
if ( varLSdefault.checkAjaxReturn(data) ) {
if ( varLSdefault.checkAjaxReturn(data) && data['success'] ) {
varLSsmoothbox.asNew();
varLSsmoothbox.addEvent('valid',this.onLSsmoothboxValid.bind(this));
varLSsmoothbox.addEvent('valid', this.onLSsmoothboxValid.bind(this));
varLSsmoothbox.openURL(data.href,{startElement: $(data.id), width: 635});
}
},
@ -126,12 +126,12 @@ var LSrelation = new Class({
LSdebug(data);
data.imgload=varLSdefault.loadingImgDisplay('LSrelation_title_'+this.refreshRelation,'inside');
new Request({url: 'ajax/class/LSrelation/refreshList', data: data, onSuccess: this.onLSsmoothboxValidComplete.bind(this)}).send();
new Request({url: 'ajax/class/LSrelation/updateFromSelection', data: data, onSuccess: this.onLSsmoothboxValidComplete.bind(this)}).send();
},
onLSsmoothboxValidComplete: function(responseText, responseXML) {
var data = JSON.decode(responseText);
if ( varLSdefault.checkAjaxReturn(data) ) {
if ( varLSdefault.checkAjaxReturn(data) && data['success'] ) {
$('LSrelation_ul_'+this.refreshRelation).set('html',data.html);
this.initializeBtn();
}

View file

@ -1,17 +1,19 @@
var LSselect = new Class({
initialize: function(){
this.main_page = $('LSobject-select-main-div').getParent();
this.content = $('content');
this.multiple = LSselect_multiple;
this.LSselect_search_form = $('LSselect_search_form');
this.id = this.LSselect_search_form.getElement('input[name=LSselect_id]').value;
this.multiple = this.LSselect_search_form.getElement('input[name=multiple]').value;
// Add ajax hidden input
var input = new Element('input');
input.setProperty('name','ajax');
input.setProperty('type','hidden');
input.injectInside(this.LSselect_search_form);
this.tempInput = [];
this.lastCheckboxChanged = null;
this.LSselect_search_form.addEvent('submit',this.onSubmitSearchForm.bindWithEvent(this));
@ -24,6 +26,22 @@ var LSselect = new Class({
this.initializeContent();
varLSdefault.ajaxDisplayDebugAndError();
this.title = $('LSselect_title');
this.tabs_ul = $$('ul.LSselect_selectable_object_types')[0];
if (this.tabs_ul) {
this.initializeTabs();
}
},
initializeTabs: function(ul) {
this.tabs_ul.getElements('li').addEvent('click', function (event) {
console.log(event.target);
this.LSselect_search_form.getElement('input[name=LSobject]').value = event.target.getProperty('data-object-type');
this.tabs_ul.getElements('li.current').each(function(li){ console.log(li); li.removeClass('current'); });
event.target.addClass('current');
this.submitSearchForm();
}.bind(this));
},
initializeContent: function() {
@ -48,30 +66,48 @@ var LSselect = new Class({
}, this);
},
loadingImgDisplay: function(place, position) {
if (!place) {
if (this.title) {
place = this.title;
}
else if (this.tabs_ul) {
place = this.tabs_ul;
}
}
if (!position) {
position = 'inside';
}
return varLSdefault.loadingImgDisplay(place, position);
},
oncheckboxChange: function(checkbox){
this.lastCheckboxChanged = checkbox;
var url;
if (checkbox.checked) {
var url = 'ajax/class/LSselect/addItem';
var data = {
objectdn: checkbox.value,
objecttype: $('LSselect-object').getProperties('caption').caption,
multiple: this.multiple
};
url = 'ajax/class/LSselect/addSelectedObject';
}
else {
var url = 'ajax/class/LSselect/dropItem';
var data = {
objectdn: checkbox.value,
objecttype: $('LSselect-object').getProperties('caption').caption,
multiple: this.multiple
};
url = 'ajax/class/LSselect/dropSelectedObject';
}
data.imgload=varLSdefault.loadingImgDisplay(checkbox.getParent().getNext(),'inside');
var data = {
LSselect_id: this.id,
object_dn: checkbox.value,
object_type: $('LSselect-object').getProperties('caption').caption,
};
data.imgload = this.loadingImgDisplay(checkbox.getParent().getNext(), 'inside');
new Request({url: url, data: data, onSuccess: this.oncheckboxChangeComplete.bind(this)}).send();
},
oncheckboxChangeComplete: function(responseText, responseXML) {
var data = JSON.decode(responseText);
varLSdefault.loadingImgHide(data.imgload);
var success = false;
if(varLSdefault.checkAjaxReturn(data)) {
success = data.success;
}
if (!success && this.lastCheckboxChanged) {
this.lastCheckboxChanged.checked = !this.lastCheckboxChanged.checked;
}
},
onChangePageClick: function(event, a) {
@ -79,7 +115,7 @@ var LSselect = new Class({
var data = {
ajax: true
};
this.searchImgload = varLSdefault.loadingImgDisplay($('LSselect_title'),'inside');
this.searchImgload = this.loadingImgDisplay();
new Request({url: a.href, data: data, onSuccess: this.onChangePageClickComplete.bind(this)}).send();
},
@ -98,8 +134,8 @@ var LSselect = new Class({
this.submitSearchForm();
},
submitSearchForm: function() {
this.searchImgload = varLSdefault.loadingImgDisplay($('LSselect_title'),'inside');
submitSearchForm: function(loading_img_place) {
this.searchImgload = this.loadingImgDisplay();
this.LSselect_search_form.set('send',{
data: this.LSselect_search_form,
evalScripts: true,

View file

@ -605,46 +605,32 @@ LSurl :: add_handler('#^custom_search_action\.php#', 'handle_old_custom_search_a
* @retval void
**/
function handle_LSobject_select($request) {
$object = get_LSobject_from_request($request, true);
if (!$object)
return;
$LSobject = $object -> getType();
if (!LSsession :: loadLSclass('LSsearch')) {
if (!LSsession :: loadLSclass('LSselect')) {
LSsession :: addErrorCode('LSsession_05', 'LSsearch');
LSsession :: displayTemplate();
return false;
}
if (!LSselect :: exists($request->LSselect_id)) {
LSurl :: error_404($request);
return;
}
// Instanciate LSsearch
$LSsearch = new LSsearch($LSobject,'LSselect');
$LSsearch = LSselect :: getSearch(
$request->LSselect_id,
(isset($_REQUEST['LSobject'])?$_REQUEST['LSobject']:null)
);
if (!$LSsearch)
LSlog :: fatal('Fail to retreive search from context.');
$LSobject = $LSsearch -> LSobject;
$object = new $LSobject();
// Handle form POST data
$LSsearch -> setParamsFormPostData();
$LSsearch -> setParam('nbObjectsByPage', NB_LSOBJECT_LIST_SELECT);
$LSsearch -> setParam('nbObjectsByPage', 4);
// Handle parameters
$selectablly = (isset($_REQUEST['selectablly'])?$_REQUEST['selectablly']:0);
if (is_string($_REQUEST['editableAttr'])) {
$LSsearch -> setParam(
'customInfos',
array (
'selectablly' => array (
'function' => array('LSselect', 'selectablly'),
'args' => $_REQUEST['editableAttr']
)
)
);
$selectablly=1;
}
if (!empty($_REQUEST['filter64'])) {
$filter = base64_decode($_REQUEST['filter64'], 1);
if ($filter) {
$LSsearch -> setParam('filter', $filter);
}
}
$multiple = (isset($_REQUEST['multiple'])?1:0);
$page = (isset($_REQUEST['page'])?(int)$_REQUEST['page']:0);
// Run search
@ -656,23 +642,16 @@ function handle_LSobject_select($request) {
array(
array (
'label' => 'Refresh',
'url' => "object/$LSobject/select?refresh",
'url' => "object/select/".$request->LSselect_id."?refresh",
'action' => 'refresh'
)
)
);
LStemplate :: assign('searchForm',
array (
'action' => "object/$LSobject/select",
'action' => "object/select/".$request->LSselect_id,
'recursive' => (! LSsession :: isSubDnLSobject($LSobject) && LSsession :: subDnIsEnabled() ),
'multiple' => $multiple,
'selectablly' => $selectablly,
'labels' => array (
'submit' => _('Search'),
'approx' => _('Approximative search'),
'recursive' => _('Recursive search'),
'level' => _('Level')
),
'multiple' => LSselect :: isMultiple($request->LSselect_id),
'values' => array (
'pattern' => $LSsearch->getParam('pattern'),
'approx' => $LSsearch->getParam('approx'),
@ -685,16 +664,17 @@ function handle_LSobject_select($request) {
'hiddenFields' => array_merge(
$LSsearch -> getHiddenFieldForm(),
array(
'ajax' => 1,
'filter64' => $_REQUEST['filter64'],
'selectablly' => $selectablly,
'multiple' => $multiple
'LSselect_id' => $request->LSselect_id,
'multiple' => LSselect :: isMultiple($request->LSselect_id),
)
)
)
);
LStemplate :: assign('page', $LSsearch -> getPage($page));
LStemplate :: assign('LSsearch', $LSsearch);
LStemplate :: assign('LSselect_id', $request->LSselect_id);
LStemplate :: assign('selectable_object_types', LSselect :: getSelectableObjectTypes($request->LSselect_id));
LStemplate :: assign('selectable_object_type', $LSobject);
LStemplate :: assign('LSobject_list_objectname', $object -> getLabel());
// Set & display template
@ -703,7 +683,7 @@ function handle_LSobject_select($request) {
LSsession :: displayTemplate();
$LSsearch->afterUsingResult();
}
LSurl :: add_handler('#^object/(?P<LSobject>[^/]+)/select?$#', 'handle_LSobject_select');
LSurl :: add_handler('#^object/select/(?P<LSselect_id>[^/]+)/?$#', 'handle_LSobject_select');
/*
* Handle old select.php request for retro-compatibility
@ -716,14 +696,7 @@ function handle_old_select_php($request) {
if (!isset($_GET['LSobject']))
$url = null;
else {
$url = "object/".$_GET['LSobject']."/select";
// Preserve GET parameters
$params = array();
foreach (array('filter64', 'multiple', 'selectablly', 'editableAttr', 'page', 'ajax', 'refresh') as $param)
if (isset($_GET[$param]))
$params[] = $param.'='.$_GET[$param];
if ($params)
$url .= '?'.implode('&', $params);
$url = "object/".$_GET['LSobject'];
}
LSerror :: addErrorCode('LSsession_26', 'select.php');
LSurl :: redirect($url);
@ -818,9 +791,9 @@ function handle_LSobject_create($request) {
if (LSsession :: loadLSobject($_GET['relatedLSobject']) && LSsession :: loadLSclass('LSrelation')) {
$obj = new $_GET['relatedLSobject']();
if ($obj -> loadData(urldecode($_GET['relatedLSobjectDN']))) {
$relation = new LSrelation($obj, $_GET['LSrelation']);
if ($relation -> exists()) {
$attr = $relation -> getRelatedEditableAttribute();
if (LSrelation :: exists($_GET['relatedLSobject'], $_GET['LSrelation'])) {
$relation = new LSrelation($obj, $_GET['LSrelation']);
$attr = $relation -> relatedEditableAttribute;
if (isset($object -> attrs[$attr])) {
$value = $relation -> getRelatedKeyValue();
if (is_array($value)) $value=$value[0];
@ -830,6 +803,9 @@ function handle_LSobject_create($request) {
LSerror :: addErrorCode('LSrelations_06',array('relation' => $relation -> getName(),'LSobject' => $obj -> getType()));
}
}
else {
LSlog :: warning("Relation '".$_GET['LSrelation']."' of object type '".$_GET['relatedLSobject']."' does not exists.");
}
}
else {
LSerror :: addErrorCode('LSsession_24');

View file

@ -4,11 +4,11 @@
<td class='LSformElement_select_object_searchAdd'>
{/if}
<ul class='LSform LSformElement_select_object' id='{$attr_name|escape:"quotes"}'>
{foreach from=$values item=txt key=dn}
{foreach from=$values item=info key=dn}
<li>{include file="ls:$fieldTemplate"}</li>
{foreachelse}
{assign var=dn value=""}
{assign var=txt value=""}
{assign var=dn value=""}
{assign var=info value=array()}
<li>{include file="ls:$fieldTemplate"}</li>
{/foreach}
</ul>

View file

@ -1,6 +1,6 @@
{if $dn}
<a href='object/{$selectableObject|escape:"url"}/{$dn|escape:'url'}' class='LSformElement_select_object'>{$txt|escape:"htmlall"}</a>
{if !$freeze}<input type='hidden' class='LSformElement_select_object' name='{$attr_name|escape:"htmlall"}[]' value='{$dn|escape:"htmlall"}' />{/if}
<a href='object/{$info.object_type|escape:"url"}/{$dn|escape:'url'}' class='LSformElement_select_object'>{$info.name|escape:"htmlall"}</a>
{if !$freeze}<input type='hidden' class='LSformElement_select_object' name='{$attr_name|escape:"htmlall"}[]' value='{$dn|escape:"htmlall"}' data-object-type='{$info.object_type|escape:'quotes'}'/>{/if}
{else}
{$noValueTxt|escape:"htmlall"}
{/if}

View file

@ -1,15 +1,23 @@
<div class='LSobject-select' id='LSobject-select-main-div'>
{if count($selectable_object_types) == 1}
<h1 id='LSselect_title'>
{$pagetitle|escape:"htmlall"}
</h1>
{else}
<ul class="LSselect_selectable_object_types">
{foreach $selectable_object_types as $type => $label}
<li data-object-type='{$type|escape:'quotes'}'{if $selectable_object_type==$type} class="current"{/if}>{$label}</li>
{/foreach}
</ul>
{/if}
<form action='{$searchForm.action}' method='post' class='LSview_search LSselect_search btn' id='LSselect_search_form'>
{foreach from=$searchForm.hiddenFields item=field_value key=field_name}
<input type='hidden' name='{$field_name|escape:"htmlall"}' value='{$field_value|escape:"htmlall"}' />
{/foreach}
{if $LSsession_subDn!=""}
<label id='LSselect_topDn_label'>{$searchForm.labels.level|escape:"htmlall"}
<label id='LSselect_topDn_label'>{tr msg="Level"|escape:"htmlall"}
<select name='subDn' id='LSselect_topDn'>
{html_options values=$LSsession_subDn_indexes output=$LSsession_subDn_names selected=$searchForm.values.basedn}
</select>
@ -17,11 +25,11 @@
{/if}
<div class='LSselect_search'>
<input type='text' name='pattern' class='LSview_search' value='{$searchForm.values.pattern|escape:"htmlall"}'/>
<input type='submit' value='{$searchForm.labels.submit|escape:"htmlall"}' name='{$searchForm.names.submit|escape:"htmlall"}' class='LSview_search' />
<img src='{img name='refresh'}' alt='{$searchForm.labels.refresh|escape:"htmlall"}' title='{$searchForm.labels.refresh|escape:"htmlall"}' id='LSselect_refresh_btn' />
<input type='submit' value='{tr msg="Search"|escape:"htmlall"}' name='{$searchForm.names.submit|escape:"htmlall"}' class='LSview_search' />
<img src='{img name='refresh'}' alt='{tr msg="Refresh"|escape:"htmlall"}' title='{tr msg="Refresh"|escape:"htmlall"}' id='LSselect_refresh_btn' />
<p id='LSview_search_param'>
<label class='LSview_search'>{$searchForm.labels.approx|escape:"htmlall"} : <input type='checkbox' name='approx' class='LSview_search' {if $searchForm.values.approx!=''}checked="true"{/if} /></label>
{if $searchForm.recursive}<label class='LSview_search'>{$searchForm.labels.recursive|escape:"htmlall"} : <input type='checkbox' name='recursive' class='LSview_search' {if $searchForm.values.recursive!=''}checked="true"{/if}/></label>{/if}
<label class='LSview_search'>{tr msg="Approximative search"|escape:"htmlall"} : <input type='checkbox' name='approx' class='LSview_search' {if $searchForm.values.approx!=''}checked="true"{/if} /></label>
{if $searchForm.recursive}<label class='LSview_search'>{tr msg="Recursive search"|escape:"htmlall"} : <input type='checkbox' name='recursive' class='LSview_search' {if $searchForm.values.recursive!=''}checked="true"{/if}/></label>{/if}
</p>
</div>
</form>
@ -30,6 +38,5 @@
</div>
</div>
<script type='text/javascript'>
LSselect_multiple = {$searchForm.multiple};
varLSselect = new LSselect();
</script>

View file

@ -26,7 +26,11 @@
</tr>
{foreach from=$page.list item=object}
<tr class='{cycle values="LSobject-list,LSobject-list LSobject-list-bis"}'>
<td class='LSobject-list LSobject-select-check'><input type='{if $searchForm.multiple}checkbox{else}radio{/if}' name='LSobjects_selected[]' value='{$object->dn|escape:"htmlall"}' {if $object->LSselect}checked="true"{/if}{if $searchForm.selectablly}{if !$object->selectablly} disabled="disabled"{/if}{/if} class='LSobject-select' /></td>
<td class='LSobject-list LSobject-select-check'>
<input type='{if $searchForm.multiple}checkbox{else}radio{/if}' name='LSobjects_selected[]'
value='{$object->dn|escape:"htmlall"}' {if $object->selected}checked="true"{/if}
{if !$object->selectable}disabled="disabled"{/if} class='LSobject-select' />
</td>
<td class='LSobject-list LSobject-select-names'>{$object->displayName|escape:"htmlall"}</td>
{if $LSsearch->displaySubDn}
<td class='LSobject-list LSobject-select-level'>{$object->subDn|escape:"htmlall"}</td>
@ -52,21 +56,21 @@
{else}
{assign var=start value=0}
{/if}
<a href='object/{$LSsearch->LSobject|escape:"url"}/select?page=0&amp;multiple={$searchForm.multiple}' class='LSobject-list-page'>&lt;</a>
<a href='object/select/{$LSselect_id|escape:"url"}?page=0' class='LSobject-list-page'>&lt;</a>
{foreach from=0|range:10 item=i}
{if $page.nb==$start+$i}
<strong class='LSobject-list-page'>{$page.nb+1}</strong>
{else}
<a href='object/{$LSsearch->LSobject|escape:"url"}/select?page={$i+$start}&amp;multiple={$searchForm.multiple}' class='LSobject-list-page'>{$i+$start+1}</a>
<a href='object/select/{$LSselect_id|escape:"url"}?page={$i+$start}' class='LSobject-list-page'>{$i+$start+1}</a>
{/if}
{/foreach}
<a href='object/{$LSsearch->LSobject|escape:"url"}/select?page={$page.nbPages-1}&amp;multiple={$searchForm.multiple}' class='LSobject-list-page'>&gt;</a>
<a href='object/select/{$LSselect_id|escape:"url"}?page={$page.nbPages-1}' class='LSobject-list-page'>&gt;</a>
{else}
{section name=listpage loop=$page.nbPages step=1}
{if $page.nb == $smarty.section.listpage.index}
<strong class='LSobject-list-page'>{$page.nb+1}</strong>
{else}
<a href='object/{$LSsearch->LSobject|escape:"url"}/select?page={$smarty.section.listpage.index}&amp;multiple={$searchForm.multiple}' class='LSobject-list-page'>{$smarty.section.listpage.index+1}</a>
<a href='object/select/{$LSselect_id|escape:"url"}?page={$smarty.section.listpage.index}' class='LSobject-list-page'>{$smarty.section.listpage.index+1}</a>
{/if}
{/section}
{/if}