class ClosureExpressionVisitor in Plug 7
Walks an expression graph and turns it into a PHP closure.
This closure can be used with {@Collection#filter()} and is used internally by {@ArrayCollection#select()}.
@author Benjamin Eberlei <kontakt@beberlei.de> @since 2.3
Hierarchy
- class \Doctrine\Common\Collections\Expr\ExpressionVisitor
- class \Doctrine\Common\Collections\Expr\ClosureExpressionVisitor
Expanded class hierarchy of ClosureExpressionVisitor
2 files declare their use of ClosureExpressionVisitor
- ArrayCollection.php in lib/
doctrine/ collections/ lib/ Doctrine/ Common/ Collections/ ArrayCollection.php - ClosureExpressionVisitorTest.php in lib/
doctrine/ collections/ tests/ Doctrine/ Tests/ Common/ Collections/ ClosureExpressionVisitorTest.php
File
- lib/
doctrine/ collections/ lib/ Doctrine/ Common/ Collections/ Expr/ ClosureExpressionVisitor.php, line 31
Namespace
Doctrine\Common\Collections\ExprView source
class ClosureExpressionVisitor extends ExpressionVisitor {
/**
* Accesses the field of a given object. This field has to be public
* directly or indirectly (through an accessor get*, is*, or a magic
* method, __get, __call).
*
* @param object $object
* @param string $field
*
* @return mixed
*/
public static function getObjectFieldValue($object, $field) {
if (is_array($object)) {
return $object[$field];
}
$accessors = array(
'get',
'is',
);
foreach ($accessors as $accessor) {
$accessor .= $field;
if (!method_exists($object, $accessor)) {
continue;
}
return $object
->{$accessor}();
}
// __call should be triggered for get.
$accessor = $accessors[0] . $field;
if (method_exists($object, '__call')) {
return $object
->{$accessor}();
}
if ($object instanceof \ArrayAccess) {
return $object[$field];
}
return $object->{$field};
}
/**
* Helper for sorting arrays of objects based on multiple fields + orientations.
*
* @param string $name
* @param int $orientation
* @param \Closure $next
*
* @return \Closure
*/
public static function sortByField($name, $orientation = 1, \Closure $next = null) {
if (!$next) {
$next = function () {
return 0;
};
}
return function ($a, $b) use ($name, $next, $orientation) {
$aValue = ClosureExpressionVisitor::getObjectFieldValue($a, $name);
$bValue = ClosureExpressionVisitor::getObjectFieldValue($b, $name);
if ($aValue === $bValue) {
return $next($a, $b);
}
return ($aValue > $bValue ? 1 : -1) * $orientation;
};
}
/**
* {@inheritDoc}
*/
public function walkComparison(Comparison $comparison) {
$field = $comparison
->getField();
$value = $comparison
->getValue()
->getValue();
// shortcut for walkValue()
switch ($comparison
->getOperator()) {
case Comparison::EQ:
return function ($object) use ($field, $value) {
return ClosureExpressionVisitor::getObjectFieldValue($object, $field) === $value;
};
case Comparison::NEQ:
return function ($object) use ($field, $value) {
return ClosureExpressionVisitor::getObjectFieldValue($object, $field) !== $value;
};
case Comparison::LT:
return function ($object) use ($field, $value) {
return ClosureExpressionVisitor::getObjectFieldValue($object, $field) < $value;
};
case Comparison::LTE:
return function ($object) use ($field, $value) {
return ClosureExpressionVisitor::getObjectFieldValue($object, $field) <= $value;
};
case Comparison::GT:
return function ($object) use ($field, $value) {
return ClosureExpressionVisitor::getObjectFieldValue($object, $field) > $value;
};
case Comparison::GTE:
return function ($object) use ($field, $value) {
return ClosureExpressionVisitor::getObjectFieldValue($object, $field) >= $value;
};
case Comparison::IN:
return function ($object) use ($field, $value) {
return in_array(ClosureExpressionVisitor::getObjectFieldValue($object, $field), $value);
};
case Comparison::NIN:
return function ($object) use ($field, $value) {
return !in_array(ClosureExpressionVisitor::getObjectFieldValue($object, $field), $value);
};
case Comparison::CONTAINS:
return function ($object) use ($field, $value) {
return false !== strpos(ClosureExpressionVisitor::getObjectFieldValue($object, $field), $value);
};
default:
throw new \RuntimeException("Unknown comparison operator: " . $comparison
->getOperator());
}
}
/**
* {@inheritDoc}
*/
public function walkValue(Value $value) {
return $value
->getValue();
}
/**
* {@inheritDoc}
*/
public function walkCompositeExpression(CompositeExpression $expr) {
$expressionList = array();
foreach ($expr
->getExpressionList() as $child) {
$expressionList[] = $this
->dispatch($child);
}
switch ($expr
->getType()) {
case CompositeExpression::TYPE_AND:
return $this
->andExpressions($expressionList);
case CompositeExpression::TYPE_OR:
return $this
->orExpressions($expressionList);
default:
throw new \RuntimeException("Unknown composite " . $expr
->getType());
}
}
/**
* @param array $expressions
*
* @return callable
*/
private function andExpressions($expressions) {
return function ($object) use ($expressions) {
foreach ($expressions as $expression) {
if (!$expression($object)) {
return false;
}
}
return true;
};
}
/**
* @param array $expressions
*
* @return callable
*/
private function orExpressions($expressions) {
return function ($object) use ($expressions) {
foreach ($expressions as $expression) {
if ($expression($object)) {
return true;
}
}
return false;
};
}
}
Members
Name | Modifiers | Type | Description | Overrides |
---|---|---|---|---|
ClosureExpressionVisitor:: |
private | function | ||
ClosureExpressionVisitor:: |
public static | function | Accesses the field of a given object. This field has to be public directly or indirectly (through an accessor get*, is*, or a magic method, __get, __call). | |
ClosureExpressionVisitor:: |
private | function | ||
ClosureExpressionVisitor:: |
public static | function | Helper for sorting arrays of objects based on multiple fields + orientations. | |
ClosureExpressionVisitor:: |
public | function |
Converts a comparison expression into the target query language output. Overrides ExpressionVisitor:: |
|
ClosureExpressionVisitor:: |
public | function |
Converts a composite expression into the target query language output. Overrides ExpressionVisitor:: |
|
ClosureExpressionVisitor:: |
public | function |
Converts a value expression into the target query language part. Overrides ExpressionVisitor:: |
|
ExpressionVisitor:: |
public | function | Dispatches walking an expression to the appropriate handler. |