Skip to content
This repository has been archived by the owner on Jan 21, 2020. It is now read-only.

Commit

Permalink
Extract type cast behaviour and add support for the immutable datetim…
Browse files Browse the repository at this point in the history
…e field types
  • Loading branch information
zluiten committed Sep 16, 2019
1 parent cca97a6 commit b20a1a0
Show file tree
Hide file tree
Showing 9 changed files with 219 additions and 110 deletions.
4 changes: 4 additions & 0 deletions config/module.config.php
Original file line number Diff line number Diff line change
Expand Up @@ -6,6 +6,8 @@

namespace ZF\Doctrine\QueryBuilder;

use Zend\ServiceManager\Factory\InvokableFactory;

return [
'service_manager' => [
'aliases' => [
Expand All @@ -19,6 +21,8 @@
Filter\Service\ODMFilterManager::class => Filter\Service\ODMFilterManagerFactory::class,
OrderBy\Service\ORMOrderByManager::class => OrderBy\Service\ORMOrderByManagerFactory::class,
OrderBy\Service\ODMOrderByManager::class => OrderBy\Service\ODMOrderByManagerFactory::class,
Filter\ORM\TypeCaster::class => InvokableFactory::class,
Filter\ODM\TypeCaster::class => InvokableFactory::class,
],
],
];
81 changes: 23 additions & 58 deletions src/Filter/ODM/AbstractFilter.php
Original file line number Diff line number Diff line change
Expand Up @@ -6,74 +6,39 @@

namespace ZF\Doctrine\QueryBuilder\Filter\ODM;

use DateTime;
use ZF\Doctrine\QueryBuilder\Filter\FilterInterface;
use ZF\Doctrine\QueryBuilder\Filter\TypeCast\TypeCastInterface;

abstract class AbstractFilter implements FilterInterface
{
abstract public function filter($queryBuilder, $metadata, $option);

protected function typeCastField($metadata, $field, $value, $format = null, $doNotTypecastDatetime = false)
protected $typeCaster;

public function __construct($params)
{
if (! isset($metadata->fieldMappings[$field])) {
return $value;
if (isset($params[1])) {
$this->setTypeCaster($params[1]);
}
}

switch ($metadata->fieldMappings[$field]['type']) {
case 'int':
settype($value, 'integer');
break;
case 'boolean':
settype($value, 'boolean');
break;
case 'float':
settype($value, 'float');
break;
case 'string':
settype($value, 'string');
break;
case 'bin_data_custom':
break;
case 'bin_data_func':
break;
case 'bin_data_md5':
break;
case 'bin_data':
break;
case 'bin_data_uuid':
break;
case 'collection':
break;
case 'custom_id':
break;
case 'date':
if ($value && ! $doNotTypecastDatetime) {
if (! $format) {
$format = 'Y-m-d H:i:s';
}
$value = DateTime::createFromFormat($format, $value);
}
break;
case 'file':
break;
case 'hash':
break;
case 'id':
break;
case 'increment':
break;
case 'key':
break;
case 'object_id':
break;
case 'raw_type':
break;
case 'timestamp':
break;
default:
break;
public function getTypeCaster()
{
if ($this->typeCaster === null) {
$this->typeCaster = new TypeCaster();
}

return $value;
return $this->typeCaster;
}

public function setTypeCaster(TypeCastInterface $typeCaster)
{
$this->typeCaster = $typeCaster;
return $this;
}

protected function typeCastField($metadata, $field, $value, $format = null, $doNotTypecastDatetime = false)
{
return $this->getTypeCaster()->typeCastField($metadata, $field, $value, $format, $doNotTypecastDatetime);
}
}
77 changes: 77 additions & 0 deletions src/Filter/ODM/TypeCaster.php
Original file line number Diff line number Diff line change
@@ -0,0 +1,77 @@
<?php
/**
* @license http://opensource.org/licenses/BSD-3-Clause BSD-3-Clause
* @copyright Copyright (c) 2014 Zend Technologies USA Inc. (http://www.zend.com)
*/

namespace ZF\Doctrine\QueryBuilder\Filter\ODM;

use DateTime;
use ZF\Doctrine\QueryBuilder\Filter\TypeCast\TypeCastInterface;

class TypeCaster implements TypeCastInterface
{
public function typeCastField($metadata, $field, $value, $format, $doNotTypecastDatetime = false)
{
if (! isset($metadata->fieldMappings[$field])) {
return $value;
}

switch ($metadata->fieldMappings[$field]['type']) {
case 'int':
settype($value, 'integer');
break;
case 'boolean':
settype($value, 'boolean');
break;
case 'float':
settype($value, 'float');
break;
case 'string':
settype($value, 'string');
break;
case 'bin_data_custom':
break;
case 'bin_data_func':
break;
case 'bin_data_md5':
break;
case 'bin_data':
break;
case 'bin_data_uuid':
break;
case 'collection':
break;
case 'custom_id':
break;
case 'date':
if ($value && ! $doNotTypecastDatetime) {
if (! $format) {
$format = 'Y-m-d H:i:s';
}
$value = DateTime::createFromFormat($format, $value);
}
break;
case 'file':
break;
case 'hash':
break;
case 'id':
break;
case 'increment':
break;
case 'key':
break;
case 'object_id':
break;
case 'raw_type':
break;
case 'timestamp':
break;
default:
break;
}

return $value;
}
}
70 changes: 20 additions & 50 deletions src/Filter/ORM/AbstractFilter.php
Original file line number Diff line number Diff line change
Expand Up @@ -6,19 +6,24 @@

namespace ZF\Doctrine\QueryBuilder\Filter\ORM;

use DateTime;
use ZF\Doctrine\QueryBuilder\Filter\FilterInterface;
use ZF\Doctrine\QueryBuilder\Filter\Service\ORMFilterManager;
use ZF\Doctrine\QueryBuilder\Filter\TypeCast\TypeCastInterface;

abstract class AbstractFilter implements FilterInterface
{
abstract public function filter($queryBuilder, $metadata, $option);

protected $filterManager;

protected $typeCaster;

public function __construct($params)
{
$this->setFilterManager($params[0]);
if (isset($params[1])) {
$this->setTypeCaster($params[1]);
}
}

public function setFilterManager(ORMFilterManager $filterManager)
Expand All @@ -32,58 +37,23 @@ public function getFilterManager()
return $this->filterManager;
}

protected function typeCastField($metadata, $field, $value, $format, $doNotTypecastDatetime = false)
public function getTypeCaster()
{
if (! isset($metadata->fieldMappings[$field])) {
return $value;
if ($this->typeCaster === null) {
$this->typeCaster = new TypeCaster();
}

switch ($metadata->fieldMappings[$field]['type']) {
case 'string':
settype($value, 'string');
break;
case 'integer':
case 'smallint':
#case 'bigint': // Don't try to manipulate bigints?
settype($value, 'integer');
break;
case 'boolean':
settype($value, 'boolean');
break;
case 'decimal':
case 'float':
settype($value, 'float');
break;
case 'date':
// For dates set time to midnight
if ($value && ! $doNotTypecastDatetime) {
if (! $format) {
$format = 'Y-m-d';
}
$value = DateTime::createFromFormat($format, $value);
$value = DateTime::createFromFormat('Y-m-d H:i:s', $value->format('Y-m-d') . ' 00:00:00');
}
break;
case 'time':
if ($value && ! $doNotTypecastDatetime) {
if (! $format) {
$format = 'H:i:s';
}
$value = DateTime::createFromFormat($format, $value);
}
break;
case 'datetime':
if ($value && ! $doNotTypecastDatetime) {
if (! $format) {
$format = 'Y-m-d H:i:s';
}
$value = DateTime::createFromFormat($format, $value);
}
break;
default:
break;
}
return $this->typeCaster;
}

return $value;
public function setTypeCaster(TypeCastInterface $typeCaster)
{
$this->typeCaster = $typeCaster;
return $this;
}

protected function typeCastField($metadata, $field, $value, $format, $doNotTypecastDatetime = false)
{
return $this->getTypeCaster()->typeCastField($metadata, $field, $value, $format, $doNotTypecastDatetime);
}
}
68 changes: 68 additions & 0 deletions src/Filter/ORM/TypeCaster.php
Original file line number Diff line number Diff line change
@@ -0,0 +1,68 @@
<?php
/**
* @license http://opensource.org/licenses/BSD-3-Clause BSD-3-Clause
* @copyright Copyright (c) 2014 Zend Technologies USA Inc. (http://www.zend.com)
*/

namespace ZF\Doctrine\QueryBuilder\Filter\ORM;

use DateTime;
use ZF\Doctrine\QueryBuilder\Filter\TypeCast\TypeCastInterface;

class TypeCaster implements TypeCastInterface
{
public function typeCastField($metadata, $field, $value, $format, $doNotTypecastDatetime = false)
{
if (! isset($metadata->fieldMappings[$field])) {
return $value;
}

switch ($metadata->fieldMappings[$field]['type']) {
case 'string':
settype($value, 'string');
break;
case 'integer':
case 'smallint':
#case 'bigint': // Don't try to manipulate bigints?
settype($value, 'integer');
break;
case 'boolean':
settype($value, 'boolean');
break;
case 'decimal':
case 'float':
settype($value, 'float');
break;
case 'date':
// For dates set time to midnight
if ($value && ! $doNotTypecastDatetime) {
if (! $format) {
$format = 'Y-m-d';
}
$value = DateTime::createFromFormat($format, $value);
$value = DateTime::createFromFormat('Y-m-d H:i:s', $value->format('Y-m-d') . ' 00:00:00');
}
break;
case 'time':
if ($value && ! $doNotTypecastDatetime) {
if (! $format) {
$format = 'H:i:s';
}
$value = DateTime::createFromFormat($format, $value);
}
break;
case 'datetime':
if ($value && ! $doNotTypecastDatetime) {
if (! $format) {
$format = 'Y-m-d H:i:s';
}
$value = DateTime::createFromFormat($format, $value);
}
break;
default:
break;
}

return $value;
}
}
5 changes: 4 additions & 1 deletion src/Filter/Service/ODMFilterManager.php
Original file line number Diff line number Diff line change
Expand Up @@ -12,6 +12,7 @@
use Zend\ServiceManager\AbstractPluginManager;
use Zend\ServiceManager\Exception;
use ZF\Doctrine\QueryBuilder\Filter\FilterInterface;
use ZF\Doctrine\QueryBuilder\Filter\ODM\TypeCaster;

class ODMFilterManager extends AbstractPluginManager
{
Expand All @@ -27,7 +28,9 @@ public function filter(QueryBuilder $queryBuilder, Metadata $metadata, $filters)
throw new RuntimeException('Array element "type" is required for all filters');
}

$filter = $this->get(strtolower($option['type']), [$this]);
$typeCaster = $this->serviceLocator->get(TypeCaster::class);

$filter = $this->get(strtolower($option['type']), [$this, $typeCaster]);
$filter->filter($queryBuilder, $metadata, $option);
}
}
Expand Down
5 changes: 4 additions & 1 deletion src/Filter/Service/ORMFilterManager.php
Original file line number Diff line number Diff line change
Expand Up @@ -11,6 +11,7 @@
use Zend\ServiceManager\AbstractPluginManager;
use Zend\ServiceManager\Exception;
use ZF\Doctrine\QueryBuilder\Filter\FilterInterface;
use ZF\Doctrine\QueryBuilder\Filter\ORM\TypeCaster;

class ORMFilterManager extends AbstractPluginManager
{
Expand All @@ -26,7 +27,9 @@ public function filter(QueryBuilder $queryBuilder, $metadata, $filters)
throw new RuntimeException('Array element "type" is required for all filters');
}

$filter = $this->get(strtolower($option['type']), [$this]);
$typeCaster = $this->serviceLocator->get(TypeCaster::class);

$filter = $this->get(strtolower($option['type']), [$this, $typeCaster]);
$filter->filter($queryBuilder, $metadata, $option);
}
}
Expand Down
Loading

0 comments on commit b20a1a0

Please sign in to comment.