错误:带有时区的时间戳类型的输入语法无效

时间:2019-06-20 07:20:19

标签: postgresql postgresql-9.3

我有一个下面运行的PostgreSQL查询。我从如下的shell脚本中调用它

Result=$(psql -U username -d database -t -c 
$'SELECT round(sum(i.total), 2) AS "ROUND(sum(i.total), 2)" 
  FROM invoice i 
  WHERE i.create_datetime = '2019-03-01 00:00:00-06' 
  AND i.is_review = '1' AND i.user_id != 60;')

现在,我希望将我硬编码为i.create_datetime = '2019-03-01 00:00:00-06'的值替换为可变的日期值。

我尝试了两种方法

方式1:

Result=$(psql -U username -d database -t -c 
$'WITH var(reviewMonth) as (values(\'$reviewMonth\')) 
SELECT round(sum(i.total),2) AS "ROUND(sum(i.total),2)" 
FROM var,invoice i 
WHERE i.create_datetime = var.reviewMonth::timestamp 
AND i.is_review = \'1\' AND i.user_id != 60;')

方式2:

Result=$(psql -U username -d database -t -c 
$'SELECT round(sum(i.total),2) AS "ROUND(sum(i.total),2)" 
FROM invoice i 
WHERE i.create_datetime = \'$reviewMonth\' 
AND i.is_review = \'1\' AND i.user_id != 60;')

但这两种方式都会引发错误

方式1的抛出错误为:

  

错误:运算符不存在:带有时区=文本的时间戳

方式2的投掷错误为:

  

错误:带有时区的时间戳类型“ $ reviewMonth”的无效输入语法

请提出我应该采取的方法。

1 个答案:

答案 0 :(得分:0)

您应该尝试使用psql变量。这是一个示例:

# Put the query in a file, with the variable TSTAMP:

> echo "SELECT :'TSTAMP'::timestamp with time zone;" > query.sql
> export TSTAMP='2019-03-01 00:00:00-06'
> RESULT=$(psql -U postgres -t --variable=TSTAMP="$TSTAMP" -f query.sql )
> echo $RESULT
2019-03-01 06:00:00+00

请注意我们如何在查询中设置字符串文字替换的格式::'TSTAMP'

您也可以自己进行替换。这是使用Heredoc的示例:

> export TSTAMP='2019-03-01 00:00:01-06'
> RESULT=$(psql -U postgres -t << EOF
SELECT '$TSTAMP'::timestamp with time zone;
EOF
)
> echo $RESULT
2019-03-01 06:00:01+00

在这种情况下,我们没有使用psql的变量替换,因此我们必须引用变量'$ TSTAMP'。与使用-c相比,使用Heredoc使引用更简单,因为您并没有尝试引用整个命令。

编辑:更多示例,因为看来这还不够清楚。 TSTAMP不必硬编码,它只是一个bash变量,可以像设置任何其他bash变量一样进行设置。

> TSTAMP=$(date -d 'now' +'%Y-%m-01 00:00:00')
> RESULT=$(psql -U postgres -t << EOF
SELECT '$TSTAMP'::timestamp with time zone;
EOF
)
> echo $RESULT
2019-06-01 00:00:00+00

但是,如果您只是在寻找本月初,则根本不需要shell变量

> RESULT=$(psql -U postgres -t << EOF
SELECT date_trunc('month', now());
EOF
)
> echo $RESULT
2019-06-01 00:00:00+00