Store result of minus query ( list of varchars) in a variable in Oracle PL/SQL

♀尐吖头ヾ 提交于 2021-01-29 15:42:50

问题


I'm using below minus query to get the extra project_ids present in TABLE_ONE compared to TABLE_TWO

select project_id from TABLE_ONE minus select project_id from TABLE_TWO;

I want to store result of above query which is list of varchars in a variable since i need to perform below 2 steps :

  1. If above query returns any project_ids, send an email which contains these project_ids in mail body
  2. insert those extra project_ids in TABLE_TWO to make sure all project_ids present in TABLE_ONE are present in TABLE_TWO

For step 2 I tried below query and it worked.

insert into TABLE_TWO columns (project_id) values (select project_id from TABLE_ONE minus select project_id from TABLE_TWO);

However to perform above 2 steps i need to store the query result in a variable. Please let me know how to do it. I'm using Oracle 12c.


回答1:


Unfortunately, neither of the two most natural ways to get the missing IDs into table_two (a multi-row INSERT or a MERGE) support the RETURNING.. BULK COLLECT INTO clause.

So, I think your best bet is to get the list of ids first and then use that list to maintain table_two.

Like this:

DECLARE 
  l_missing_id_list SYS.ODCINUMBERLIST;
BEGIN
  SELECT project_id
  BULK COLLECT INTO l_missing_id_list
  FROM 
    (
    SELECT t1.project_id FROM table_one t1
    MINUS
    SELECT t2.project_id FROM table_two t2 );
    
  FORALL i IN l_missing_id_list.FIRST..l_missing_id_list.LAST
    INSERT INTO table_two VALUES ( l_missing_id_list(i) );
    
  COMMIT;
  
  -- Values are now inserted and you have the list of IDs in l_missing_id_list to add to your email.
END;

That's the basic concept. Presumably you have more columns in TABLE_TWO than just the id, so you'll have to add those.




回答2:


something like this. Use a cursor loop.

begin
  for c_record in (select project_id from TABLE_ONE minus select project_id from TABLE_TWO)
  loop
        -- send your email however it is done using c_record.project_id
        insert into TABLE_TWO columns (project_id) values (c_record.project_id);
  end loop;

FYI, there is a disadvantage to doing it this way potentially. If you send the email and then the transaction is rolled back, the email still went out the door. A more robust way would be to use Oracle Advances Queues, but that starts getting complicated pretty fast.




回答3:


SELECT LISTAGG(project_id,',')  WITHIN GROUP (ORDER BY project_id)
FROM (select project_id from TABLE_ONE minus select project_id from TABLE_TWO) x;


来源:https://stackoverflow.com/questions/63341473/store-result-of-minus-query-list-of-varchars-in-a-variable-in-oracle-pl-sql

标签
易学教程内所有资源均来自网络或用户发布的内容,如有违反法律规定的内容欢迎反馈
该文章没有解决你所遇到的问题?点击提问,说说你的问题,让更多的人一起探讨吧!