【问题标题】:Can I join two queries together in a Stored procedure on Redshift?我可以在 Redshift 上的存储过程中将两个查询连接在一起吗?
【发布时间】:2019-07-12 04:45:31
【问题描述】:

最初我正在尝试使用函数但无济于事。 Redshift 不允许表返回类型或从表中选择数据。我希望也许有一种方法可以使用存储过程来做到这一点,但我不再有信心了。我为下面列出的代码创建了一个 SP,是否可以为 SP 将两个查询连接到自身?

尝试做一个功能,但不可能发生

YTD current year
select 
   year
  , month
  , revenue
  ,transactiondate
  , Flag
from (
select
  extract(year from transactiondate) as year
  , to_char(transactiondate, 'Mon') as month
  , extract(month from transactiondate) as month_number
  , sum(netamount) as revenue
  ,transactiondate
  ,Flag
from
  vw_costs_of_businesss_copy

--where to_date(transactiondate, 'YYYY-MM-DD') <= '2019-06-07' and to_date(transactiondate, 'YYYY-MM-DD') ->=  concat(to_char(extract(year from '2019-01-01'), 'YYYY'),'01-01') --Convert the date param to year and concatenate with '01/01'
--where to_date(transactiondate, 'YYYY-MM-DD') <= '2019-06-07' and to_date(concat(to_char(extract(year from to_date('2019-01-01', 'YYYY-MM-DD'))),'01-01') , 'YYYY-MM-DD') >= '2019-01-01' --Convert the date param to year and concatenate with '01/01'
--where to_date(transactiondate, 'YYYY-MM-DD') <= '2019-06-07' and to_date(concat(to_char(Cas(extract(year from to_date('2019-01-01', 'YYYY-MM-DD')) as text ),'-01-01') , 'YYYY-MM-DD') >= '2019-01-01' --Convert the date param to year and concatenate with '01/01'
--where to_date(transactiondate, 'YYYY-MM-DD') <= '2019-06-07' and to_date(concat(to_char(Cast(extract(year from to_date('2019-01-01', 'YYYY-MM-DD')) as Text),'0000'),'-01') , 'YYYY-MM-DD') >= '2019-01-01' --Convert the date param to year and concatenate with '01/01'
where to_date(transactiondate, 'YYYY-MM-DD') <= '2019-06-07' and to_date(transactiondate, 'YYYY-MM-DD')>= to_date(concat(to_char(Cast(extract(year from to_date('2019-01-01', 'YYYY-MM-DD')) as Text),'0000'),'-01') , 'YYYY-MM-DD')

group by
  year
  , month
  , month_number
  ,transactiondate
 , Flag
)
order by month_number, year

--YTD PREV YEAR
select 
   year
  , month
  , revenue
  ,transactiondate
  , Flag
from (
select
  extract(year from transactiondate) as year
  , to_char(transactiondate, 'Mon') as month
  , extract(month from transactiondate) as month_number
  , sum(netamount) as revenue
  ,transactiondate
  ,Flag
from
  vw_costs_of_businesss_copy

--where to_date(transactiondate, 'YYYY-MM-DD') <= '2019-06-07' and to_date(transactiondate, 'YYYY-MM-DD') ->=  concat(to_char(extract(year from '2019-01-01'), 'YYYY'),'01-01') --Convert the date param to year and concatenate with '01/01'
--where to_date(transactiondate, 'YYYY-MM-DD') <= '2019-06-07' and to_date(concat(to_char(extract(year from to_date('2019-01-01', 'YYYY-MM-DD'))),'01-01') , 'YYYY-MM-DD') >= '2019-01-01' --Convert the date param to year and concatenate with '01/01'
--where to_date(transactiondate, 'YYYY-MM-DD') <= '2019-06-07' and to_date(concat(to_char(Cas(extract(year from to_date('2019-01-01', 'YYYY-MM-DD')) as text ),'-01-01') , 'YYYY-MM-DD') >= '2019-01-01' --Convert the date param to year and concatenate with '01/01'
--where to_date(transactiondate, 'YYYY-MM-DD') <= '2019-06-07' and to_date(concat(to_char(Cast(extract(year from to_date('2019-01-01', 'YYYY-MM-DD')) as Text),'0000'),'-01') , 'YYYY-MM-DD') >= '2019-01-01' --Convert the date param to year and concatenate with '01/01'
where to_date(transactiondate, 'YYYY-MM-DD') <= '2019-06-07' and to_date(transactiondate, 'YYYY-MM-DD')>= to_date(concat(to_char(Cast(extract(year from to_date('2019-01-01', 'YYYY-MM-DD')-1) as Text),'0000'),'-01') , 'YYYY-MM-DD')

group by
  year
  , month
  , month_number
  ,transactiondate
 , Flag
)

order by month_number, year

它需要列出 YTD 和 prev_YTD 以便我可以将其作为参数传递,这可能吗?我意识到我必须为此制作一张桌子。 我在哪里放置 Prev_year、Prev-month 列

【问题讨论】:

    标签: stored-procedures amazon-redshift


    【解决方案1】:

    我认为您正在寻找UNION ALL 的概念来“加入两个查询”。

    这是一个使用存储过程的示例。请参阅"Overview of Stored Procedures in Amazon Redshift" 了解更多信息。

    CREATE PROCEDURE ytd_comparison(
          date_param IN    DATE
        , result_set INOUT REFCURSOR) 
    AS $$
    BEGIN
        OPEN result_set FOR --YTD
        SELECT year , month , revenue , transactiondate , Flag
        FROM (SELECT EXTRACT(year FROM transactiondate) AS year
                   , TO_CHAR(transactiondate, 'Mon') AS month
                   , EXTRACT(month FROM transactiondate) AS month_number
                   , SUM(netamount) AS revenue
                   , transactiondate
                   , Flag
              FROM vw_costs_of_businesss_copy
              WHERE TO_DATE(transactiondate, 'YYYY-MM-DD') <= date_param
                AND TO_DATE(transactiondate, 'YYYY-MM-DD') >= DATE_TRUNC('year',date_param)
              GROUP BY year , month , month_number , transactiondate , Flag
              )
        UNION ALL --YTD PREV YEAR
        SELECT year ,month ,revenue ,transactiondate ,Flag
        FROM (SELECT EXTRACT(year FROM transactiondate) AS year
                   , TO_CHAR(transactiondate, 'Mon') AS month
                   , EXTRACT(month FROM transactiondate) AS month_number
                   , SUM(netamount) AS revenue
                   , transactiondate
                   , Flag
              FROM vw_costs_of_businesss_copy
              WHERE TO_DATE(transactiondate, 'YYYY-MM-DD') <= DATEADD(year, -1, date_param)
                AND TO_DATE(transactiondate, 'YYYY-MM-DD') >= DATE_TRUNC('year', DATEADD(year, -1, date_param))
              GROUP BY year , month , month_number , transactiondate , Flag
              )
        ORDER BY month_number , year
        ;
        RETURN;
    END;
    $$ LANGUAGE plpgsql;
    

    您需要在调用过程时为输出REFCURSOR 提供名称。您必须使用BEGIN 打开一个事务来维护游标,然后从REFCURSOR 获取输出,然后使用END 事务丢弃结果游标。

    BEGIN;
    CALL ytd_comparison ('2016-07-01'::DATE, 'ytd_results'); 
    FETCH ALL FROM ytd_results; 
    END;
    

    更新:
    或者,您可以仅创建前一天的视图。

    CREATE OR REPLACE VIEW ytd_comparison AS
    SELECT year , month , revenue , transactiondate , Flag
    FROM (SELECT EXTRACT(year FROM transactiondate) AS year
               , TO_CHAR(transactiondate, 'Mon') AS month
               , EXTRACT(month FROM transactiondate) AS month_number
               , SUM(netamount) AS revenue
               , transactiondate
               , Flag
          FROM vw_costs_of_businesss_copy
          WHERE TO_DATE(transactiondate, 'YYYY-MM-DD') <= GETDATE() - 1
            AND TO_DATE(transactiondate, 'YYYY-MM-DD') >= DATE_TRUNC('year',GETDATE() - 1)
          GROUP BY year , month , month_number , transactiondate , Flag
          )
    UNION ALL --YTD PREV YEAR
    SELECT year ,month ,revenue ,transactiondate ,Flag
    FROM (SELECT EXTRACT(year FROM transactiondate) AS year
               , TO_CHAR(transactiondate, 'Mon') AS month
               , EXTRACT(month FROM transactiondate) AS month_number
               , SUM(netamount) AS revenue
               , transactiondate
               , Flag
          FROM vw_costs_of_businesss_copy
          WHERE TO_DATE(transactiondate, 'YYYY-MM-DD') <= DATEADD(year, -1, GETDATE() - 1)
            AND TO_DATE(transactiondate, 'YYYY-MM-DD') >= DATE_TRUNC('year', DATEADD(year, -1, GETDATE() - 1))
          GROUP BY year , month , month_number , transactiondate , Flag
          )
    ORDER BY month_number , year
    ;
    

    【讨论】:

    • 从这一点开始的问题是可以把它做成一个视图或表格吗?
    • 要使其成为视图或表格,您必须计算每一天的值,然后在查询时仅过滤您想要的那一天。如果存储过程不合适,使用准备好的语句可能会更好。 docs.aws.amazon.com/redshift/latest/dg/r_PREPARE.html
    • 我只需要它直到今天以及过去两年的年初至今和当月。但是,查看准备语句,我需要传递您重新处理的 SP 给我的结果集中的值。
    • 在这种情况下,是的,你可以很容易地做到这一点。在答案中添加了示例。
    • 老兄你最好的。有时它的蚂蚁小山我们制造了山,但对于我的生活,我可以弄清楚如何做到这一点。真的非常感谢您的帮助!
    猜你喜欢
    • 1970-01-01
    • 2013-12-19
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2016-02-27
    相关资源
    最近更新 更多