Postgresql For循环,内部函数更新

时间:2017-03-13 18:30:37

标签: database postgresql for-loop

我尝试使用postgresql函数启动对几个表的查询,然后在符合条件的情况下插入另一个表。我每次都会在声明或return语句中遇到错误。任何帮助表示赞赏。

基本上应该:​​

  1. 循环使用health_alerts_triggered表并使用每行中的字段数据,然后查询" healthEvents"表
  2. 如果子查询中的计数为" healthEvents"返回大于零的行,并且应该在health_alerts_triggered表中插入。

    CREATE OR REPLACE FUNCTION sp_alertcheck() 
    RETURNS SETOF record;
    DECLARE r record;
    FOR r IN SELECT * 
        FROM health_alerts_config
    LOOP
    INSERT INTO health_alerts_triggered (health_affiliate_id, alert_format,alert_minutes, health_client_internal_id, alert_triggered_date, alert_processed_date, alert_id, affiliate_name, client_name)
    VALUES (r.health_affiliate_id, r.alert_format, r.alert_minutes, r.health_client_internal_id, now() as alert_triggered_date, '' as alert_processed_date, id, ha.health_affiliate_description, hc.health_client_description)
    WHERE (SELECT COUNT(*) from "heatlhEvents" he 
       WHERE he.format = r.format,
       AND he.healthaffiliatclientid = r.health_affiliate_description,
       AND he.timestamp > Now() - r.minutes
        )
        > 0
    INNER JOIN health_affiliates ha
    ON r.health_affiliate_id = ha.id
    INNER JOIN health_clients hc
    ON r.health_client_internal_id = hc.id
    END LOOP;
    RETURN result;
    $BODY$
    LANGUAGE plpgsql;
    
  3. health_alerts_config的架构:

    CREATE TABLE public.health_alerts_config
    (
        id bigint NOT NULL DEFAULT nextval('"healthAlerts_id_seq"'::regclass),
        health_affiliate_id bigint NOT NULL,
        alert_format character varying(10) COLLATE pg_catalog."default" NOT NULL,
        alert_minutes integer NOT NULL,
        health_client_internal_id bigint NOT NULL,
        CONSTRAINT health_alerts_pkey PRIMARY KEY (id)
    )
    

    样本行:1,1,ADT,60,1

    health_affiliates的架构

    CREATE TABLE public.health_affiliates
    (
        id bigint NOT NULL,
        health_affiliate_description character varying(50) COLLATE pg_catalog."default" NOT NULL,
        CONSTRAINT health_affiliates_pkey PRIMARY KEY (id)
    )
    

    示例行:1,' TestCo'

    health_clients的架构

    CREATE TABLE public.health_clients
    (
        id integer NOT NULL DEFAULT nextval('"healthClients_id_seq"'::regclass),
        health_affiliate integer NOT NULL,
        health_client_id character varying(20) COLLATE pg_catalog."default" NOT NULL,
        health_client_description character varying(100) COLLATE pg_catalog."default" NOT NULL,
        CONSTRAINT id_pk PRIMARY KEY (id)
    )
    

    示例行:1,1,200,' TestCoClient'

    " healthEvents"

    的架构
    CREATE TABLE public."healthEvents"
    (
        "ID" integer NOT NULL DEFAULT nextval('"healthEvents_ID_seq"'::regclass),
        "fileName" character varying(100) COLLATE pg_catalog."default" NOT NULL,
        "instanceName" character varying(20) COLLATE pg_catalog."default" NOT NULL,
        "channelName" character varying(50) COLLATE pg_catalog."default" NOT NULL,
        affiliate character varying(20) COLLATE pg_catalog."default" NOT NULL,
        "fileSizeKB" bigint,
        "beginProcessing" timestamp without time zone,
        "endProcessing" timestamp without time zone,
        resubmission boolean NOT NULL,
        destination integer NOT NULL,
        "insertTime" timestamp without time zone NOT NULL DEFAULT now(),
        "messageID" bigint NOT NULL,
        direction integer NOT NULL,
        "affiliateClient" character varying(40) COLLATE pg_catalog."default" NOT NULL,
        "messageType" character varying(15) COLLATE pg_catalog."default",
        "messageStatus" integer,
        "messageCode" character varying(10) COLLATE pg_catalog."default",
        "insertDate" date DEFAULT ('now'::text)::date,
        "affiliateClientID" character varying(50) COLLATE pg_catalog."default",
        CONSTRAINT "PK" PRIMARY KEY ("ID")
    

1 个答案:

答案 0 :(得分:0)

我认为你甚至不需要循环。我会做(未经测试)的事情:

INSERT INTO health_alerts_triggered (
  health_affiliate_id, alert_format, alert_minutes, health_client_internal_id,
  alert_triggered_date, alert_processed_date, alert_id,
  affiliate_name, client_name
)
SELECT
  r.health_affiliate_id, r.alert_format, r.alert_minutes, r.health_client_internal_id,
  now() as alert_triggered_date, '' as alert_processed_date, id,
  ha.health_affiliate_description, hc.health_client_description
FROM
  health_alerts_config r
  INNER JOIN health_affiliates ha
    ON r.health_affiliate_id = ha.id
  INNER JOIN health_clients hc
    ON r.health_client_internal_id = hc.id
WHERE
  exists(
    SELECT 1
    FROM "heatlhEvents" he 
    WHERE he.format = r.format,
    AND he.healthaffiliatclientid = r.health_affiliate_description,
    AND he.timestamp > now() - r.minutes
  )
;