2016-09-09 22 views
-1

My機能は3つのパラメータ(siteid bigint, datefrom timestamp, dateto timestamp)を取得し、私は付属のテーブルを返すべきPostgres関数からテーブルとして結果を返すには?

ERROR: structure of query does not match function result type

私は、私はPostgresのために、SQL Serverから変換機能のスクリプトを持っている私は、関数を実行しているとき、今、私はエラーを取得しますコード内。私は "Return Query"を使用しました。

私はこのように私の関数を実行しています:

getrtbactivesiteplaces(1475, '2016-02-01', '2016-08-01') 

私は私の関数から表としてこの結果を取得できますか?

これはあなたの関数の戻り値の型がsetof varcharですが、それはのようなものである必要があり、私の機能のスクリーンショット

{ 
CREATE OR REPLACE FUNCTION "whis2011"."getrtbactivesiteplaces"(IN siteid int8, IN datefrom timestamp, IN dateto timestamp) RETURNS SETOF "varchar" 
AS $BODY$ 

DECLARE 
siteid BIGINT; 
datefrom timestamp without time zone; 
dateto timestamp without time zone; 


BEGIN 


-- SET NOCOUNT ON added to prevent extra result sets from 
-- interfering with SELECT statements. 

    /* SQLWays Notice: SET TRANSACTION ISOLATION LEVEL READ COMMITTED must be called before procedure call */ 
-- SET TRANSACTION ISOLATION LEVEL READ COMMITTED 


    -- Insert statements for procedure here 
RETURN QUERY SELECT pl."Id", 
     pl."RtbActiveSiteId", 
     pl."AdPlaceId", 
     pl."AdPosition", 
     pl."Ctr", 
     pl."State", 
     pl."BidPrice", 
     pl."MinBidFloor", 
     pl."MinBidFloorCurrency", 
     pl."AverageCpm", 
     pl."AverageClickCost", 
     coalesce(SUM(ss."BidsCount"),0) AS BidsCount, 
     coalesce(SUM(ss."ShowsCount"),0) AS ShowsCount, 
     coalesce(SUM(ss."RealShowsCount"),0) AS RealShowsCount, 
     coalesce(SUM(ss."ClicksCount"),0) AS ClicksCount, 
     coalesce(SUM(ss."ClickLayerClicksCount"),0) as ClickLayerClicksCount, 
     coalesce(SUM(ss."ShowsCost"),0::money) AS ShowsCost, 
     coalesce(SUM(ss."ClicksCost"),0::money) AS ClicksCost, 
     coalesce(SUM(ss."BidsCost"),0::money) AS BidsCost, 
     coalesce(SUM(ss."SliderMovesCount"),0) AS SliderMovesCount 
    FROM "whis2011"."RtbActiveSitePlaces" pl 
    LEFT OUTER JOIN "whis2011"."RtbActiveSitePlaceStatistics" ss ON ss."RtbActiveSitePlaceId" = pl."Id" 
    WHERE ss."Date" >= datefrom AND ss."Date" < dateto AND pl."RtbActiveSiteId" = siteid 
    GROUP BY pl."Id", pl."RtbActiveSiteId", pl."AdPlaceId", pl."AdPosition", pl."Ctr", pl."State", pl."BidPrice", 
    pl."MinBidFloor", pl."MinBidFloorCurrency", pl."AverageCpm", pl."AverageClickCost"; 
END; 
$BODY$ 
LANGUAGE plpgsql 
COST 100 
CALLED ON NULL INPUT 
SECURITY INVOKER 
VOLATILE; 

} 
+1

スクリーンショットが含まれています。コードの場合は、コードの画像を表示しないでください。実際のコードをここに掲載してください。 – Gerrat

+0

この関数がテーブルを返す場合、 'select * from getrtbactivesiteplaces(1475、 '2016-02-01'、 '2016-08-01')' –

+1

http://meta.stackoverflow.com/questions/を使用する必要があります。 285551 /なぜか私のアップロードしない画像のコードの画像の285557#285557 –

答えて

1

改善のために。

まず、RETURNS SETOF varcharの代わりに、関数が返すすべての列を指定するのがRETURNS TABLE ...である必要があります。第2に、3つの関数パラメータがあります。その名前は、関数ブロックで再宣言し、パラメータ値をマスクします。これは、パラメータ値が使用されないために関数が何も返さない理由です。

第3に、すべての合計をサブクエリに入れます。サブクエリは読みやすく、効率的です。最後に、関数本体は単一のSQL文であるため、PL/pgSQL言語関数より効率的なSQL関数にする必要があります。

以下を参照してください。

CREATE OR REPLACE FUNCTION "whis2011"."getrtbactivesiteplaces" 
    (IN siteid int8, IN datefrom timestamp, IN dateto timestamp) 
RETURNS 
             
  
    SETOF "varchar" 
   TABLE (id int, RtbActiveSiteId int, ...) -- add all fields 
AS $BODY$ 

             
  
    DECLARE siteid BIGINT; datefrom timestamp without time zone; dateto timestamp without time zone; 
   -- don't redeclare parameters!!! 

             
  
    BEGIN 
   -- not needed for a SQL function 
    -- Insert statements for procedure here 
    
             
  
    RETURN QUERY 
   SELECT pl."Id", -- SQL function uses simple SELECT 
     pl."RtbActiveSiteId", 
     pl."AdPlaceId", 
     pl."AdPosition", 
     pl."Ctr", 
     pl."State", 
     pl."BidPrice", 
     pl."MinBidFloor", 
     pl."MinBidFloorCurrency", 
     pl."AverageCpm", 
     pl."AverageClickCost", 
     ss.* 
    FROM "whis2011"."RtbActiveSitePlaces" pl 
    LEFT JOIN (
     SELECT "RtbActiveSitePlaceId" AS "Id" 
       coalesce(SUM("BidsCount"),0) AS BidsCount, 
       coalesce(SUM("ShowsCount"),0) AS ShowsCount, 
       coalesce(SUM("RealShowsCount"),0) AS RealShowsCount, 
       coalesce(SUM("ClicksCount"),0) AS ClicksCount, 
       coalesce(SUM("ClickLayerClicksCount"),0) as ClickLayerClicksCount, 
       coalesce(SUM("ShowsCost"),0::money) AS ShowsCost, 
       coalesce(SUM("ClicksCost"),0::money) AS ClicksCost, 
       coalesce(SUM("BidsCost"),0::money) AS BidsCost, 
       coalesce(SUM("SliderMovesCount"),0) AS SliderMovesCount 
     FROM "whis2011"."RtbActiveSitePlaceStatistics" 
     WHERE "Date" >= datefrom AND "Date" < dateto 
     GROUP BY "RtbActiveSitePlaceId") ss USING ("Id") 
    WHERE pl."RtbActiveSiteId" = siteid; 

             
  
    END; 
   -- not needed for a SQL function 
$BODY$ LANGUAGE sql STRICT STABLE; -- don't call on NULL input and use STABLE

あなたがそのようにように、この関数を呼び出す:あなたの問題は、グラフィカルなものである場合は、すべての手段によって、

SELECT * FROM getrtbactivesiteplaces(1475, '2016-02-01', '2016-08-01'); 
+0

ありがとう!それは今働いている。 – Nikito

0

です:あなたはあなたのコードには二つの問題があり、私は2つの推奨を持つ

RETURNS TABLE (Id    integer, 
       RtbActiveSiteId integer, 
       ... etc ... 
      ) 
+0

それは動作しません!実際にスクリプトは動作しますが、何も返されません(ただし、結果に応じて少なくとも2行戻ってください) – Nikito

関連する問題