web-dev-qa-db-ja.com

org.postgresql.util.PSQLException:ERROR: "$ 1"またはその近くの構文エラー

私はこのPSQLExceptionを取得しています:

org.postgresql.util.PSQLException: ERROR: syntax error at or near "$1"
  Position: 37

次のコードを実行すると:

ps = connection.prepareStatement("SELECT current_timestamp + INTERVAL ?;");
ps.setString(1, "30 minutes");
System.out.println(ps);
rs = ps.executeQuery();

ただし、println関数はこれをコンソールに表示します。

SELECT current_timestamp + INTERVAL '30 minutes'

誰が何が悪いのか知っていますか?コンソールのクエリはpgAdminで正常に実行されるため、構文エラーではないことがわかります。

15
Kevin Orriss

構文_INTERVAL '30 minutes'_は、コンソールでSQLを直接書き込む場合に有効ですが、実際には間隔リテラルと見なされ、 Word INTERVALに続く文字列がリテラル文字列でない場合に機能します。

PostgreSQLで準備されたステートメントは PREPARE を使用してサーバー側で実装され、各_?_はサーバー上で実際の変数と見なされます。これが_$1_について文句を言う理由でもありますが、ステートメントで_$_を記述したことはありません。

したがって、リテラル構文はプリペアドステートメントでは機能しません。

準備されたステートメントの文字列表現(printlnの結果)が混乱しないようにしてください。これはサーバーが認識しているものではありません。サーバーはそこで変数を参照します。

したがって、文字列(変数またはリテラルにすることができます)を受け取り、それを間隔に変換する構文を使用する必要があります。たとえば、_?::INTERVAL_またはCAST(? AS INTERVAL)です。

したがって、これはバグではありません

19
RealSkeptic