Skip to content

Instantly share code, notes, and snippets.

@ndm2
Last active October 10, 2016 09:23
Show Gist options
  • Star 1 You must be signed in to star a gist
  • Fork 1 You must be signed in to fork a gist
  • Save ndm2/87568a2ea0bd20ad8637b42ae1ac7add to your computer and use it in GitHub Desktop.
Save ndm2/87568a2ea0bd20ad8637b42ae1ac7add to your computer and use it in GitHub Desktop.
<?php
namespace App\Database\Expression;
use Cake\Database\Expression\FieldInterface;
use Cake\Database\Expression\FieldTrait;
use Cake\Database\ExpressionInterface;
use Cake\Database\Type\ExpressionTypeCasterTrait;
use Cake\Database\ValueBinder;
class MatchAgainstExpression implements ExpressionInterface, FieldInterface
{
use ExpressionTypeCasterTrait;
use FieldTrait;
const MODIFIER_BOOLEAN = 'IN BOOLEAN MODE';
const MODIFIER_NATURAL_LANGUAGE = 'IN NATURAL LANGUAGE MODE';
const MODIFIER_NATURAL_LANGUAGE_WITH_QUERY_EXPANSION = 'IN NATURAL LANGUAGE MODE WITH QUERY EXPANSION';
const MODIFIER_WITH_QUERY_EXPANSION = 'WITH QUERY EXPANSION';
protected $_modifier;
protected $_type;
protected $_value;
public function getFields()
{
$fields = $this->_field;
if (!is_array($this->_field)) {
$fields = [$this->_field];
}
return $fields;
}
public function getModifier()
{
return $this->_modifier;
}
public function setModifier($modifier)
{
$this->_modifier = $modifier;
}
public function getType()
{
return $this->_type;
}
public function setType($type)
{
$this->_type = $type;
}
public function getValue()
{
return $this->_value;
}
public function setValue($value)
{
$this->_value = $value;
}
public function __construct($fields, $value, $type = null, $modifier = null)
{
if ($type !== null) {
$value = $this->_castToExpression($value, $type);
}
$this->_field = $fields;
$this->_value = $value;
$this->_type = $type;
$this->_modifier = $modifier;
}
public function sql(ValueBinder $generator)
{
$fields = [];
foreach ($this->getFields() as $field) {
if ($field instanceof ExpressionInterface) {
$field = $field->sql($generator);
}
$fields[] = $field;
}
$value = $this->_value;
if ($value instanceof ExpressionInterface) {
$value = $value->sql($generator);
} else {
$value = $this->_bindValue($value, $generator, $this->_type);
}
$modifier = $this->_modifier;
if ($modifier) {
$modifier = ' ' . $modifier;
}
return sprintf(
'MATCH(%s) AGAINST(%s%s)',
implode(',', $fields),
$value,
$modifier
);
}
public function traverse(callable $callable)
{
foreach (array_merge($this->getFields(), [$this->_value]) as $part) {
if ($part instanceof ExpressionInterface) {
$callable($part);
$part->traverse($callable);
}
}
}
protected function _bindValue($value, ValueBinder $generator, $type)
{
$placeholder = $generator->placeholder('c');
$generator->bind($placeholder, $value, $type);
return $placeholder;
}
public function __clone()
{
$parts = ['_value'];
if (is_array($this->_field)) {
foreach ($this->_field as $key => $field) {
if ($this->_field[$key] instanceof ExpressionInterface) {
$this->_field[$key] = clone $this->_field[$key];
}
}
} else {
$parts[] = '_field';
}
foreach ($parts as $part) {
if ($this->{$part} instanceof ExpressionInterface) {
$this->{$part} = clone $this->{$part};
}
}
}
}
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment