Servicestack 自动查询自定义约定不适用于 PostgreSQL
Servicestack autoquery custom convention doesn't work with PostgreSQL
我定义了新的隐式约定
autoQuery.ImplicitConventions.Add("%WithinLastDays", "{Field} > NOW() - INTERVAL '{Value} days'");
问题是对于 postgres 连接,查询被错误翻译成
WHERE "TABLE"."FIELD" > NOW() - INTERVAL ':0 days'
并且它不向数据库发送参数。在内置约定的情况下,它工作正常。
更新
我试图定义 EndsWithConvention 但存在同样的问题 - 参数未传递给 pgsql 引擎(但它在 SqlExpression 中可用)
autoQuery.EndsWithConventions
.Add("WithinLastDays", new QueryDbFieldAttribute() { Template= "{Field} >= CURRENT_DATE - {Value}", ValueFormat= "interval '{0} days ago'" });
autoQuery.EndsWithConventions
.Add("WithinLastDays", new QueryDbFieldAttribute() { Template= "{Field} >= CURRENT_DATE - interval '{Value}'", ValueFormat= "{0} days ago" });
更新 2
下面的定义导致 PostgresException: 42601: błąd składni w lub blisko "$1" (抱歉波兰语错误)
autoQuery.EndsWithConventions.Add("WithinLastDays", new QueryDbFieldAttribute() { Template= "{Field} >= CURRENT_DATE - interval {Value}", ValueFormat= "{0} days ago" });
生成的查询是
SELECT here columns
FROM table
WHERE table."publication_date" >= CURRENT_DATE - interval
LIMIT 100
更新 3
autoQuery.EndsWithConventions.Add("WithinLastDays", new QueryDbFieldAttribute() { Template= "{Field} >= CURRENT_DATE - {Value}", ValueFormat= "interval {0} 'days ago'" });
生成
SELECT ...
FROM ...
WHERE ...."publication_date" >= CURRENT_DATE -
并发出 PostgresException: 42883: operator doesn't exist: date - text
这是 dto 定义
[Route("/search/tenders")]
public class FindTenders : QueryDb<TenderSearchResult>
{
public int? PublicationDateWithinLastDays { get; set; }
}
型号:
public class EntitiySearchResult
{
public DateTime PublicationDate { get; set; }
}
最终解决方案
@mythz 解决了在我的原始查询中使用 interval 子句的注册问题和问题。下面的定义可以很好地获取从现在起过去 X 天内的记录。谢谢@mythz
var autoQuery = new AutoQueryFeature() { MaxLimit = 100 };
autoQuery.EndsWithConventions.Add("WithinLastDays", new QueryDbFieldAttribute
{
Template = "{Field} >= CURRENT_DATE + {Value}::interval",
ValueFormat = "{0} days ago"
});
{Value}
被 db 参数替换,如果你想改变你 need to use ValueFormat 的 db 参数的值,例如ValueFormat="{0} days"
.
要定义 ValueFormat
格式,您需要 register an EndsWithConventions 的隐式约定,例如:
autoQuery.EndsWithConventions.Add("WithinLastDays", new QueryDbFieldAttribute {
Template= "{Field} >= CURRENT_DATE + {Value}::interval",
ValueFormat= "{0} days ago"
});
另请注意,您可能需要 CURRENT_DATE + interval
而不是 -
。
我定义了新的隐式约定
autoQuery.ImplicitConventions.Add("%WithinLastDays", "{Field} > NOW() - INTERVAL '{Value} days'");
问题是对于 postgres 连接,查询被错误翻译成
WHERE "TABLE"."FIELD" > NOW() - INTERVAL ':0 days'
并且它不向数据库发送参数。在内置约定的情况下,它工作正常。
更新
我试图定义 EndsWithConvention 但存在同样的问题 - 参数未传递给 pgsql 引擎(但它在 SqlExpression 中可用)
autoQuery.EndsWithConventions
.Add("WithinLastDays", new QueryDbFieldAttribute() { Template= "{Field} >= CURRENT_DATE - {Value}", ValueFormat= "interval '{0} days ago'" });
autoQuery.EndsWithConventions
.Add("WithinLastDays", new QueryDbFieldAttribute() { Template= "{Field} >= CURRENT_DATE - interval '{Value}'", ValueFormat= "{0} days ago" });
更新 2 下面的定义导致 PostgresException: 42601: błąd składni w lub blisko "$1" (抱歉波兰语错误)
autoQuery.EndsWithConventions.Add("WithinLastDays", new QueryDbFieldAttribute() { Template= "{Field} >= CURRENT_DATE - interval {Value}", ValueFormat= "{0} days ago" });
生成的查询是
SELECT here columns
FROM table
WHERE table."publication_date" >= CURRENT_DATE - interval
LIMIT 100
更新 3
autoQuery.EndsWithConventions.Add("WithinLastDays", new QueryDbFieldAttribute() { Template= "{Field} >= CURRENT_DATE - {Value}", ValueFormat= "interval {0} 'days ago'" });
生成
SELECT ...
FROM ...
WHERE ...."publication_date" >= CURRENT_DATE -
并发出 PostgresException: 42883: operator doesn't exist: date - text
这是 dto 定义
[Route("/search/tenders")]
public class FindTenders : QueryDb<TenderSearchResult>
{
public int? PublicationDateWithinLastDays { get; set; }
}
型号:
public class EntitiySearchResult
{
public DateTime PublicationDate { get; set; }
}
最终解决方案 @mythz 解决了在我的原始查询中使用 interval 子句的注册问题和问题。下面的定义可以很好地获取从现在起过去 X 天内的记录。谢谢@mythz
var autoQuery = new AutoQueryFeature() { MaxLimit = 100 };
autoQuery.EndsWithConventions.Add("WithinLastDays", new QueryDbFieldAttribute
{
Template = "{Field} >= CURRENT_DATE + {Value}::interval",
ValueFormat = "{0} days ago"
});
{Value}
被 db 参数替换,如果你想改变你 need to use ValueFormat 的 db 参数的值,例如ValueFormat="{0} days"
.
要定义 ValueFormat
格式,您需要 register an EndsWithConventions 的隐式约定,例如:
autoQuery.EndsWithConventions.Add("WithinLastDays", new QueryDbFieldAttribute {
Template= "{Field} >= CURRENT_DATE + {Value}::interval",
ValueFormat= "{0} days ago"
});
另请注意,您可能需要 CURRENT_DATE + interval
而不是 -
。