Skip to content

Commit

Permalink
Using magic funciton __call to help create any arbitrary SQL function
Browse files Browse the repository at this point in the history
  • Loading branch information
lorenzo committed Nov 18, 2013
1 parent 4730e77 commit 9cc7a05
Show file tree
Hide file tree
Showing 2 changed files with 30 additions and 10 deletions.
36 changes: 28 additions & 8 deletions Cake/Database/FunctionsBuilder.php
Expand Up @@ -34,7 +34,7 @@ class FunctionsBuilder {
* @param array $types list of types for each function param
* @return FunctionExpression
*/
public function func($name, $params = [], $types = []) {
protected function _build($name, $params = [], $types = []) {
return new FunctionExpression($name, $params, $types);
}

Expand All @@ -53,7 +53,7 @@ protected function _literalArgumentFunction($name, $expression, $types = []) {
} else {
$expression = [$expression => 'literal'];
}
return $this->func($name, $expression, $types);
return $this->_build($name, $expression, $types);
}

/**
Expand Down Expand Up @@ -119,7 +119,7 @@ public function count($expression, $types = []) {
* @return FunctionExpression
*/
public function concat($args, $types = []) {
return $this->func('CONCAT', $args, $types);
return $this->_build('CONCAT', $args, $types);
}

/**
Expand All @@ -130,7 +130,7 @@ public function concat($args, $types = []) {
* @return FunctionExpression
*/
public function coalesce($args, $types = []) {
return $this->func('COALESCE', $args, $types);
return $this->_build('COALESCE', $args, $types);
}

/**
Expand All @@ -142,7 +142,7 @@ public function coalesce($args, $types = []) {
* @return FunctionExpression
*/
public function dateDiff($dates, $types = []) {
return $this->func('DATEDIFF', $dates, $types);
return $this->_build('DATEDIFF', $dates, $types);
}

/**
Expand All @@ -155,13 +155,33 @@ public function dateDiff($dates, $types = []) {
*/
public function now($type = 'datetime') {
if ($type === 'datetime') {
return $this->func('NOW');
return $this->_build('NOW');
}
if ($type === 'date') {
return $this->func('CURRENT_DATE');
return $this->_build('CURRENT_DATE');
}
if ($type === 'time') {
return $this->func('CURRENT_TIME');
return $this->_build('CURRENT_TIME');
}
}

/**
* Magic method dispatcher to create custom SQL function calls
*
* @param string $name the SQL function name to construct
* @param array $args list with up to 2 arguments, first one being an array with
* parameters for the SQL function and second one a list of types to bind to those
* params
* @return \Cake\Database\FunctionExpression
*/
public function __call($name, $args) {
switch (count($args)) {
case 0:
return $this->_build($name);
case 1:
return $this->_build($name, $args[0]);
default:
return $this->_build($name, $args[0], $args[1]);
}
}

Expand Down
4 changes: 2 additions & 2 deletions Cake/Test/TestCase/Database/FunctionsBuilderTest.php
Expand Up @@ -40,8 +40,8 @@ public function setUp() {
*
* @return void
*/
public function testFunc() {
$function = $this->functions->func('MyFunc', ['b' => 'literal']);
public function testArbitrary() {
$function = $this->functions->MyFunc(['b' => 'literal']);
$this->assertInstanceOf('\Cake\Database\Expression\FunctionExpression', $function);
$this->assertEquals('MyFunc', $function->name());
$this->assertEquals('MyFunc(b)', $function->sql(new ValueBinder));
Expand Down

0 comments on commit 9cc7a05

Please sign in to comment.