Merged in upgrade_and_refactoring (pull request #29)
Updating dependencies and implementing ILIKE for DQL.
This commit is contained in:
commit
a722dd4653
|
@ -19,6 +19,7 @@
|
||||||
"sentry/sentry-symfony": "^2.2",
|
"sentry/sentry-symfony": "^2.2",
|
||||||
"symfony/console": "^4.1",
|
"symfony/console": "^4.1",
|
||||||
"symfony/dotenv": "^4.1",
|
"symfony/dotenv": "^4.1",
|
||||||
|
"symfony/expression-language": "^4.1",
|
||||||
"symfony/flex": "^1.0",
|
"symfony/flex": "^1.0",
|
||||||
"symfony/form": "^4.1",
|
"symfony/form": "^4.1",
|
||||||
"symfony/framework-bundle": "^4.1",
|
"symfony/framework-bundle": "^4.1",
|
||||||
|
|
972
composer.lock
generated
972
composer.lock
generated
File diff suppressed because it is too large
Load diff
|
@ -41,3 +41,6 @@ doctrine:
|
||||||
dir: '%kernel.project_dir%/src/Magnetico/Entity'
|
dir: '%kernel.project_dir%/src/Magnetico/Entity'
|
||||||
prefix: 'App\Magnetico'
|
prefix: 'App\Magnetico'
|
||||||
alias: Magnetico
|
alias: Magnetico
|
||||||
|
dql:
|
||||||
|
string_functions:
|
||||||
|
ILIKE: 'App\Doctrine\ORM\AST\Ilike'
|
||||||
|
|
|
@ -43,4 +43,4 @@ services:
|
||||||
# Torrent searcher
|
# Torrent searcher
|
||||||
App\Search\TorrentSearcher:
|
App\Search\TorrentSearcher:
|
||||||
arguments:
|
arguments:
|
||||||
$em: '@doctrine.orm.magneticod_entity_manager'
|
$classMetadata: '@=service(''doctrine.orm.magneticod_entity_manager'').getClassMetadata(''App\\Magnetico\\Entity\\Torrent'')'
|
||||||
|
|
73
src/Doctrine/ORM/AST/BaseFunction.php
Normal file
73
src/Doctrine/ORM/AST/BaseFunction.php
Normal file
|
@ -0,0 +1,73 @@
|
||||||
|
<?php
|
||||||
|
|
||||||
|
declare(strict_types=1);
|
||||||
|
|
||||||
|
namespace App\Doctrine\ORM\AST;
|
||||||
|
|
||||||
|
use Doctrine\ORM\Query\{AST\Functions\FunctionNode, AST\Node, Lexer, Parser, SqlWalker};
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @since 0.1
|
||||||
|
*
|
||||||
|
* @author Martin Georgiev <martin.georgiev@gmail.com>
|
||||||
|
* @see https://github.com/martin-georgiev/postgresql-for-doctrine
|
||||||
|
*/
|
||||||
|
abstract class BaseFunction extends FunctionNode
|
||||||
|
{
|
||||||
|
/** @var string */
|
||||||
|
protected $functionPrototype;
|
||||||
|
|
||||||
|
/** @var string[] */
|
||||||
|
protected $nodesMapping = [];
|
||||||
|
|
||||||
|
/** @var Node[] */
|
||||||
|
protected $nodes = [];
|
||||||
|
|
||||||
|
abstract protected function customiseFunction(): void;
|
||||||
|
|
||||||
|
protected function setFunctionPrototype(string $functionPrototype): void
|
||||||
|
{
|
||||||
|
$this->functionPrototype = $functionPrototype;
|
||||||
|
}
|
||||||
|
|
||||||
|
protected function addNodeMapping(string $parserMethod): void
|
||||||
|
{
|
||||||
|
$this->nodesMapping[] = $parserMethod;
|
||||||
|
}
|
||||||
|
|
||||||
|
public function parse(Parser $parser): void
|
||||||
|
{
|
||||||
|
$this->customiseFunction();
|
||||||
|
|
||||||
|
$parser->match(Lexer::T_IDENTIFIER);
|
||||||
|
$parser->match(Lexer::T_OPEN_PARENTHESIS);
|
||||||
|
$this->feedParserWithNodes($parser);
|
||||||
|
$parser->match(Lexer::T_CLOSE_PARENTHESIS);
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Feeds given parser with previously set nodes.
|
||||||
|
*/
|
||||||
|
protected function feedParserWithNodes(Parser $parser): void
|
||||||
|
{
|
||||||
|
$nodesMappingCount = \count($this->nodesMapping);
|
||||||
|
$lastNode = $nodesMappingCount - 1;
|
||||||
|
for ($i = 0; $i < $nodesMappingCount; $i++) {
|
||||||
|
$parserMethod = $this->nodesMapping[$i];
|
||||||
|
$this->nodes[$i] = $parser->{$parserMethod}();
|
||||||
|
if ($i < $lastNode) {
|
||||||
|
$parser->match(Lexer::T_COMMA);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
public function getSql(SqlWalker $sqlWalker): string
|
||||||
|
{
|
||||||
|
$dispatched = [];
|
||||||
|
foreach ($this->nodes as $node) {
|
||||||
|
$dispatched[] = $node->dispatch($sqlWalker);
|
||||||
|
}
|
||||||
|
|
||||||
|
return \vsprintf($this->functionPrototype, $dispatched);
|
||||||
|
}
|
||||||
|
}
|
25
src/Doctrine/ORM/AST/Ilike.php
Normal file
25
src/Doctrine/ORM/AST/Ilike.php
Normal file
|
@ -0,0 +1,25 @@
|
||||||
|
<?php
|
||||||
|
|
||||||
|
declare(strict_types=1);
|
||||||
|
|
||||||
|
namespace App\Doctrine\ORM\AST;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Implementation of PostgreSql ILIKE().
|
||||||
|
*
|
||||||
|
* For usage example @see https://github.com/martin-georgiev/postgresql-for-doctrine/blob/master/docs/USE-CASES-AND-EXAMPLES.md
|
||||||
|
*
|
||||||
|
* @see https://www.postgresql.org/docs/9.3/functions-matching.html
|
||||||
|
*
|
||||||
|
* @author llaakkkk <lenakirichokv@gmail.com>
|
||||||
|
* @see https://github.com/martin-georgiev/postgresql-for-doctrine
|
||||||
|
*/
|
||||||
|
class Ilike extends BaseFunction
|
||||||
|
{
|
||||||
|
protected function customiseFunction(): void
|
||||||
|
{
|
||||||
|
$this->setFunctionPrototype('%s ilike %s');
|
||||||
|
$this->addNodeMapping('StringPrimary');
|
||||||
|
$this->addNodeMapping('StringPrimary');
|
||||||
|
}
|
||||||
|
}
|
|
@ -2,9 +2,8 @@
|
||||||
|
|
||||||
namespace App\Search;
|
namespace App\Search;
|
||||||
|
|
||||||
use App\Magnetico\Entity\Torrent;
|
|
||||||
use App\Magnetico\Repository\TorrentRepository;
|
use App\Magnetico\Repository\TorrentRepository;
|
||||||
use Doctrine\ORM\{EntityManagerInterface, QueryBuilder};
|
use Doctrine\ORM\{Mapping\ClassMetadata, QueryBuilder};
|
||||||
|
|
||||||
class TorrentSearcher
|
class TorrentSearcher
|
||||||
{
|
{
|
||||||
|
@ -13,13 +12,13 @@ class TorrentSearcher
|
||||||
/** @var TorrentRepository */
|
/** @var TorrentRepository */
|
||||||
private $torrentRepo;
|
private $torrentRepo;
|
||||||
|
|
||||||
/** @var EntityManagerInterface */
|
/** @var ClassMetadata */
|
||||||
private $em;
|
private $classMetadata;
|
||||||
|
|
||||||
public function __construct(TorrentRepository $torrentRepo, EntityManagerInterface $em)
|
public function __construct(TorrentRepository $torrentRepo, ClassMetadata $classMetadata)
|
||||||
{
|
{
|
||||||
$this->torrentRepo = $torrentRepo;
|
$this->torrentRepo = $torrentRepo;
|
||||||
$this->em = $em;
|
$this->classMetadata = $classMetadata;
|
||||||
}
|
}
|
||||||
|
|
||||||
public function createSearchQueryBuilder(string $query, string $orderBy = null, string $order = 'asc'): QueryBuilder
|
public function createSearchQueryBuilder(string $query, string $orderBy = null, string $order = 'asc'): QueryBuilder
|
||||||
|
@ -40,7 +39,7 @@ class TorrentSearcher
|
||||||
$where = $qb->expr()->andX();
|
$where = $qb->expr()->andX();
|
||||||
|
|
||||||
foreach ($this->splitQueryToParts($query) as $idx => $part) {
|
foreach ($this->splitQueryToParts($query) as $idx => $part) {
|
||||||
$where->add($qb->expr()->like('LOWER(t.name)', ':part_'.$idx));
|
$where->add('ILIKE(t.name , :part_'.$idx.') = TRUE');
|
||||||
$qb->setParameter('part_'.$idx, '%'.strtolower($part).'%');
|
$qb->setParameter('part_'.$idx, '%'.strtolower($part).'%');
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -64,7 +63,7 @@ class TorrentSearcher
|
||||||
{
|
{
|
||||||
return (
|
return (
|
||||||
!\in_array($orderBy, self::ORDER_DISABLED_FIELDS, true)
|
!\in_array($orderBy, self::ORDER_DISABLED_FIELDS, true)
|
||||||
&& $this->em->getClassMetadata(Torrent::class)->hasField($orderBy)
|
&& $this->classMetadata->hasField($orderBy)
|
||||||
);
|
);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -76,4 +75,4 @@ class TorrentSearcher
|
||||||
|
|
||||||
return explode(' ', $query);
|
return explode(' ', $query);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
|
@ -158,6 +158,9 @@
|
||||||
"symfony/event-dispatcher-contracts": {
|
"symfony/event-dispatcher-contracts": {
|
||||||
"version": "v1.1.5"
|
"version": "v1.1.5"
|
||||||
},
|
},
|
||||||
|
"symfony/expression-language": {
|
||||||
|
"version": "v4.3.5"
|
||||||
|
},
|
||||||
"symfony/filesystem": {
|
"symfony/filesystem": {
|
||||||
"version": "v4.1.0"
|
"version": "v4.1.0"
|
||||||
},
|
},
|
||||||
|
|
Binary file not shown.
Loading…
Reference in a new issue