[英]Wrong query generated by PostgreSQL provider to Entity Framework for Contains and Concat
我正在使用EF连接到PostgreSQL。 EF是5.0版,Npgsql是2.0.14.3。
我要运行的查询是:
var list = new List<string> { "test" };
var res = from t in db.Test
where !list.Contains(string.Concat(t.test1, "_", t.test2))
select t;
res.ToList();
生成的查询类似于:
SELECT "Extent1"."id" AS "id","Extent1"."test1" AS "test1","Extent1"."test2" AS "test2" FROM "public"."test" AS "Extent1" WHERE 'test'!="Extent1"."test1" || '_' || "Extent1"."test2"
当我运行它时,我得到一个错误: argument of WHERE must be type boolean, not type text
。
但是,当我将!=
更改为=
它可以工作。 当我在Postgres中的连接字符串周围添加一个括号,但无法更改EF生成的查询时,它也起作用。
解决方法是,我将第二个(虚拟)元素添加到列表中,因为随后EF生成了一些不同的查询,但这不是一个很好的解决方案……
这是pgSQL中的错误吗? 还是在EF提供程序中? 您能为这个问题提出更好的解决方案吗?
更多信息
表脚本:
CREATE TABLE test
(
test1 character varying(255),
test2 character varying(255),
id integer NOT NULL,
CONSTRAINT "PK" PRIMARY KEY (id)
)
WITH (
OIDS=FALSE
);
该表的类:
[Table("test", Schema = "public")]
public class Test
{
[Key]
public int id { get; set; }
public string test1 { get; set; }
public string test2 { get; set; }
}
App.config中:
<?xml version="1.0" encoding="utf-8"?>
<configuration>
<configSections>
<section name="entityFramework" type="System.Data.Entity.Internal.ConfigFile.EntityFrameworkSection, EntityFramework, Version=4.4.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089" requirePermission="false" />
</configSections>
<entityFramework>
<defaultConnectionFactory type="System.Data.Entity.Infrastructure.SqlConnectionFactory, EntityFramework" />
</entityFramework>
<connectionStrings>
<add name="local" connectionString="Server=localhost;Port=5432;Database=test;User Id=user;Password=password;" providerName="Npgsql" />
</connectionStrings>
<system.data>
<DbProviderFactories>
<add name="Npgsql Data Provider" invariant="Npgsql" description="Data Provider for PostgreSQL" type="Npgsql.NpgsqlFactory, Npgsql" />
</DbProviderFactories>
</system.data>
<startup>
<supportedRuntime version="v4.0" sku=".NETFramework,Version=v4.0" />
</startup>
</configuration>
是的,那是EF提供程序Npgsql中的错误。
据http://www.postgresql.org/docs/9.3/static/sql-syntax-lexical.html#SQL-PRECEDENCE-TABLE , !=
和||
在(any other)
,这意味着它们具有相同的优先级。 它们也保持关联,因此查询将被解析为
SELECT ... FROM "public"."test" AS "Extent1"
WHERE ((('test'!="Extent1"."test1") || '_') || "Extent1"."test2")
这是错误的。 正确的解析是
SELECT ... FROM "public"."test" AS "Extent1"
WHERE ('test'!=(("Extent1"."test1" || '_') || "Extent1"."test2"))
=
优先级比!=
低,因此可以使用。
此请求的修复程序包含在https://github.com/npgsql/Npgsql/pull/256的拉取请求中。
声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.