SQL::Abstract::Limit 在 OR 逻辑上失败

发布于 2024-10-18 11:01:52 字数 1657 浏览 5 评论 0原文

我正在尝试使用 Class::DBI/Class::DBI::AbstractSearch。我的代码看起来像这样:

my $results = Example::CDBI::Quote->search_where(
    {   field_1 => {'like', $search_string},
        field_2 => {'like', $search_string}},
    {logic => 'or'}
);

根据 文档 这应该有效。它表示信息被传递到 SQL::Abstract::Limit,显示为采用 logic 参数。不幸的是,MySQL 在查询日志中显示以下内容(为简洁起见进行了编辑,并假设搜索“123”):

SELECT * FROM quote WHERE ((field_1 LIKE '123' AND field_2 LIKE '123' ))

我尝试将 'or' 更改为 'OR' (愚蠢,但值得一试)这不起作用。我还尝试寻找 SQL::Abstract::Limit 中的逻辑,但该运算符被传递给 SQL::Abstract

如何让 SQL::Abstract::Limit 接受来自 Class::DBIOR 逻辑?

Class::DBI 如何调用 SQL::Abstract::Limit
我能够确定 SQL::Abstract::Limit 是如何构建的。我用值代替变量名,这样更容易阅读。

my $sql = SQL::Abstract::Limit->new({'logic' => 'OR'});
my($phrase, @bind) = $sql->where(
    {'field_1'=>{'like' => '123'},'field_2'=>{'like'=>'123'}},
    undef, undef, undef);

I'm trying to create an OR logic query using Class::DBI/Class::DBI::AbstractSearch. My code looks something like this:

my $results = Example::CDBI::Quote->search_where(
    {   field_1 => {'like', $search_string},
        field_2 => {'like', $search_string}},
    {logic => 'or'}
);

According to the documentation this should work. It says that the information is passed to SQL::Abstract::Limit, which shows as taking the logic parameter. Unfortunately, MySQL shows the following in the query log (edited for brevity, and assuming a search of "123"):

SELECT * FROM quote WHERE ((field_1 LIKE '123' AND field_2 LIKE '123' ))

I have trying changing 'or' to 'OR' (silly, but worth a shot) which did not work. I also tried hunting down the logic in SQL::Abstract::Limit, but this operator is being passed to SQL::Abstract instead.

How do I get SQL::Abstract::Limit to accept OR logic from Class::DBI?

How Class::DBI calls SQL::Abstract::Limit
I was able to determine how SQL::Abstract::Limit is being constructed. I put values in instead of the variable names so it is easier to read.

my $sql = SQL::Abstract::Limit->new({'logic' => 'OR'});
my($phrase, @bind) = $sql->where(
    {'field_1'=>{'like' => '123'},'field_2'=>{'like'=>'123'}},
    undef, undef, undef);

如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。

扫码二维码加入Web技术交流群

发布评论

需要 登录 才能够评论, 你可以免费 注册 一个本站的账号。

评论(1

随遇而安 2024-10-25 11:01:52

您可以像这样在本地应用 OR:

use SQL::Abstract;

my $sql = SQL::Abstract->new;
my ($stmt, @bind) = $sql->where(
    { -or => [ { field_1 => { 'like', 'John' }},
               { field_2 => { 'like', 'John' }},
             ],
    }, []);

$stmt 中给出:

WHERE ( ( field_1 LIKE ? OR field_2 LIKE ? ) ) 

logic 属性可以在 SQL::Abstract 构造函数中设置,但我不这样做不知道如何从 Class::DBI 传播。

编辑:我不知道这是错误还是功能,但由 logic 子句更改的运算符似乎仅在使用 arrayrefs 定义时才适用。使用 hashrefs,您总是可以使用 AND:

my $sql_and = SQL::Abstract::Limit->new(logic => 'AND');
my $sql_or  = SQL::Abstract::Limit->new(logic => 'OR');

say $sql_and->where(['field_1'=>{'like' => '123'},'field_2'=>{'like'=>'123'}]);  
# WHERE ( ( field_1 LIKE ? AND field_2 LIKE ? ) )

say $sql_or->where (['field_1'=>{'like' => '123'},'field_2'=>{'like'=>'123'}]);  
# WHERE ( ( field_1 LIKE ? OR field_2 LIKE ? ) )

或者,使用 Class::DBI:

my $results = Example::CDBI::Quote->search_where(
    [   field_1 => {'like', $search_string},
        field_2 => {'like', $search_string}],
    {logic => 'or'}
);

You can apply OR locally like this:

use SQL::Abstract;

my $sql = SQL::Abstract->new;
my ($stmt, @bind) = $sql->where(
    { -or => [ { field_1 => { 'like', 'John' }},
               { field_2 => { 'like', 'John' }},
             ],
    }, []);

gives in $stmt:

WHERE ( ( field_1 LIKE ? OR field_2 LIKE ? ) ) 

The logic property can be set in SQL::Abstract constructor, but I don't have idea how to propagate from Class::DBI.

Edit: I don't know if it is bug or feature, but it the operators changed by logic clause seems apply only when you define with arrayrefs. With hashrefs, you get always AND:

my $sql_and = SQL::Abstract::Limit->new(logic => 'AND');
my $sql_or  = SQL::Abstract::Limit->new(logic => 'OR');

say $sql_and->where(['field_1'=>{'like' => '123'},'field_2'=>{'like'=>'123'}]);  
# WHERE ( ( field_1 LIKE ? AND field_2 LIKE ? ) )

say $sql_or->where (['field_1'=>{'like' => '123'},'field_2'=>{'like'=>'123'}]);  
# WHERE ( ( field_1 LIKE ? OR field_2 LIKE ? ) )

Or, to work with Class::DBI:

my $results = Example::CDBI::Quote->search_where(
    [   field_1 => {'like', $search_string},
        field_2 => {'like', $search_string}],
    {logic => 'or'}
);
~没有更多了~
我们使用 Cookies 和其他技术来定制您的体验包括您的登录状态等。通过阅读我们的 隐私政策 了解更多相关信息。 单击 接受 或继续使用网站,即表示您同意使用 Cookies 和您的相关数据。
原文