转换为Postgres功能

时间:2014-12-26 05:52:23

标签: postgresql

我正在将我的SQL存储过程转换为Postgres函数,但它在一个语句中导致错误

错误:“或”附近的语法错误 第7行:CAST(时间(0),'00:00'+(h.hour * interval'1Hour ...                               ^

下面是我正在转换的Postgres函数和SQL Store程序。请告诉我哪里出错了。

CREATE OR REPLACE FUNCTION shiftwisedata_sp(INOut shift_id bigint,InOut userdate date,OUT shift_name character varying (50),OUT from_time character varying(50),OUT to_time character varying(50),OUT cal bigint)
  RETURNS SETOF record AS
$BODY$
  BEGIN
return query
SELECT userdate, s.shift_name, 
          CAST(time(0), '00:00' + (h.hour  * interval '1Hour')) AS from_time,
           CAST(time(0), '00:00' + ((h.hour + 1)  * interval '1Hour')) AS to_time,
          COALESCE(r.Readings, 0) AS readings
   FROM   shift_wise s
   CROSS  JOIN (VALUES(0), (1), (2), (3), (4), (5), (6), (7), (8), (9),
                      (10), (11), (12), (13), (14), (15), (16), (17), (18), (19),
                      (20), (21), (22), (23)) AS h(hour)
   OUTER  APPLY (SELECT SUM(r.param_value) AS Readings
                 FROM   table_1 r
                 WHERE  r.timestamp_col >= CAST(userdate as timestamp without time zone) + (h.hour  * interval '1Hour')
                   AND  r.timestamp_col < CAST(userdate as timestamp without time zone) + ((h.hour + 1) * interval '1Hour')) AS r
WHERE s.shift_id = shift_id
 AND (s.to_time > s.from_time              AND 
       h.hour >= date_part(HOUR, s.from_time) AND
       h.hour <  date_part(HOUR, s.to_time) 
    OR
      s.to_time < s.from_time AND
         (h.hour >= date_part(HOUR, s.from_time) OR
          h.hour < date_part(HOUR, s.to_time))
       )
      ORDER BY s.to_time;
	
  END;
$BODY$
  LANGUAGE plpgsql VOLATILE

CREATE PROCEDURE Shiftdata @date date, @shiftid int AS
   SELECT @date, s.Shift_Name, 
           convert(time(0), dateadd(HOUR, h.hour, '00:00')) AS from_time,
           convert(time(0), dateadd(HOUR, h.hour + 1, '00:00')) AS to_time,
          coalesce(r.Readings, 0) AS readings
   FROM   Shift_Wise s
   CROSS  JOIN (VALUES(0), (1), (2), (3), (4), (5), (6), (7), (8), (9),
                      (10), (11), (12), (13), (14), (15), (16), (17), (18), (19),
                      (20), (21), (22), (23)) AS h(hour)
   OUTER  APPLY (SELECT SUM(r.Reading_Col) AS Readings
                 FROM   Reading r
                 WHERE  r.Timestamp_Col >= dateadd(HOUR, h.hour, convert(datetime, @date))
                   AND  r.Timestamp_Col < dateadd(HOUR, h.hour + 1, convert(datetime, @date))) AS r
WHERE s.Shift_ID = @shiftid
  AND (s.to_time > s.from_time              AND 
       h.hour >= datepart(HOUR, s.from_time) AND
       h.hour <  datepart(HOUR, s.to_time) 
    OR
      s.to_time < s.from_time AND
         (h.hour >= datepart(HOUR, s.from_time) OR
          h.hour < datepart(HOUR, s.to_time))
       )
ORDER BY s.to_time

2 个答案:

答案 0 :(得分:0)

这不是CAST在Postgresql中的工作原理。见http://www.postgresql.org/docs/9.2/static/sql-createcast.html

('00:00' + (h.hour  * interval '1Hour'))::time
如果您不介意使用非标准::符号,

最容易阅读(恕我直言)。

答案 1 :(得分:0)

最后, 将SQL SP转换为Postgres函数并获得所需的结果

CREATE OR REPLACE FUNCTION shiftwisedata_sp(IN shiftid bigint, INOUT userdate date, OUT shift_name character varying, OUT from_time time without time zone, OUT to_time time without time zone, OUT readings bigint)
  RETURNS SETOF record AS
$BODY$
  BEGIN
  return query
SELECT userdate, s.shift_name, 
          ('00:00' + (h.hour  * interval '1Hour'):: time) AS from_time,
          ('00:00' + ((h.hour + 1)  * interval '1Hour'):: time) AS to_time,
          COALESCE(r.Readings, 0) AS readings
   FROM   shift_wise s
  CROSS  JOIN (VALUES(0), (1), (2), (3), (4), (5), (6), (7), (8), (9),
                      (10), (11), (12), (13), (14), (15), (16), (17), (18), (19),
                      (20), (21), (22), (23)) AS h(hour)
   LEFT JOIN LATERAL (SELECT CAST(SUM(r.param_value) as bigint) AS Readings
                 FROM   table_1 r
                 WHERE  r.timestamp_col >= (CASt(userdate As timestamp without time zone)  + h.hour  * interval '1Hour')
                   AND  r.timestamp_col < (CASt(userdate As timestamp without time zone) + (h.hour + 1) * interval '1Hour')
                   ) AS r ON TRUE
WHERE s.shift_id = shiftid
 AND (s.to_time > s.from_time              AND 
       h.hour >= Extract(HOUR from CAST(s.from_time as time)) AND
       h.hour <  Extract(HOUR from CAST(s.to_time as time)) 
    OR
      s.to_time < s.from_time AND
         (h.hour >= Extract(HOUR from CAST(s.from_time as time)) OR
          h.hour < Extract(HOUR from CAST(s.to_time as time))
       ))
      ORDER BY s.to_time;	
  END;
$BODY$
  LANGUAGE plpgsql VOLATILE