I need to add a dynamic condition to the catalog price rules.
For example:
- Special Price From Date equals or greater than TODAY
I think it is not a big deal once figure out the right files to be edited, I just need a couple of hint ...
UPDATE:
I managed to save the value {TODAY}
.
The only change required is the edit to the following function in Mage_Rule_Model_Condition_Abstract
public function getValue()
{
if ($this->getInputType() == 'date' && !$this->getIsValueParsed() && $this->getData('value') == '{TODAY}') {
$this->setIsValueParsed(true);
}
if ($this->getInputType() == 'date' && !$this->getIsValueParsed() && $this->getData('value') != '{TODAY}') {
// date format intentionally hard-coded
$this->setValue(
Mage::app()->getLocale()->date($this->getData('value'),
Varien_Date::DATE_INTERNAL_FORMAT, null, false)->toString(Varien_Date::DATE_INTERNAL_FORMAT)
);
$this->setIsValueParsed(true);
}
return $this->getData('value');
}
So the next step is to find the place where the value is used in the rule processing.
UPDATE-2
I have managed to make the value dynamic during the validation
It looks that the condition is evaluated in Mage_Rule_Model_Condition_Abstract::validateAttribute($validatedValue)
$validatedValue
is the product attribute value that we want to evaluate.
In the same class we can change the following method in order to use our custom variable
{TODAY} for the validation.
public function getValueParsed()
{
if (!$this->hasValueParsed()) {
$value = $this->getData('value');
if ($value == '{TODAY}') {
$value = Mage::app()->getLocale()->date(Mage::getModel('core/date')->date(),
Varien_Date::DATE_INTERNAL_FORMAT, null, false)->toString(Varien_Date::DATE_INTERNAL_FORMAT);
} else if ($this->isArrayOperatorType() && is_string($value)) {
$value = preg_split('#\s*[,;]\s*#', $value, null, PREG_SPLIT_NO_EMPTY);
}
$this->setValueParsed($value);
}
return $this->getData('value_parsed');
}
UPDATE-3
The modification to this function looks the last effort (Modifications done in Update-2 should not be necessary)
Mage_Rule_Model_Condition_Product_Abstract
public function validate(Varien_Object $object)
{
$attrCode = $this->getAttribute();
if ('category_ids' == $attrCode) {
return $this->validateAttribute($object->getAvailableInCategories());
} elseif (! isset($this->_entityAttributeValues[$object->getId()])) {
if (!$object->getResource()) {
return false;
}
$attr = $object->getResource()->getAttribute($attrCode);
if ($attr && $attr->getBackendType() == 'datetime' && $this->getValue() == '{TODAY}') {
$today = Mage::getModel('core/date')->date();
$today = Mage::app()->getLocale()->date($today,
Varien_Date::DATE_INTERNAL_FORMAT, null, false)->toString(Varien_Date::DATE_INTERNAL_FORMAT);
$this->setValue($today);
}
if ($attr && $attr->getBackendType() == 'datetime' && !is_int($this->getValue()) && $this->getValue() != '{TODAY}') {
$this->setValue(strtotime($this->getValue()));
$value = strtotime($object->getData($attrCode));
return $this->validateAttribute($value);
}
if ($attr && $attr->getFrontendInput() == 'multiselect') {
$value = $object->getData($attrCode);
$value = strlen($value) ? explode(',', $value) : array();
return $this->validateAttribute($value);
}
return parent::validate($object);
} else {
$result = false; // any valid value will set it to TRUE
// remember old attribute state
$oldAttrValue = $object->hasData($attrCode) ? $object->getData($attrCode) : null;
foreach ($this->_entityAttributeValues[$object->getId()] as $storeId => $value) {
$attr = $object->getResource()->getAttribute($attrCode);
if ($attr && $attr->getBackendType() == 'datetime') {
$value = strtotime($value);
} else if ($attr && $attr->getFrontendInput() == 'multiselect') {
$value = strlen($value) ? explode(',', $value) : array();
}
$object->setData($attrCode, $value);
$result |= parent::validate($object);
if ($result) {
break;
}
}
if (is_null($oldAttrValue)) {
$object->unsetData($attrCode);
} else {
$object->setData($attrCode, $oldAttrValue);
}
return (bool) $result;
}
}
UPDATE-4
There is still one issue:
The second time I save the rule the {TODAY}
variable is changed into a date (this is caused by some JS but I'm not able to understand witch one )