繁体   English   中英

INET_ATON在where语句doctrine2 querybuilder zend2中

[英]INET_ATON in where statement doctrine2 querybuilder zend2

问题:我想在Doctrine2中使用querybuilder运行查询,例如:

SELECT * FROM TABLE WHERE `column1` = 'x' and (`column2` = INET_ATON('1.1.1.1') OR `column3` like '%bla%'...)

我该如何在Zend2中使用Doctrine2?

我尝试了这个:

$where->add($qb->expr()->eq('column2', $qb->expr()->literal('inet_aton('1.1.1.1'))));

但这不起作用。 原则仍然在inet_aton函数周围添加引号。

好吧,我自己弄清楚了:

您应该做的几件事:

首先做一个DQL功能

<?php

namespace Application\DQL;

use Doctrine\ORM\Query\Lexer;

class InetAtonFunction extends \Doctrine\ORM\Query\AST\Functions\FunctionNode
{
    public $valueExpression = null;

    /**
     * parse
     *
     * @param \Doctrine\ORM\Query\Parser $parser
     * @access public
     * @return void
     */
    public function parse(\Doctrine\ORM\Query\Parser $parser)
    {
        $parser->match(Lexer::T_IDENTIFIER);
        $parser->match(Lexer::T_OPEN_PARENTHESIS);
        $this->valueExpression = $parser->StringPrimary();
        $parser->match(Lexer::T_CLOSE_PARENTHESIS);
    }

    /**
     * getSql
     *
     * @param \Doctrine\ORM\Query\SqlWalker $sqlWalker
     * @access public
     * @return string
     */
    public function getSql(\Doctrine\ORM\Query\SqlWalker $sqlWalker)
    {
        return 'INET_ATON('. $this->valueExpression->dispatch($sqlWalker) . ')'; 
    }
}

之后,将功能添加到Doctrine ORM

<?php
namespace Observer;

//...

class Module implements
    AutoloaderProviderInterface,
    ConfigProviderInterface,
    ServiceProviderInterface
{
//...
    public function onBootstrap($e)
    {

        $application = $e->getParam('application');
        $sm  = $application->getServiceManager();
        $em  = $application->getEventManager();

        $entityManager = $sm->get('doctrine.entitymanager.orm_default');
        $entityManager->getConfiguration()->addCustomStringFunction('inet_aton', 'Application\DQL\InetAtonFunction');       
    }
...

在此之后,您就可以开始了。 现在,您可以使用querybuilder运行查询,例如

SELECT whatever FROM someting where cloumn = inet_aton(:?)

我希望这对在Doctrine和Zend Framework2中具有特殊功能的其他人有所帮助

只是更新的答案:(对于新的SF版本)

创建DQL函数后(请参见旧文章),

我们想要像这样在Yaml(config.yml)中注册自定义DQL类:

doctrine:
    dbal:
        driver:   "%database_driver%"
        host:     "%database_host%"
        port:     "%database_port%"
        dbname:   "%database_name%"
        user:     "%database_user%"
        password: "%database_password%"

    orm:
        auto_generate_proxy_classes: "%kernel.debug%"
        auto_mapping: true
        dql:
            string_functions:
                inet_aton: home\myBundle\myFolderContaintClass\InetAton

这是解释在这里正式的Symfony文档上。

这个问题似乎是等同于ROUND()Doctrine 2 DQL MySQL的副本吗?

您需要为此实现一个自定义DQL函数

DoctrineExtensions中有一些示例。

您可以像下面这样实现:

<?php

namespace MyApp\DQL;

use Doctrine\ORM\Query\AST\Functions\FunctionNode;
use Doctrine\ORM\Query\Lexer;
use Doctrine\ORM\Query\SqlWalker;

class InetAnon extends FunctionNode
{
    private $arithmeticExpression;

    public function getSql(SqlWalker $sqlWalker)
    {

        return 'INET_ANON(' . $sqlWalker->walkSimpleArithmeticExpression(
            $this->arithmeticExpression
        ) . ')';
    }

    public function parse(\Doctrine\ORM\Query\Parser $parser)
    {

        $lexer = $parser->getLexer();

        $parser->match(Lexer::T_IDENTIFIER);
        $parser->match(Lexer::T_OPEN_PARENTHESIS);

        $this->arithmeticExpression = $parser->SimpleArithmeticExpression();

        $parser->match(Lexer::T_CLOSE_PARENTHESIS);
    }
}

然后,您可以在引导ORM时在配置中注册它:

$config = new \Doctrine\ORM\Configuration();

$config->addCustomNumericFunction('INET_ANON', 'MyApp\DQL\InetAnon');

暂无
暂无

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM