ERROR: operator does not exist: date = character varying

huangapple go评论118阅读模式
英文:

ERROR: operator does not exist: date = character varying

问题

I have this problem:

在PostgreSQL PG Admin中,这个查询工作正常:

SELECT ST_AsGeoJSON(t1.*) as extent FROM ricepest.forecast t1 where state = 'Andhra Pradesh' AND dist = 'Ananthapur' AND date_id = '2023-01-01';

但在Spring Boot中使用Hibernate,我编写了一个类似于这样的服务:

@Query(nativeQuery = true, value = "SELECT ST_AsGeoJSON(t1.*) as extent FROM ricepest.state t1 where state = :val")
List<GetFeature> getFeatureByStateIdService(@Param("val") String val);

@Query(nativeQuery = true, value = "SELECT ST_AsGeoJSON(t1.*) as extent FROM ricepest.district t1 where state = :state_val AND dist = :dist_val")
List<GetFeature> getFeatureByStateIdService(@Param("state_val") String state_val, @Param("dist_val") String dist_val);

@Query(nativeQuery = true, value = "SELECT ST_AsGeoJSON(t1.*) as extent FROM ricepest.forecast t1 where state = :state_val AND dist = :dist_val AND date_id = :from_date")
List<GetFeature> getFeatureByStateIdService(@Param("state_val") String state_val, @Param("dist_val") String dist_val, @Param("from_date") String from_date);

public static interface GetFeature {
    String getExtent();
}

这是我的Java控制器:

@PostMapping(value = "/feature")
public ResponseEntity<List<GetFeature>> getFeatureByStateIdService(@RequestBody RequestInputs reqInputs) {
    System.out.println("The state and district input value for getFeature : " + reqInputs.getState_id() + " and " + reqInputs.getDist() + " and " + reqInputs.getFromdate_id());
    List<GetFeature> extent;
    if (reqInputs.getDist().equalsIgnoreCase("0") || reqInputs.getDist().equalsIgnoreCase("-- SELECT DISTRICT--")) {
        extent = pestServiceRepository.getFeatureByStateIdService(reqInputs.getState_id());
    } else if (reqInputs.getFromdate_id().equalsIgnoreCase("0") || reqInputs.getFromdate_id().equalsIgnoreCase("-- SELECT DATE--")) {
        extent = pestServiceRepository.getFeatureByStateIdService(reqInputs.getDist());
    } else {
        extent = pestServiceRepository.getFeatureByStateIdService(reqInputs.getState_id(), reqInputs.getDist(), reqInputs.getFromdate_id());
    }
    if (!extent.isEmpty()) {
        return new ResponseEntity<>(extent, HttpStatus.OK);
    } else {
        return new ResponseEntity<>(HttpStatus.NOT_FOUND);
    }
}

我遇到了这个错误:

ERROR: operator does not exist: date = character varying
  Hint: No operator matches the given name and argument types. You might need to add explicit type casts.

我不明白出了什么问题。任何帮助将不胜感激。

英文:

I have this problem:

this query in PostgreSQL PG Admin work fine:

SELECT ST_AsGeoJSON(t1.\*) as extent FROM ricepest.forecast t1 where state = &#39;Andhra Pradesh&#39; AND dist = &#39;Ananthapur&#39; AND date_id = &#39;2023-01-01&#39;;

but in spring-boot with hibernate i wrote a service like this:

@Query(nativeQuery = true, value = &quot;SELECT ST_AsGeoJSON(t1.*) as extent FROM ricepest.state t1 where state = :val&quot;)
	List&lt;GetFeature&gt; getFeatureByStateIdService(@Param(&quot;val&quot;) String val);
	
	@Query(nativeQuery = true, value = &quot;SELECT ST_AsGeoJSON(t1.*) as extent FROM ricepest.district t1 where state = :state_val AND dist = :dist_val&quot;)
	List&lt;GetFeature&gt; getFeatureByStateIdService(@Param(&quot;state_val&quot;) String state_val, @Param(&quot;dist_val&quot;) String dist_val);
	
	@Query(nativeQuery = true, value = &quot;SELECT ST_AsGeoJSON(t1.*) as extent FROM ricepest.forecast t1 where state = :state_val AND dist = :dist_val AND date_id = :from_date&quot;)
	List&lt;GetFeature&gt; getFeatureByStateIdService(@Param(&quot;state_val&quot;) String state_val, @Param(&quot;dist_val&quot;) String dist_val, @Param(&quot;from_date&quot;) String from_date);
	
	public static interface GetFeature {
		String getExtent();
	}

This is my java Controller:

@PostMapping(value = &quot;/feature&quot;)
	public ResponseEntity&lt;List&lt;GetFeature&gt;&gt; getFeatureByStateIdService(@RequestBody RequestInputs reqInputs) {
		System.out.println(&quot;The state and district input value for getFeature : &quot; + reqInputs.getState_id() + &quot; and &quot; + reqInputs.getDist() + &quot; and &quot; + reqInputs.getFromdate_id());
		List&lt;GetFeature&gt; extent;
		if (reqInputs.getDist().equalsIgnoreCase(&quot;0&quot;) || reqInputs.getDist().equalsIgnoreCase(&quot;-- SELECT DISTRICT--&quot;)) {
			extent = pestServiceRepository.getFeatureByStateIdService(reqInputs.getState_id());
		} else if (reqInputs.getFromdate_id().equalsIgnoreCase(&quot;0&quot;) || reqInputs.getFromdate_id().equalsIgnoreCase(&quot;-- SELECT DATE--&quot;)) {
			extent = pestServiceRepository.getFeatureByStateIdService(reqInputs.getDist());
		} else {
			extent = pestServiceRepository.getFeatureByStateIdService(reqInputs.getState_id(), reqInputs.getDist(), reqInputs.getFromdate_id());
		}
		if (!extent.isEmpty()) {
			return new ResponseEntity&lt;&gt;(extent, HttpStatus.OK);
		} else {
			return new ResponseEntity&lt;&gt;(HttpStatus.NOT_FOUND);
		}
	}

I have this ERROR:

ERROR: operator does not exist: date = character varying
  Hint: No operator matches the given name and argument types. You might need to add explicit type casts.

I am not getting what has went wrong. Any help would be appreciated.

答案1

得分: 3

在pgAdmin中,文字&#39;2023-01-01&#39;被解析为日期值,而不是文本值,这是由于表达式的上下文。在使用Spring Boot和Hibernate的Java代码中,参数已明确指定为String类。在比较之前,PostgreSQL不会对文本值执行隐式转换为日期值。解析SQL语句和评估带有明确参数的语句之间存在根本区别。要么将参数传递为日期,要么在查询中明确将文本值转换为日期。将参数传递为所需的类型是首选方法。

以下语句可以在pgAdmin中运行,演示了这些差异:

-- 因为&#39;2023-06-06&#39;被解析为日期,所以此查询不会引发异常
SELECT current_date = &#39;2023-06-06&#39;;

-- 因为test_date明确为日期,所以此查询不会引发异常
-- 这类似于将日期值传递给参数化查询
WITH t(test_date) AS (
  VALUES (&#39;2023-06-06&#39;::date)
)
SELECT current_date = t.test_date
FROM t;

-- 由于类型差异,此查询将引发异常
-- 没有上下文会导致PostgreSQL将&#39;2023-06-06&#39;解析为日期
WITH t(test_date) AS (
  VALUES (&#39;2023-06-06&#39;)
)
SELECT current_date = t.test_date
FROM t;

-- 由于明确的类型转换,此查询不会引发异常
-- 这类似于传递字符串并在SELECT语句中明确将其转换为日期
WITH t(test_date) AS (
  VALUES (&#39;2023-06-06&#39;)
)
SELECT current_date = t.test_date::date
FROM t;

希望这对您有所帮助。

英文:

In pgAdmin, the literal &#39;2023-01-01&#39; is being parsed as a date value, not a text value, because of the context of the expression. In the Java code with Spring Boot and Hibernate, the parameter has been explicitly specified to be of class String. PostgreSQL doesn't perform implicit conversions of text values to date values prior to the comparison. There is a fundamental difference between parsing a SQL statement and evaluating a statement with explicit parameters. Either pass the parameter as a date, or explicitly cast the text value to a date in the query. Passing the parameter as the intended type is the preferred approach.

The following statements, which can be run in pgAdmin, demonstrate the differences:

-- because &#39;2023-06-06&#39; is parsed as a date, this query will not raise an exception
SELECT current_date = &#39;2023-06-06&#39;;

-- because test_date is explicitely made a date, this query will not raise an exception
-- this is analogous to passing a date value to a parameterized query
WITH t(test_date) AS (
  VALUES (&#39;2023-06-06&#39;::date)
)
SELECT current_date = t.test_date
FROM t;

-- this query will raise an exception due to type differences
-- there is no context to cause PostgreSQL to parse &#39;2023-06-06&#39; as a date
WITH t(test_date) AS (
  VALUES (&#39;2023-06-06&#39;)
)
SELECT current_date = t.test_date
FROM t;

-- because of the explicit type cast, this query will not raise an exception
-- this is similar to passing a string and explicitly casting it to date in the SELECT
WITH t(test_date) AS (
  VALUES (&#39;2023-06-06&#39;)
)
SELECT current_date = t.test_date::date
FROM t;

huangapple
  • 本文由 发表于 2023年6月6日 15:05:01
  • 转载请务必保留本文链接:https://go.coder-hub.com/76412167.html
匿名

发表评论

匿名网友

:?: :razz: :sad: :evil: :!: :smile: :oops: :grin: :eek: :shock: :???: :cool: :lol: :mad: :twisted: :roll: :wink: :idea: :arrow: :neutral: :cry: :mrgreen:

确定