Index: branches/5.2.x/core/kernel/db/dbitem.php
===================================================================
diff -u -N -r14585 -r14596
--- branches/5.2.x/core/kernel/db/dbitem.php (.../dbitem.php) (revision 14585)
+++ branches/5.2.x/core/kernel/db/dbitem.php (.../dbitem.php) (revision 14596)
@@ -1,6 +1,6 @@
validator) ) {
+ $validator_class = $this->Application->getUnitOption($this->Prefix, 'ValidatorClass', 'kValidator');
- $this->ErrorMsgs['required'] = '!la_err_required!'; //'Field is required';
- $this->ErrorMsgs['unique'] = '!la_err_unique!'; //'Field value must be unique';
- $this->ErrorMsgs['value_out_of_range'] = '!la_err_value_out_of_range!'; //'Field is out of range, possible values from %s to %s';
- $this->ErrorMsgs['length_out_of_range'] = '!la_err_length_out_of_range!'; //'Field is out of range';
- $this->ErrorMsgs['bad_type'] = '!la_err_bad_type!'; //'Incorrect data format, please use %s';
- $this->ErrorMsgs['invalid_format'] = '!la_err_invalid_format!'; //'Incorrect data format, please use %s';
- $this->ErrorMsgs['bad_date_format'] = '!la_err_bad_date_format!'; //'Incorrect date format, please use (%s) ex. (%s)';
- $this->ErrorMsgs['primary_lang_required'] = '!la_err_primary_lang_required!';
+ $this->validator =& $this->Application->makeClass($validator_class);
+ }
+
+ $this->validator->setDataSource($this);
}
public function SetDirtyField($field_name, $field_value)
@@ -131,14 +123,16 @@
return $value;
}
- $options = $this->GetFieldOptions($field_name);
$res = $value;
- if (array_key_exists('formatter', $options)) {
- $formatter =& $this->Application->recallObject($options['formatter']);
+ $formatter = $this->GetFieldOption($field_name, 'formatter');
+
+ if ( $formatter ) {
+ $formatter =& $this->Application->recallObject($formatter);
/* @var $formatter kFormatter */
$res = $formatter->Format($value, $field_name, $this, $format);
}
+
return $res;
}
@@ -191,6 +185,8 @@
// kFormatter is always used, to make sure, that numeric value is converted to normal representation
// according to regional format, even when formatter is not set (try seting format to 1.234,56 to understand why)
$formatter =& $this->Application->recallObject(isset($options['formatter']) ? $options['formatter'] : 'kFormatter');
+ /* @var $formatter kFormatter */
+
$parsed = $formatter->Parse($value, $name, $this);
$this->SetDBField($name,$parsed);
@@ -208,48 +204,25 @@
public function SetDBField($name,$value)
{
$this->FieldValues[$name] = $value;
- /*if (isset($this->Fields[$name]['formatter'])) {
- $formatter =& $this->Application->recallObject($this->Fields[$name]['formatter']);
- $formatter->UpdateSubFields($name, $value, $this->Fields[$name], $this);
- }*/
}
/**
* Set's field error, if pseudo passed not found then create it with message text supplied.
- * Don't owerrite existing pseudo translation.
+ * Don't overwrite existing pseudo translation.
*
* @param string $field
* @param string $pseudo
* @param string $error_label
+ * @param Array $error_params
*
* @return bool
+ * @access public
*/
public function SetError($field, $pseudo, $error_label = null, $error_params = null)
{
- $error_field = isset($this->Fields[$field]['error_field']) ? $this->Fields[$field]['error_field'] : $field;
- if (isset($this->FieldErrors[$error_field]['pseudo'])) {
- // don't set more then one error on field
- return false;
- }
+ $this->initValidator();
- $this->FieldErrors[$error_field]['pseudo'] = $pseudo;
-
- if (isset($error_params)) {
- if (array_key_exists('value', $error_params)) {
- $this->FieldErrors[$error_field]['value'] = $error_params['value'];
- unset($error_params['value']);
- }
-
- // additional params, that helps to determine error sources
- $this->FieldErrors[$error_field]['params'] = $error_params;
- }
-
- if (isset($error_label) && !isset($this->ErrorMsgs[$pseudo])) {
- // label for error (only when not already set)
- $this->ErrorMsgs[$pseudo] = (substr($error_label, 0, 1) == '+') ? substr($error_label, 1) : '!'.$error_label.'!';
- }
-
- return true;
+ return $this->validator->SetError($field, $pseudo, $error_label, $error_params);
}
/**
@@ -260,7 +233,11 @@
*/
public function RemoveError($field)
{
- unset( $this->FieldErrors[$field] );
+ if ( !is_object($this->validator) ) {
+ return ;
+ }
+
+ $this->validator->RemoveError($field);
}
/**
@@ -271,11 +248,11 @@
*/
public function GetErrorPseudo($field)
{
- if ( !array_key_exists($field, $this->FieldErrors) ) {
+ if ( !is_object($this->validator) ) {
return '';
}
- return array_key_exists('pseudo', $this->FieldErrors[$field]) ? $this->FieldErrors[$field]['pseudo'] : '';
+ return $this->validator->GetErrorPseudo($field);
}
/**
@@ -306,81 +283,76 @@
}
/**
- * Sets item' fields corresponding to elements in passed $hash values.
- *
- * The function sets current item fields to values passed in $hash, by matching $hash keys with field names
- * of current item. If current item' fields are unknown {@link kDBItem::PrepareFields()} is called before acutally setting the fields
- *
- * @param Array $hash
- * @param Array $set_fields Optional param, field names in target object to set, other fields will be skipped
- * @access public
- */
- public function SetFieldsFromHash($hash, $set_fields = null)
+ * Sets item' fields corresponding to elements in passed $hash values.
+ *
+ * The function sets current item fields to values passed in $hash, by matching $hash keys with field names
+ * of current item. If current item' fields are unknown {@link kDBItem::PrepareFields()} is called before actually setting the fields
+ *
+ * @param Array $hash
+ * @param Array $set_fields Optional param, field names in target object to set, other fields will be skipped
+ * @return void
+ * @access public
+ */
+ public function SetFieldsFromHash($hash, $set_fields = Array ())
{
- // used in formatter which work with multiple fields together
- foreach($hash as $field_name => $field_value) {
- if (is_numeric($field_name) || !array_key_exists($field_name, $this->Fields)) {
- continue;
- }
+ if ( !$set_fields ) {
+ $set_fields = array_keys($hash);
+ }
- if (is_array($set_fields) && !in_array($field_name, $set_fields)) {
- continue;
- }
+ $set_fields = array_intersect($set_fields, array_keys($this->Fields));
- $this->SetDirtyField($field_name, $field_value);
+ // used in formatter which work with multiple fields together
+ foreach ($set_fields as $field_name) {
+ $this->SetDirtyField($field_name, $hash[$field_name]);
}
// formats all fields using associated formatters
- foreach ($hash as $field_name => $field_value)
- {
- if (is_numeric($field_name) || !array_key_exists($field_name, $this->Fields)) {
- continue;
- }
-
- if (is_array($set_fields) && !in_array($field_name, $set_fields)) {
- continue;
- }
-
- $this->SetField($field_name,$field_value);
+ foreach ($set_fields as $field_name) {
+ $this->SetField($field_name, $hash[$field_name]);
}
}
- public function SetDBFieldsFromHash($hash, $set_fields = null)
+ /**
+ * Sets object fields from $hash arrat
+ * @param Array $hash
+ * @param Array|null $set_fields
+ * @return void
+ * @access public
+ */
+ public function SetDBFieldsFromHash($hash, $set_fields = Array ())
{
- foreach ($hash as $field_name => $field_value) {
- if (is_numeric($field_name) || !array_key_exists($field_name, $this->Fields)) {
- continue;
- }
+ if ( !$set_fields ) {
+ $set_fields = array_keys($hash);
+ }
- if (is_array($set_fields) && !in_array($field_name, $set_fields)) {
- continue;
- }
+ $set_fields = array_intersect($set_fields, array_keys($this->Fields));
- $this->SetDBField($field_name, $field_value);
+ foreach ($set_fields as $field_name) {
+ $this->SetDBField($field_name, $hash[$field_name]);
}
}
/**
- * Returns part of SQL WHERE clause identifing the record, ex. id = 25
- *
- * @param string $method Child class may want to know who called GetKeyClause, Load(), Update(), Delete() send its names as method
- * @param Array $keys_hash alternative, then item id, keys hash to load item by
- * @return void
- * @see kDBItem::Load()
- * @see kDBItem::Update()
- * @see kDBItem::Delete()
- * @access protected
- */
- protected function GetKeyClause($method=null, $keys_hash = null)
+ * Returns part of SQL WHERE clause identifying the record, ex. id = 25
+ *
+ * @param string $method Child class may want to know who called GetKeyClause, Load(), Update(), Delete() send its names as method
+ * @param Array $keys_hash alternative, then item id, keys hash to load item by
+ * @see kDBItem::Load()
+ * @see kDBItem::Update()
+ * @see kDBItem::Delete()
+ * @return string
+ * @access protected
+ */
+ protected function GetKeyClause($method = null, $keys_hash = null)
{
- if (!isset($keys_hash)) {
+ if ( !isset($keys_hash) ) {
$keys_hash = Array ($this->IDField => $this->ID);
}
$ret = '';
foreach ($keys_hash as $field => $value) {
- if (!preg_match('/\./', $field)) {
+ if ( !preg_match('/\./', $field) ) {
$ret .= '(`' . $this->TableName . '`.' . $field . ' = ' . $this->Conn->qstr($value) . ') AND ';
}
else {
@@ -534,9 +506,13 @@
public function UpdateFormattersMasterFields()
{
+ $this->initValidator(); // used, when called not from kValidator::Validate method
+
foreach ($this->Fields as $field => $options) {
- if (isset($options['formatter'])) {
+ if ( isset($options['formatter']) ) {
$formatter =& $this->Application->recallObject($options['formatter']);
+ /* @var $formatter kFormatter */
+
$formatter->UpdateMasterFields($field, $this->GetDBField($field), $options, $this);
}
}
@@ -576,101 +552,96 @@
}
/**
- * Updates previously loaded record with current item' values
- *
- * @access public
- * @param int Primery Key Id to update
- * @return bool
- */
+ * Updates previously loaded record with current item' values
+ *
+ * @access public
+ * @param int $id Primary Key Id to update
+ * @param bool $system_update
+ * @return bool
+ * @access public
+ */
public function Update($id = null, $system_update = false)
{
- if (isset($id)) {
+ if ( isset($id) ) {
$this->setID($id);
}
- if (!$this->raiseEvent('OnBeforeItemUpdate')) {
+ if ( !$this->raiseEvent('OnBeforeItemUpdate') ) {
return false;
}
- if (!isset($this->ID)) {
+ if ( !isset($this->ID) ) {
// ID could be set inside OnBeforeItemUpdate event, so don't combine this check with previous one
return false;
}
// validate before updating
- if (!$this->Validate()) {
+ if ( !$this->Validate() ) {
return false;
}
- if (!$this->FieldValues) {
- // nothing to update
- return true;
- }
+ if ( !$this->FieldValues ) {
+ // nothing to update
+ return true;
+ }
- $sql = '';
+ $sql = '';
- foreach ($this->FieldValues as $field_name => $field_value) {
- if ($this->skipField($field_name)) {
- continue;
- }
+ foreach ($this->FieldValues as $field_name => $field_value) {
+ if ( $this->skipField($field_name) ) {
+ continue;
+ }
- if ( is_null($field_value) ) {
- if (array_key_exists('not_null', $this->Fields[$field_name]) && $this->Fields[$field_name]['not_null']) {
- // "kFormatter::Parse" methods converts empty values to NULL and for
- // not-null fields they are replaced with default value here
- $field_value = $this->Fields[$field_name]['default'];
- }
- }
+ if ( is_null($field_value) ) {
+ if ( array_key_exists('not_null', $this->Fields[$field_name]) && $this->Fields[$field_name]['not_null'] ) {
+ // "kFormatter::Parse" methods converts empty values to NULL and for
+ // not-null fields they are replaced with default value here
+ $field_value = $this->Fields[$field_name]['default'];
+ }
+ }
- $sql .= '`' . $field_name . '` = ' . $this->Conn->qstr($field_value) . ', ';
- }
+ $sql .= '`' . $field_name . '` = ' . $this->Conn->qstr($field_value) . ', ';
+ }
- $sql = 'UPDATE ' . $this->TableName . '
- SET ' . substr($sql, 0, -2) . '
- WHERE ' . $this->GetKeyClause('update');
+ $sql = 'UPDATE ' . $this->TableName . '
+ SET ' . substr($sql, 0, -2) . '
+ WHERE ' . $this->GetKeyClause('update');
- if ($this->Conn->ChangeQuery($sql) === false) {
- // there was and sql error
- return false;
- }
+ if ( $this->Conn->ChangeQuery($sql) === false ) {
+ // there was and sql error
+ return false;
+ }
$affected_rows = $this->Conn->getAffectedRows();
- if (!$system_update && ($affected_rows > 0)) {
+ if ( !$system_update && ($affected_rows > 0) ) {
$this->setModifiedFlag(ChangeLog::UPDATE);
}
$this->saveCustomFields();
- $this->raiseEvent('OnAfterItemUpdate');
- $this->OriginalFieldValues = $this->FieldValues;
- $this->Loaded = true;
+ $this->raiseEvent('OnAfterItemUpdate');
+ $this->OriginalFieldValues = $this->FieldValues;
+ $this->Loaded = true;
- if (!$this->IsTempTable()) {
+ if ( !$this->IsTempTable() ) {
$this->Application->resetCounters($this->TableName);
}
return true;
}
+ /**
+ * Validates given field
+ *
+ * @param string $field
+ * @return bool
+ * @access public
+ */
public function ValidateField($field)
{
- $options = $this->Fields[$field];
+ $this->initValidator();
- /*if (isset($options['formatter'])) {
- $formatter =& $this->Application->recallObject($options['formatter']);
- $formatter->UpdateMasterFields($field, $this->GetDBField($field), $options, $this);
- }*/
-
- $error_field = isset($options['error_field']) ? $options['error_field'] : $field;
- $res = !isset($this->FieldErrors[$error_field]['pseudo']) || !$this->FieldErrors[$error_field]['pseudo'];
-
- $res = $res && $this->ValidateRequired($field, $options);
- $res = $res && $this->ValidateType($field, $options);
- $res = $res && $this->ValidateRange($field, $options);
- $res = $res && $this->ValidateUnique($field, $options);
- $res = $res && $this->CustomValidation($field, $options);
-
- return $res;
+ return $this->validator->ValidateField($field);
}
/**
@@ -683,101 +654,38 @@
*/
public function Validate()
{
- $this->UpdateFormattersMasterFields(); //order is critical - should be called BEFORE checking errors
-
- if ($this->IgnoreValidation) {
+ if ( $this->IgnoreValidation ) {
return true;
}
+ $this->initValidator();
+
// will apply any custom validation to the item
$this->raiseEvent('OnBeforeItemValidate');
- $global_res = true;
- foreach ($this->Fields as $field => $params) {
- $res = $this->ValidateField($field);
-
-
- $global_res = $global_res && $res;
- }
-
- if (!$global_res && $this->Application->isDebugMode()) {
- $error_msg = ' Validation failed in prefix '.$this->Prefix.',
- FieldErrors follow (look at items with "pseudo" key set)
- You may ignore this notice if submitted data really has a validation error';
- trigger_error(trim($error_msg), E_USER_NOTICE);
- $this->Application->Debugger->dumpVars($this->FieldErrors);
- }
-
- if ($global_res) {
+ if ( $this->validator->Validate() ) {
// no validation errors
$this->raiseEvent('OnAfterItemValidate');
+
+ return true;
}
- return $global_res;
+ return false;
}
/**
- * Check field value by user-defined alghoritm
- *
- * @param string $field field name
- * @param Array $params field options from config
- * @return bool
- */
- protected function CustomValidation($field, $params)
- {
- return true;
- }
-
- /**
* Check if item has errors
*
* @param Array $skip_fields fields to skip during error checking
* @return bool
*/
public function HasErrors($skip_fields = Array ())
{
- $global_res = false;
-
- foreach ($this->Fields as $field => $field_params) {
- // If Formatter has set some error messages during values parsing
- if ( !( in_array($field, $skip_fields) ) &&
- isset($this->FieldErrors[$field]['pseudo']) && $this->FieldErrors[$field] != '') {
- $global_res = true;
- }
+ if ( !is_object($this->validator) ) {
+ return false;
}
- return $global_res;
- }
- /**
- * Check if value in field matches field type specified in config
- *
- * @param string $field field name
- * @param Array $params field options from config
- * @return bool
- */
- protected function ValidateType($field, $params)
- {
- $res = true;
- $val = $this->FieldValues[$field];
- if ( $val != '' &&
- isset($params['type']) &&
- preg_match("#int|integer|double|float|real|numeric|string#", $params['type'])
- ) {
- if ($params['type'] == 'numeric') {
- trigger_error('Invalid field type '.$params['type'].' (in ValidateType method), please use float instead', E_USER_NOTICE);
- $params['type'] = 'float';
- }
- $res = is_numeric($val);
- if ($params['type']=='string' || $res) {
- $f = 'is_'.$params['type'];
- settype($val, $params['type']);
- $res = $f($val) && ($val == $this->FieldValues[$field]);
- }
- if (!$res) {
- $this->SetError($field, 'bad_type', null, Array ($params['type']));
- }
- }
- return $res;
+ return $this->validator->HasErrors($skip_fields);
}
/**
@@ -787,125 +695,14 @@
* @param Array $params field options from config
* @return bool
* @access public
+ * @todo Find a way to get rid of direct call from kMultiLanguage::UpdateMasterFields method
*/
public function ValidateRequired($field, $params)
{
- $res = true;
- if (isset($params['required']) && $params['required']) {
- $check_value = $this->FieldValues[$field];
- if ($this->Application->ConfigValue('TrimRequiredFields')) {
- $check_value = trim($check_value);
- }
- $res = ((string)$check_value != '');
- }
-
- if (!$res) {
- $this->SetError($field, 'required');
- }
-
- return $res;
+ return $this->validator->ValidateRequired($field, $params);
}
/**
- * Validates that current record has unique field combination among other table records
- *
- * @param string $field field name
- * @param Array $params field options from config
- * @return bool
- * @access private
- */
- protected function ValidateUnique($field, $params)
- {
- $res = true;
- $unique_fields = getArrayValue($params,'unique');
- if($unique_fields !== false)
- {
- $where = Array();
- array_push($unique_fields,$field);
- foreach($unique_fields as $unique_field)
- {
- // if field is not empty or if it is required - we add where condition
- if ((string)$this->GetDBField($unique_field) != '' || (isset($this->Fields[$unique_field]['required']) && $this->Fields[$unique_field]['required'])) {
- $where[] = '`'.$unique_field.'` = '.$this->Conn->qstr( $this->GetDBField($unique_field) );
- }
- else {
- // not good if we check by less fields than indicated
- return true;
- }
- }
- // This can ONLY happen if all unique fields are empty and not required.
- // In such case we return true, because if unique field is not required there may be numerous empty values
-// if (!$where) return true;
-
- $sql = 'SELECT COUNT(*) FROM %s WHERE ('.implode(') AND (',$where).') AND ('.$this->IDField.' <> '.(int)$this->ID.')';
-
- $res_temp = $this->Conn->GetOne( str_replace('%s', $this->TableName, $sql) );
-
- $current_table_only = getArrayValue($params, 'current_table_only'); // check unique record only in current table
- $res_live = $current_table_only ? 0 : $this->Conn->GetOne( str_replace('%s', $this->Application->GetLiveName($this->TableName), $sql) );
-
- $res = ($res_temp == 0) && ($res_live == 0);
-
- if (!$res) {
- $this->SetError($field, 'unique');
- }
- }
- return $res;
- }
-
- /**
- * Check if field value is in range specified in config
- *
- * @param string $field field name
- * @param Array $params field options from config
- * @return bool
- * @access private
- */
- protected function ValidateRange($field, $params)
- {
- $res = true;
- $val = $this->FieldValues[$field];
-
- if ( isset($params['type']) && preg_match("#int|integer|double|float|real#", $params['type']) && strlen($val) > 0 ) {
- if ( isset($params['max_value_inc'])) {
- $res = $res && $val <= $params['max_value_inc'];
- $max_val = $params['max_value_inc'].' (inclusive)';
- }
- if ( isset($params['min_value_inc'])) {
- $res = $res && $val >= $params['min_value_inc'];
- $min_val = $params['min_value_inc'].' (inclusive)';
- }
- if ( isset($params['max_value_exc'])) {
- $res = $res && $val < $params['max_value_exc'];
- $max_val = $params['max_value_exc'].' (exclusive)';
- }
- if ( isset($params['min_value_exc'])) {
- $res = $res && $val > $params['min_value_exc'];
- $min_val = $params['min_value_exc'].' (exclusive)';
- }
- }
- if (!$res) {
- if ( !isset($min_val) ) $min_val = '-∞';
- if ( !isset($max_val) ) $max_val = '∞';
-
- $this->SetError($field, 'value_out_of_range', null, Array ($min_val, $max_val));
- return $res;
- }
- if ( isset($params['max_len'])) {
- $res = $res && mb_strlen($val) <= $params['max_len'];
- }
- if ( isset($params['min_len'])) {
- $res = $res && mb_strlen($val) >= $params['min_len'];
- }
- if (!$res) {
- $error_params = Array (getArrayValue($params, 'min_len'), getArrayValue($params, 'max_len'), mb_strlen($val));
- $this->SetError($field, 'length_out_of_range', null, $error_params);
- return $res;
- }
- return $res;
- }
-
- /**
* Return error message for field
*
* @param string $field
@@ -914,33 +711,11 @@
*/
public function GetErrorMsg($field, $force_escape = null)
{
- $err = $this->GetErrorPseudo($field);
-
- if (!$err) {
+ if ( !is_object($this->validator) ) {
return '';
}
- // if special error msg defined in config
- if( isset($this->Fields[$field]['error_msgs'][$err]) )
- {
- $msg = $this->Fields[$field]['error_msgs'][$err];
- }
- else //fall back to defaults
- {
- if( !isset($this->ErrorMsgs[$err]) ) {
- trigger_error('No user message is defined for pseudo error '.$err.'
', E_USER_WARNING);
- return $err; //return the pseudo itself
- }
- $msg = $this->ErrorMsgs[$err];
- }
- $msg = $this->Application->ReplaceLanguageTags($msg, $force_escape);
-
- if ( isset($this->FieldErrors[$field]['params']) )
- {
- return vsprintf($msg, $this->FieldErrors[$field]['params']);
- }
-
- return $msg;
+ return $this->validator->GetErrorMsg($field, $force_escape);
}
/**
@@ -951,16 +726,21 @@
*/
public function GetFieldErrors()
{
- return $this->FieldErrors;
+ if ( !is_object($this->validator) ) {
+ return Array ();
+ }
+
+ return $this->validator->GetFieldErrors();
}
/**
- * Creates a record in the database table with current item' values
- *
- * @param mixed $force_id Set to TRUE to force creating of item's own ID or to value to force creating of passed id. Do not pass 1 for true, pass exactly TRUE!
- * @access public
- * @return bool
- */
+ * Creates a record in the database table with current item' values
+ *
+ * @param mixed $force_id Set to TRUE to force creating of item's own ID or to value to force creating of passed id. Do not pass 1 for true, pass exactly TRUE!
+ * @param bool $system_create
+ * @return bool
+ * @access public
+ */
public function Create($force_id = false, $system_create = false)
{
if (!$this->raiseEvent('OnBeforeItemCreate')) {
@@ -989,7 +769,7 @@
if (is_null($field_value)) {
if (array_key_exists('not_null', $this->Fields[$field_name]) && $this->Fields[$field_name]['not_null']) {
// "kFormatter::Parse" methods converts empty values to NULL and for
- // not-null fields they are replaced with default value here
+ // not-null fields they are replaced with default value here
$values_sql .= $this->Conn->qstr($this->Fields[$field_name]['default']);
}
else {
@@ -1048,18 +828,19 @@
}
/**
- * Deletes the record from databse
- *
- * @access public
- * @return bool
- */
+ * Deletes the record from database
+ *
+ * @param int $id
+ * @return bool
+ * @access public
+ */
public function Delete($id = null)
{
- if (isset($id)) {
+ if ( isset($id) ) {
$this->setID($id);
}
- if (!$this->raiseEvent('OnBeforeItemDelete')) {
+ if ( !$this->raiseEvent('OnBeforeItemDelete') ) {
return false;
}
@@ -1069,14 +850,14 @@
$ret = $this->Conn->ChangeQuery($sql);
$affected_rows = $this->Conn->getAffectedRows();
- if ($affected_rows > 0) {
+ if ( $affected_rows > 0 ) {
$this->setModifiedFlag(ChangeLog::DELETE); // will change affected rows, so get it before this line
// something was actually deleted
$this->raiseEvent('OnAfterItemDelete');
}
- if (!$this->IsTempTable()) {
+ if ( !$this->IsTempTable() ) {
$this->Application->resetCounters($this->TableName);
}
@@ -1089,10 +870,10 @@
// master field is set only for CURRENT language
$formatter = array_key_exists('formatter', $options) ? $options['formatter'] : false;
- if (($formatter == 'kMultiLanguage') && array_key_exists('master_field', $options) && array_key_exists('error_field', $options)) {
+ if ( ($formatter == 'kMultiLanguage') && isset($options['master_field']) && isset($options['error_field']) ) {
// MuliLanguage formatter sets error_field to master_field, but in PopulateMlFields mode,
- // we display ML fields directly so we set it back to itself, otherwise error will not be displayed
- unset($this->Fields[$field]['error_field']);
+ // we display ML fields directly so we set it back to itself, otherwise error won't be displayed
+ unset( $this->Fields[$field]['error_field'] );
}
}
}
@@ -1279,7 +1060,7 @@
protected function LogChanges($main_prefix, $mode)
{
- if (!$mode) {
+ if ( !$mode ) {
return ;
}
@@ -1295,7 +1076,7 @@
'Action' => $mode,
);
- if ($this->Prefix == $main_prefix) {
+ if ( $this->Prefix == $main_prefix ) {
// main item
$fields_hash['MasterId'] = $this->GetID();
$fields_hash['ParentPrefix'] = Array ($main_prefix);
@@ -1304,10 +1085,11 @@
else {
// sub item
// collect foreign key values (for serial reset)
- $foreign_keys = $this->Application->getUnitOption($this->Prefix, 'ForeignKey');
+ $foreign_keys = $this->Application->getUnitOption($this->Prefix, 'ForeignKey', Array ());
$dependent_fields = $fields_hash['ParentId'] = $fields_hash['ParentPrefix'] = Array ();
+ /* @var $foreign_keys Array */
- if (is_array($foreign_keys)) {
+ if ( is_array($foreign_keys) ) {
foreach ($foreign_keys as $prefix => $field_name) {
$dependent_fields[$field_name] = $this->GetDBField($field_name);
$fields_hash['ParentPrefix'][] = $prefix;
@@ -1323,18 +1105,18 @@
$fields_hash['DependentFields'] = $dependent_fields;
- // works only, when main item is present in url, when subitem is changed
+ // works only, when main item is present in url, when sub-item is changed
$master_id = $this->Application->GetVar($main_prefix . '_id');
- if ($master_id === false) {
- // works in case of we are not editing topmost item, when subitem is created/updated/deleted
+ if ( $master_id === false ) {
+ // works in case of we are not editing topmost item, when sub-item is created/updated/deleted
$master_id = $this->getParentId('auto', true);
}
$fields_hash['MasterId'] = $master_id;
}
- switch ($mode) {
+ switch ( $mode ) {
case ChangeLog::UPDATE:
$to_save = array_merge($this->GetTitleField(), $this->GetChangedFields());
break;
@@ -1346,6 +1128,10 @@
case ChangeLog::DELETE:
$to_save = array_merge($this->GetTitleField(), $this->GetRealFields());
break;
+
+ default:
+ $to_save = Array ();
+ break;
}
$fields_hash['Changes'] = serialize($to_save);
@@ -1453,22 +1239,7 @@
*/
public function GetRealFields()
{
- if (function_exists('array_diff_key')) {
- $db_fields = array_diff_key($this->FieldValues, $this->VirtualFields, $this->CalculatedFields);
- }
- else {
- $db_fields = Array();
-
- foreach ($this->FieldValues as $key => $value) {
- if (array_key_exists($key, $this->VirtualFields) || array_key_exists($key, $this->CalculatedFields)) {
- continue;
- }
-
- $db_fields[$key] = $value;
- }
- }
-
- return $db_fields;
+ return array_diff_key($this->FieldValues, $this->VirtualFields, $this->CalculatedFields);
}
/**
@@ -1542,22 +1313,37 @@
/**
* Sets new required flag to field
*
- * @param string $field
+ * @param mixed $fields
* @param bool $is_required
*/
- public function setRequired($field, $is_required = true)
+ public function setRequired($fields, $is_required = true)
{
- $this->Fields[$field]['required'] = $is_required;
+ if ( !is_array($fields) ) {
+ $fields = explode(',', $fields);
+ }
+
+ foreach ($fields as $field) {
+ $this->Fields[$field]['required'] = $is_required;
+ }
}
+ /**
+ * Removes all data from an object
+ *
+ * @param int $new_id
+ * @return bool
+ * @access public
+ */
public function Clear($new_id = null)
{
$this->Loaded = false;
- $this->FieldValues = Array();
- $this->OriginalFieldValues = Array ();
+ $this->FieldValues = $this->OriginalFieldValues = Array ();
$this->SetDefaultValues(); // will wear off kDBItem::setID effect, so set it later
- $this->FieldErrors = Array();
+ if ( is_object($this->validator) ) {
+ $this->validator->reset();
+ }
+
$this->setID($new_id);
return $this->Loaded;
@@ -1570,13 +1356,13 @@
protected function saveCustomFields()
{
- if (!$this->customFields || $this->inCloning) {
+ if ( !$this->customFields || $this->inCloning ) {
return true;
}
$cdata_key = rtrim($this->Prefix . '-cdata.' . $this->Special, '.');
- $cdata =& $this->Application->recallObject($cdata_key, null, Array('skip_autoload' => true));
+ $cdata =& $this->Application->recallObject($cdata_key, null, Array ('skip_autoload' => true, 'populate_ml_fields' => true));
/* @var $cdata kDBItem */
$resource_id = $this->GetDBField('ResourceId');
@@ -1586,25 +1372,9 @@
$ml_formatter =& $this->Application->recallObject('kMultiLanguage');
/* @var $ml_formatter kMultiLanguage */
- $ml_helper =& $this->Application->recallObject('kMultiLanguageHelper');
- /* @var $ml_helper kMultiLanguageHelper */
-
foreach ($this->customFields as $custom_id => $custom_name) {
- $field_options = $cdata->GetFieldOptions('cust_' . $custom_id);
- $force_primary = isset($field_options['force_primary']) && $field_options['force_primary'];
-
- if ($force_primary) {
- $cdata->SetDBField($ml_formatter->LangFieldName('cust_' . $custom_id, true), $this->GetDBField('cust_' . $custom_name));
- }
- else {
- for ($language_id = 1; $language_id <= $ml_helper->languageCount; $language_id++) {
- if (!$ml_helper->LanguageFound($language_id)) {
- continue;
- }
-
- $cdata->SetDBField('l' . $language_id . '_cust_' . $custom_id, $this->GetDBField('l' . $language_id . '_cust_' . $custom_name));
- }
- }
+ $force_primary = $cdata->GetFieldOption('cust_' . $custom_id, 'force_primary');
+ $cdata->SetDBField($ml_formatter->LangFieldName('cust_' . $custom_id, $force_primary), $this->GetDBField('cust_' . $custom_name));
}
return $cdata->isLoaded() ? $cdata->Update() : $cdata->Create();