* */ /** * Модуль управления дополнительными полями * * @package application.modules.property * @since 2.0 */ class ModuleProperty extends ModuleORM { /** * Список возможных типов свойств/полей */ const PROPERTY_TYPE_INT = 'int'; const PROPERTY_TYPE_FLOAT = 'float'; const PROPERTY_TYPE_VARCHAR = 'varchar'; const PROPERTY_TYPE_TEXT = 'text'; const PROPERTY_TYPE_CHECKBOX = 'checkbox'; const PROPERTY_TYPE_TAGS = 'tags'; const PROPERTY_TYPE_VIDEO_LINK = 'video_link'; const PROPERTY_TYPE_SELECT = 'select'; const PROPERTY_TYPE_DATE = 'date'; const PROPERTY_TYPE_FILE = 'file'; const PROPERTY_TYPE_IMAGE = 'image'; /** * Список состояний типов объектов */ const TARGET_STATE_ACTIVE = 1; const TARGET_STATE_NOT_ACTIVE = 2; const TARGET_STATE_REMOVE = 3; protected $oMapper = null; /** * Список доступных типов полей * * @var array */ protected $aPropertyTypes = array( self::PROPERTY_TYPE_INT, self::PROPERTY_TYPE_FLOAT, self::PROPERTY_TYPE_VARCHAR, self::PROPERTY_TYPE_TEXT, self::PROPERTY_TYPE_CHECKBOX, self::PROPERTY_TYPE_TAGS, self::PROPERTY_TYPE_VIDEO_LINK, self::PROPERTY_TYPE_SELECT, self::PROPERTY_TYPE_DATE, self::PROPERTY_TYPE_FILE, self::PROPERTY_TYPE_IMAGE ); /** * Список разрешенных типов * На данный момент допустимы параметры entity=>ModuleTest_EntityTest - указывает на класс сущности * name=>Статьи * * @var array */ protected $aTargetTypes = array(); public function Init() { parent::Init(); $this->oMapper = Engine::GetMapper(__CLASS__); /** * Получаем типы из БД и активируем их */ if ($aTargetItems = $this->GetTargetItemsByFilter(array('state' => self::TARGET_STATE_ACTIVE))) { foreach ($aTargetItems as $oTarget) { $this->Property_AddTargetType($oTarget->getType(), $oTarget->getParams()); } } } /** * Возвращает список типов объектов * * @return array */ public function GetTargetTypes() { return $this->aTargetTypes; } /** * Добавляет в разрешенные новый тип * * @param string $sTargetType Тип * @param array $aParams Параметры * @return bool */ public function AddTargetType($sTargetType, $aParams = array()) { if (!array_key_exists($sTargetType, $this->aTargetTypes)) { $this->aTargetTypes[$sTargetType] = $aParams; return true; } return false; } /** * Проверяет разрешен ли данный тип * * @param string $sTargetType Тип * @return bool */ public function IsAllowTargetType($sTargetType) { return in_array($sTargetType, array_keys($this->aTargetTypes)); } /** * Возвращает парметры нужного типа * * @param string $sTargetType * * @return mixed */ public function GetTargetTypeParams($sTargetType) { if ($this->IsAllowTargetType($sTargetType)) { return $this->aTargetTypes[$sTargetType]; } } /** * Проверяет разрешен ли тип поля * * @param string $sType * * @return bool */ public function IsAllowPropertyType($sType) { return in_array($sType, $this->aPropertyTypes); } /** * Для каждого из свойств получает значение * * @param array $aProperties Список свойств * @param string $sTargetType Тип объекта * @param int $iTargetId ID объекта * * @return bool */ public function AttachValueForProperties($aProperties, $sTargetType, $iTargetId) { if (!$aProperties) { return false; } /** * Формируем список ID свойств */ $aPropertyIds = array(); foreach ($aProperties as $oProperty) { $aPropertyIds[] = $oProperty->getId(); } /** * Получаем список значений */ $aValues = $this->Property_GetValueItemsByFilter(array( 'target_id' => $iTargetId, 'target_type' => $sTargetType, 'property_id in' => $aPropertyIds, '#index-from' => 'property_id' )); /** * Аттачим значения к свойствам */ foreach ($aProperties as $oProperty) { if (isset($aValues[$oProperty->getId()])) { $oProperty->setValue($aValues[$oProperty->getId()]); } else { $oProperty->setValue(Engine::GetEntity('ModuleProperty_EntityValue', array( 'property_id' => $oProperty->getId(), 'property_type' => $oProperty->getType(), 'target_type' => $sTargetType, 'target_id' => $iTargetId ))); } $oProperty->getValue()->setProperty($oProperty); } return true; } /** * Сохраняет текущие значения свойств * * @param array $aProperties * @param Entity|int $oTarget Объект сущности или ID сущности */ public function UpdatePropertiesValue($aProperties, $oTarget) { if ($aProperties) { foreach ($aProperties as $oProperty) { $oValue = $oProperty->getValue(); $oValue->setTargetId(is_object($oTarget) ? $oTarget->getId() : $oTarget); $oValue->setPropertyType($oProperty->getType()); $oValue->Save(); } } } /** * Удаление всех свойств у конкретного объекта/сущности * * @param Entity $oTarget */ public function RemovePropertiesValue($oTarget) { $aProperties = $this->Property_GetPropertyItemsByFilter(array('target_type' => $oTarget->property->getPropertyTargetType())); if ($aProperties) { $this->AttachValueForProperties($aProperties, $oTarget->property->getPropertyTargetType(), $oTarget->getId()); foreach ($aProperties as $oProperty) { $oValue = $oProperty->getValue(); if ($oValue and $oValue->getId()) { $oValueType = $oValue->getValueTypeObject(); /** * Кастомное удаление */ $oValueType->removeValue(); /** * Удаляем основные данные */ $oValue->Delete(); } } } } /** * Валидирует значение свойств у объекта * * @param Entity $oTarget * * @return bool|string */ public function ValidateEntityPropertiesCheck($oTarget) { /** * Пробуем получить свойства из реквеста */ $oTarget->setProperties($oTarget->getProperties() ? $oTarget->getProperties() : getRequest('property')); $aPropertiesValue = $oTarget->getProperties(); $aPropertiesResult = array(); /** * Получаем весь список свойств у объекта */ $aPropertiesObject = $this->Property_GetPropertyItemsByFilter(array('target_type' => $oTarget->property->getPropertyTargetType())); $this->Property_AttachValueForProperties($aPropertiesObject, $oTarget->property->getPropertyTargetType(), $oTarget->getId()); foreach ($aPropertiesObject as $oProperty) { $oValue = $oProperty->getValue(); $sValue = isset($aPropertiesValue[$oProperty->getId()]) ? $aPropertiesValue[$oProperty->getId()] : null; /** * Валидируем значение */ $oValueType = $oValue->getValueTypeObject(); $oValueType->setValueForValidate($sValue); if (true === ($sRes = $oValueType->validate())) { $oValueType->setValue($oValueType->getValueForValidate()); $aPropertiesResult[$oProperty->getId()] = $oProperty; } else { return $this->Lang_Get('property.notices.validate_value_wrong', array('field' => $oProperty->getTitle())) . ($sRes ? $sRes : $this->Lang_Get('property.notices.validate_value_wrong_base')); } } $oTarget->setPropertiesObject($aPropertiesResult); return true; } /** * Возвращает значение свойсва у объекта * * @param Entity $oTarget Объект сущности * @param int $sPropertyId ID свойства * * @return null|mixed */ public function GetEntityPropertyValue($oTarget, $sPropertyId) { if ($oProperty = $this->GetEntityPropertyValueObject($oTarget, $sPropertyId)) { return $oProperty->getValue()->getValueForDisplay(); } return null; } /** * Возвращает объект свойства сущности * * @param Entity $oTarget Объект сущности * @param int $sPropertyId ID свойства * * @return null|ModuleProperty_EntityProperty */ public function GetEntityProperty($oTarget, $sPropertyId) { if ($oProperty = $this->GetEntityPropertyValueObject($oTarget, $sPropertyId)) { return $oProperty; } return null; } /** * Возвращает список свойств сущности * * @param Entity $oTarget Объект сущности * * @return array */ public function GetEntityPropertyList($oTarget) { $sTargetType = $oTarget->property->getPropertyTargetType(); /** * Проверяем зарегистрирован ли такой тип */ if (!$this->IsAllowTargetType($sTargetType)) { return array(); } if (!$oTarget->getPropertyIsLoadAll()) { $aProperties = $this->oMapper->GetPropertiesValueByTarget($oTarget->property->getPropertyTargetType(), $oTarget->getId()); $this->AttachPropertiesForTarget($oTarget, $aProperties); } return $oTarget->_getDataOne('property_list'); } /** * Служебный метод для аттача свойст к сущности * * @param Entity $oTarget Объект сущности * @param array $aProperties Список свойств */ public function AttachPropertiesForTarget($oTarget, $aProperties) { $oTarget->setPropertyList($aProperties); $oTarget->setPropertyIsLoadAll(true); $aMapperCode = array(); foreach ($aProperties as $oProperty) { $aMapperCode[$oProperty->getCode()] = $oProperty->getId(); } $oTarget->setPropertyMapperCode($aMapperCode); } /** * Возвращает объект свойства * * @param Entity $oTarget Объект сущности * @param array $sPropertyId ID свойства * * @return null */ public function GetEntityPropertyValueObject($oTarget, $sPropertyId) { if (!$oTarget->getPropertyIsLoadAll()) { /** * Загружаем все свойства */ $aProperties = $this->oMapper->GetPropertiesValueByTarget($oTarget->property->getPropertyTargetType(), $oTarget->getId()); $this->AttachPropertiesForTarget($oTarget, $aProperties); } if (!is_numeric($sPropertyId)) { $aMapperCode = $oTarget->getPropertyMapperCode(); if (isset($aMapperCode[$sPropertyId])) { $sPropertyId = $aMapperCode[$sPropertyId]; } else { return null; } } $aProperties = $oTarget->property->getPropertyList(); if (isset($aProperties[$sPropertyId])) { return $aProperties[$sPropertyId]; } return null; } /** * Переопределяем метод для возможности цеплять свои кастомные данные при ORM запросах - свойства * * @param array $aResult * @param array $aFilter * @param null|string $sEntityFull */ public function RewriteGetItemsByFilter($aResult, $aFilter = array(), $sEntityFull = null) { if (!$aResult) { return; } /** * Список на входе может быть двух видом: * 1 - одномерный массив * 2 - двумерный, если применялась группировка (использование '#index-group') * * Поэтому сначала сформируем линейный список */ if (isset($aFilter['#index-group']) and $aFilter['#index-group']) { $aEntitiesWork = array(); foreach ($aResult as $aItems) { foreach ($aItems as $oItem) { $aEntitiesWork[] = $oItem; } } } else { $aEntitiesWork = $aResult; } if (!$aEntitiesWork) { return; } $oEntityFirst = reset($aEntitiesWork); if (!$oEntityFirst->property) { return; } $sTargetType = $oEntityFirst->property->getPropertyTargetType(); /** * Проверяем зарегистрирован ли такой тип */ if (!$this->IsAllowTargetType($sTargetType)) { return; } /** * Проверяем необходимость цеплять свойства */ if (isset($aFilter['#properties']) and $aFilter['#properties']) { $aEntitiesId = array(); $aTargetTypes = array(); foreach ($aEntitiesWork as $oEntity) { $aEntitiesId[] = $oEntity->getId(); $aTargetTypes[] = $oEntity->getPropertyTargetType(); } $aTargetTypes = array_unique($aTargetTypes); /** * Получаем все свойства со значениями для всех объектов */ $aResult = $this->oMapper->GetPropertiesValueByTargetArray($aTargetTypes, $aEntitiesId); if ($aResult) { /** * Формируем список свойств и значений */ $aProperties = array(); $aValues = array(); foreach ($aResult as $aRow) { $aPropertyData = array(); $aValueData = array(); foreach ($aRow as $k => $v) { if (strpos($k, 'prop_') === 0) { $aPropertyData[str_replace('prop_', '', $k)] = $v; } else { $aValueData[$k] = $v; } } if (!isset($aProperties[$aRow['prop_id']])) { $oProperty = Engine::GetEntity('ModuleProperty_EntityProperty', $aPropertyData); $aProperties[$aRow['prop_id']] = $oProperty; } if ($aRow['target_id']) { $sKey = $aRow['property_id'] . '_' . $aRow['target_id']; $aValues[$sKey] = Engine::GetEntity('ModuleProperty_EntityValue', $aValueData); } } /** * Собираем данные */ foreach ($aEntitiesWork as $oEntity) { $aPropertiesClone = array(); foreach ($aProperties as $oProperty) { $oPropertyNew = clone $oProperty; $sKey = $oProperty->getId() . '_' . $oEntity->getId(); if (isset($aValues[$sKey])) { $oValue = $aValues[$sKey]; } else { $oValue = Engine::GetEntity('ModuleProperty_EntityValue', array( 'property_type' => $oProperty->getType(), 'property_id' => $oProperty->getId(), 'target_type' => $oProperty->getTargetType(), 'target_id' => $oEntity->getId() )); } $oPropertyNew->setValue($oValue); $oValue->setProperty($oPropertyNew); $aPropertiesClone[$oPropertyNew->getId()] = $oPropertyNew; } $this->AttachPropertiesForTarget($oEntity, $aPropertiesClone); } } } } /** * Обработка фильтра ORM запросов * * @param array $aFilter * @param array $sEntityFull * * @return array */ public function RewriteFilter($aFilter, $sEntityFull) { $oEntitySample = Engine::GetEntity($sEntityFull); if (!$oEntitySample->property) { return $aFilter; } if (!isset($aFilter['#join'])) { $aFilter['#join'] = array(); } $aPropFields = array(); foreach ($aFilter as $k => $v) { if (preg_match('@^#prop:(.+)$@i', $k, $aMatch)) { /** * Сначала формируем список полей с операндами */ $aK = explode(' ', trim($aMatch[1]), 2); $sPropCurrent = $aK[0]; $sConditionCurrent = ' = '; if (count($aK) > 1) { $sConditionCurrent = strtolower($aK[1]); } $aPropFields[$sPropCurrent] = array('value' => $v, 'condition' => $sConditionCurrent); } } /** * Проверяем на наличие сортировки по полям */ $aOrders = array(); if (isset($aFilter['#order'])) { if (!is_array($aFilter['#order'])) { $aFilter['#order'] = array($aFilter['#order']); } foreach ($aFilter['#order'] as $key => $value) { $aKeys = explode(':', $key); if (count($aKeys) == 2 and strtolower($aKeys[0]) == 'prop') { $aOrders[$aKeys[1]] = array('way' => $value, 'replace' => $key); } } } /** * Получаем данные по полям */ if ($aPropFields) { $sTargetType = $oEntitySample->property->getPropertyTargetType(); $aProperties = $this->Property_GetPropertyItemsByFilter(array( 'code in' => array_keys($aPropFields), 'target_type' => $sTargetType )); $iPropNum = 0; foreach ($aProperties as $oProperty) { /** * По каждому полю строим JOIN запрос */ $sCondition = $aPropFields[$oProperty->getCode()]['condition']; $bIsArray = in_array(strtolower($sCondition), array('in', 'not in')) ? true : false; if (in_array($oProperty->getType(), array(ModuleProperty::PROPERTY_TYPE_INT, ModuleProperty::PROPERTY_TYPE_CHECKBOX))) { $sFieldValue = "value_int"; $sConditionFull = $sCondition . ($bIsArray ? ' (?a) ' : ' ?d '); } elseif ($oProperty->getType() == ModuleProperty::PROPERTY_TYPE_FLOAT) { $sFieldValue = "value_float"; $sConditionFull = $sCondition . ($bIsArray ? ' (?a) ' : ' ?f '); } elseif (in_array($oProperty->getType(), array( ModuleProperty::PROPERTY_TYPE_VARCHAR, ModuleProperty::PROPERTY_TYPE_TAGS, ModuleProperty::PROPERTY_TYPE_VIDEO_LINK ))) { $sFieldValue = "value_varchar"; $sConditionFull = $sCondition . ($bIsArray ? ' (?a) ' : ' ? '); } elseif ($oProperty->getType() == ModuleProperty::PROPERTY_TYPE_TEXT) { $sFieldValue = "value_text"; $sConditionFull = $sCondition . ($bIsArray ? ' (?a) ' : ' ? '); } else { $sFieldValue = "value_varchar"; $sConditionFull = $sCondition . ($bIsArray ? ' (?a) ' : ' ? '); } $iPropNum++; $sJoin = "JOIN " . Config::Get('db.table.property_value') . " propv{$iPropNum} ON t.`{$oEntitySample->_getPrimaryKey()}` = propv{$iPropNum}.target_id and propv{$iPropNum}.target_type = '{$sTargetType}' and propv{$iPropNum}.property_id = {$oProperty->getId()} and propv{$iPropNum}.{$sFieldValue} {$sConditionFull}"; $aFilter['#join'][$sJoin] = array($aPropFields[$oProperty->getCode()]['value']); /** * Проверяем на сортировку по текущему полю */ if (isset($aOrders[$oProperty->getCode()])) { $aOrders[$oProperty->getCode()]['field'] = "propv{$iPropNum}.{$sFieldValue}"; } } } /** * Подменяем сортировку */ foreach ($aOrders as $aItem) { if (isset($aFilter['#order'][$aItem['replace']])) { $aFilter['#order'] = $this->ArrayReplaceKey($aFilter['#order'], $aItem['replace'], $aItem['field']); } } return $aFilter; } /** * Служебный метод для замены ключа в массиве * * @param array $aArray * @param string $sKeyOld * @param string $sKeyNew * * @return array|bool */ protected function ArrayReplaceKey($aArray, $sKeyOld, $sKeyNew) { $aKeys = array_keys($aArray); if (false === $iIndex = array_search($sKeyOld, $aKeys)) { return false; } $aKeys[$iIndex] = $sKeyNew; return array_combine($aKeys, array_values($aArray)); } /** * Удаляет теги свойства у сущности * * @param string $sTargetType Тип объекта сущности * @param int $iTargetId ID объекта сущности * @param int $iPropertyId ID свойства * * @return mixed */ public function RemoveValueTagsByTarget($sTargetType, $iTargetId, $iPropertyId) { // сбрасываем кеш $this->Cache_Clean(Zend_Cache::CLEANING_MODE_MATCHING_TAG, array('ModuleProperty_EntityValueTag_delete')); return $this->oMapper->RemoveValueTagsByTarget($sTargetType, $iTargetId, $iPropertyId); } /** * Удаляет значения типа select * * @param string $sTargetType Тип объекта сущности * @param int $iTargetId ID объекта сущности * @param int $iPropertyId ID свойства * * @return mixed */ public function RemoveValueSelectsByTarget($sTargetType, $iTargetId, $iPropertyId) { // сбрасываем кеш $this->Cache_Clean(Zend_Cache::CLEANING_MODE_MATCHING_TAG, array('ModuleProperty_EntityValueSelect_delete')); return $this->oMapper->RemoveValueSelectsByTarget($sTargetType, $iTargetId, $iPropertyId); } /** * Возвращает список тегов/знаяений свойства. Используется для авкомплиттера тегов. * * @param string $sTag * @param int $iPropertyId * @param int $iLimit * * @return mixed */ public function GetPropertyTagsByLike($sTag, $iPropertyId, $iLimit) { return $this->oMapper->GetPropertyTagsByLike($sTag, $iPropertyId, $iLimit); } /** * Возвращет список группированных тегов с их количеством для необходимого свойства * * @param int $iPropertyId * @param int $iLimit * * @return mixed */ public function GetPropertyTagsGroup($iPropertyId, $iLimit) { return $this->oMapper->GetPropertyTagsGroup($iPropertyId, $iLimit); } /** * Формирует и возвращает облако тегов необходимого свойства * * @param int $iPropertyId * @param int $iLimit * * @return mixed */ public function GetPropertyTagsCloud($iPropertyId, $iLimit) { $aTags = $this->Property_GetPropertyTagsGroup($iPropertyId, $iLimit); if ($aTags) { $this->Tools_MakeCloud($aTags); } return $aTags; } /** * Список ID сущностей по тегу конкретного свойства * * @param int $iPropertyId * @param string $sTag * @param int $iCurrPage * @param int $iPerPage * * @return array */ public function GetTargetsByTag($iPropertyId, $sTag, $iCurrPage, $iPerPage) { return array( 'collection' => $this->oMapper->GetTargetsByTag($iPropertyId, $sTag, $iCount, $iCurrPage, $iPerPage), 'count' => $iCount ); } /** * Производит изменение названия типа объекта, например "article" меняем на "news" * * @param $sType * @param $sTypeNew */ public function ChangeTargetType($sType, $sTypeNew) { $this->oMapper->UpdatePropertyByTargetType($sType, $sTypeNew); $this->oMapper->UpdatePropertyTargetByTargetType($sType, $sTypeNew); $this->oMapper->UpdatePropertySelectByTargetType($sType, $sTypeNew); $this->oMapper->UpdatePropertyValueByTargetType($sType, $sTypeNew); $this->oMapper->UpdatePropertyValueSelectByTargetType($sType, $sTypeNew); $this->oMapper->UpdatePropertyValueTagByTargetType($sType, $sTypeNew); /** * Сбрасываем кеши */ $this->Cache_Clean(Zend_Cache::CLEANING_MODE_MATCHING_TAG, array( 'ModuleProperty_EntityProperty_save', 'ModuleProperty_EntityTarget_save', 'ModuleProperty_EntitySelect_save', 'ModuleProperty_EntityValue_save', 'ModuleProperty_EntityValueSelect_save', 'ModuleProperty_EntityValueTag_save', )); } /** * Создает новый тип объекта в БД для дополнительных полей * * @param string $sType * @param array $aParams * @param bool $bRewrite * * @return bool|ModuleProperty_EntityTarget */ public function CreateTargetType($sType, $aParams, $bRewrite = false) { /** * Проверяем есть ли уже такой тип */ if ($oTarget = $this->GetTargetByType($sType)) { if (!$bRewrite) { return false; } } else { $oTarget = Engine::GetEntity('ModuleProperty_EntityTarget'); $oTarget->setType($sType); } $oTarget->setState(self::TARGET_STATE_ACTIVE); $oTarget->setParams($aParams); if ($oTarget->Save()) { return $oTarget; } return false; } /** * Отключает тип объекта для дополнительных полей * * @param string $sType * @param int $iState self::TARGET_STATE_NOT_ACTIVE или self::TARGET_STATE_REMOVE */ public function RemoveTargetType($sType, $iState = self::TARGET_STATE_NOT_ACTIVE) { if ($oTarget = $this->GetTargetByType($sType)) { $oTarget->setState($iState); $oTarget->Save(); } } /** * Возвращает набор полей/свойств для показа их на форме редактирования * * @param $sTargetType * @param $iTargetId * * @return mixed */ public function GetPropertiesForUpdate($sTargetType, $iTargetId) { /** * Проверяем зарегистрирован ли такой тип */ if (!$this->IsAllowTargetType($sTargetType)) { return array(); } /** * Получаем набор свойств */ $aProperties = $this->Property_GetPropertyItemsByFilter(array( 'target_type' => $sTargetType, '#order' => array('sort' => 'desc') )); $this->Property_AttachValueForProperties($aProperties, $sTargetType, $iTargetId); return $aProperties; } /** * Автоматическое создание дополнительного поля * TODO: учитывать $aAdditional для создание вариантов в типе select * * @param string $sTargetType Тип объекта дял которого добавляем поле * @param array $aData Данные поля: array('type'=>'int','title'=>'Название','code'=>'newfield','description'=>'Описание поля','sort'=>100); * @param bool $bSkipErrorUniqueCode Пропускать ошибку при дублировании кода поля (такое поле уже существует) * @param array $aValidateRules Данные валидатора поля, зависят от конкретного типа поля: array('allowEmpty'=>true,'max'=>1000) * @param array $aParams Дополнительные параметры поля, зависят от типа поля * @param array $aAdditional Дополнительные данные, которые нужно учитывать при создании поля, зависят от типа поля * * @return bool|ModuleProperty_EntityProperty */ public function CreateTargetProperty( $sTargetType, $aData, $bSkipErrorUniqueCode = true, $aValidateRules = array(), $aParams = array(), $aAdditional = array() ) { /** * Если необходимо и поле уже существует, то пропускаем создание */ if ($bSkipErrorUniqueCode and isset($aData['code']) and $this->GetPropertyByTargetTypeAndCode($sTargetType, $aData['code']) ) { return true; } $oProperty = Engine::GetEntity('ModuleProperty_EntityProperty'); $oProperty->_setValidateScenario('auto'); $oProperty->_setDataSafe($aData); $oProperty->setValidateRulesRaw($aValidateRules); $oProperty->setParamsRaw($aParams); $oProperty->setTargetType($sTargetType); if ($oProperty->_Validate()) { if ($oProperty->Add()) { return $oProperty; } else { return $this->Lang_Get('property.notices.create_error'); } } else { return $oProperty->_getValidateError(); } return false; } /** * Используется для создания дефолтных дополнительных полей при активации плагина * * @param array $aProperties Список полей *
     * array(
     *    array(
     *        'data'=>array(
     *        'type'=>ModuleProperty::PROPERTY_TYPE_INT,
     *        'title'=>'Номер',
     *        'code'=>'number',
     *        'sort'=>100
     *    ),
     *    'validate_rule'=>array(
     *        'min'=>10
     *    ),
     *    'params'=>array(),
     *    'additional'=>array()
     *    )
     * );
     * 
* @param string $sTargetType Тип объекта * * @return bool */ public function CreateDefaultTargetPropertyFromPlugin($aProperties, $sTargetType) { foreach ($aProperties as $aProperty) { $sResultMsg = $this->CreateTargetProperty($sTargetType, $aProperty['data'], true, $aProperty['validate_rule'], $aProperty['params'], $aProperty['additional']); if ($sResultMsg !== true and !is_object($sResultMsg)) { if (is_string($sResultMsg)) { $this->Message_AddErrorSingle($sResultMsg, $this->Lang_Get('common.error.error'), true); } /** * Отменяем добавление типа */ $this->RemoveTargetType($sTargetType, ModuleProperty::TARGET_STATE_NOT_ACTIVE); return false; } } return true; } public function RemoveValueByPropertyId($iPropertyId) { $bRes = $this->oMapper->RemoveValueByPropertyId($iPropertyId); $this->Cache_Clean(Zend_Cache::CLEANING_MODE_MATCHING_TAG, array('ModuleProperty_EntityValue_delete')); return $bRes; } public function RemoveValueTagByPropertyId($iPropertyId) { $bRes = $this->oMapper->RemoveValueTagByPropertyId($iPropertyId); $this->Cache_Clean(Zend_Cache::CLEANING_MODE_MATCHING_TAG, array('ModuleProperty_EntityValueTag_delete')); return $bRes; } public function RemoveValueSelectByPropertyId($iPropertyId) { $bRes = $this->oMapper->RemoveValueSelectByPropertyId($iPropertyId); $this->Cache_Clean(Zend_Cache::CLEANING_MODE_MATCHING_TAG, array('ModuleProperty_EntityValueSelect_delete')); return $bRes; } public function RemoveSelectByPropertyId($iPropertyId) { $bRes = $this->oMapper->RemoveSelectByPropertyId($iPropertyId); $this->Cache_Clean(Zend_Cache::CLEANING_MODE_MATCHING_TAG, array('ModuleProperty_EntitySelect_delete')); return $bRes; } public function CheckAllowTargetObject($sTargetType, $iTargetId, $aParams = array()) { $sMethod = 'CheckAllowTargetObject' . func_camelize($sTargetType); if (method_exists($this, $sMethod)) { if (!array_key_exists('user', $aParams)) { $aParams['user'] = $this->oUserCurrent; } return $this->$sMethod($iTargetId, $aParams); } /** * По умолчанию считаем доступ разрешен */ return true; } }