	/*  
	
	procs.sql -	PL/SQL Procedures used in Collaboration Area Data Integrity Check 

	Copyright 2005, IBM Corporation
	Version August 17, 2005

	*/
CREATE OR REPLACE PROCEDURE COUNT_SHOW_SOME_PK_VIEW(View_Name VARCHAR2, Description VARCHAR2, KEYS_TO_SHOW NUMBER)
IS
	TYPE MyCurTyp IS REF CURSOR;
	my_cv MyCurTyp;
	TYPE view_rec_type IS RECORD(itm_primary_key VARCHAR2(300)); -- dependent on ITM ddl
	view_rec view_rec_type;
	sql_stmt VARCHAR2(200);
	rows_fetched NUMBER;
   	TYPE primary_key_tab_type is table of VARCHAR2(300) index by binary_integer;
	primary_key_tab primary_key_tab_type;
	-- KEYS_TO_SHOW NUMBER := 5;
BEGIN
	DBMS_OUTPUT.PUT_LINE(' ');
	DBMS_OUTPUT.PUT_LINE('*** REPORT FOR VIEW ' || View_Name || ', Description = ' || Description);
	sql_stmt := 'SELECT * FROM ' || LTRIM(RTRIM(View_Name)) || ' ORDER BY ITM_PRIMARY_KEY';

	-- Report total count	
	OPEN my_cv FOR sql_stmt;
	FETCH my_cv BULK COLLECT INTO primary_key_tab;
	rows_fetched := my_cv%ROWCOUNT;
	DBMS_OUTPUT.PUT_LINE('Total number of primary keys in view = ' || rows_fetched);
	CLOSE my_cv;

	-- show some primary keys
	OPEN my_cv FOR sql_stmt;
	LOOP
		FETCH my_cv INTO view_rec;
		EXIT WHEN my_cv%NOTFOUND;
		IF (KEYS_TO_SHOW > 0) THEN EXIT WHEN my_cv%ROWCOUNT > KEYS_TO_SHOW; END IF;
		DBMS_OUTPUT.PUT_LINE('Next primary key in this view = ' || view_rec.itm_primary_key);
	END LOOP;
	CLOSE my_cv;

EXCEPTION
	WHEN OTHERS THEN
		DBMS_OUTPUT.PUT_LINE('Error in proc COUNT_SHOW_SOME_PK_VIEW('||View_Name||', '||Description||')');
END;
/
CREATE OR REPLACE PROCEDURE COUNT_SHOW_SOME_ITEM_ID_VIEW(View_Name VARCHAR2, Description VARCHAR2, KEYS_TO_SHOW NUMBER)
IS
	TYPE MyCurTyp IS REF CURSOR;
	my_cv MyCurTyp;
	TYPE view_rec_type IS RECORD(itm_id NUMBER(9)); -- dependent on ITM ddl
	view_rec view_rec_type;
	sql_stmt VARCHAR2(200);
	rows_fetched NUMBER;
   	TYPE item_id_tab_type is table of NUMBER(9) index by binary_integer;
	item_id_tab item_id_tab_type;
	-- KEYS_TO_SHOW NUMBER := 5;
BEGIN
	DBMS_OUTPUT.PUT_LINE(' ');
	DBMS_OUTPUT.PUT_LINE('*** REPORT FOR VIEW ' || View_Name || ', Description = ' || Description);
	sql_stmt := 'SELECT * FROM ' || LTRIM(RTRIM(View_Name));

	-- Report total count	
	OPEN my_cv FOR sql_stmt;
	FETCH my_cv BULK COLLECT INTO item_id_tab;
	rows_fetched := my_cv%ROWCOUNT;
	DBMS_OUTPUT.PUT_LINE('Total number of item ids in view = ' || rows_fetched);
	CLOSE my_cv;

	-- show some item ids
	OPEN my_cv FOR sql_stmt;
	LOOP
		FETCH my_cv INTO view_rec;
		EXIT WHEN my_cv%NOTFOUND;
		IF (KEYS_TO_SHOW > 0) THEN EXIT WHEN my_cv%ROWCOUNT > KEYS_TO_SHOW; END IF;
		DBMS_OUTPUT.PUT_LINE('Next item id in this view = ' || view_rec.itm_id);
	END LOOP;
	CLOSE my_cv;

EXCEPTION
	WHEN OTHERS THEN
		DBMS_OUTPUT.PUT_LINE('Error in proc COUNT_SHOW_SOME_ITEM_ID_VIEW('||View_Name||', '||Description||')');
END;
/

CREATE OR REPLACE PROCEDURE SHOW_ALL_PK_VIEW(View_Name VARCHAR2, Description VARCHAR2)
IS
	TYPE MyCurTyp IS REF CURSOR;
	my_cv MyCurTyp;
	TYPE view_rec_type IS RECORD(itm_primary_key VARCHAR2(300)); -- dependent on ITM ddl
	view_rec view_rec_type;
	sql_stmt VARCHAR2(200);
BEGIN
	sql_stmt := 'SELECT * FROM ' || LTRIM(RTRIM(View_Name)) || ' ORDER BY ITM_PRIMARY_KEY';

	-- show all primary keys
	OPEN my_cv FOR sql_stmt;
	LOOP
		FETCH my_cv INTO view_rec;
		EXIT WHEN my_cv%NOTFOUND;
		DBMS_OUTPUT.PUT_LINE(view_rec.itm_primary_key);
	END LOOP;
	CLOSE my_cv;

EXCEPTION
	WHEN OTHERS THEN
		DBMS_OUTPUT.PUT_LINE('Error in proc SHOW_ALL_PRIMARY_KEY_VIEW('||View_Name||', '||Description||')');
END;
/


CREATE OR REPLACE PROCEDURE SHOW_ALL_IID_VIEW(View_Name VARCHAR2, Description VARCHAR2)
IS
	TYPE MyCurTyp IS REF CURSOR;
	my_cv MyCurTyp;
	TYPE view_rec_type IS RECORD(itm_id NUMBER(9)); -- dependent on ITM ddl
	view_rec view_rec_type;
	sql_stmt VARCHAR2(200);
BEGIN
	sql_stmt := 'SELECT * FROM ' || LTRIM(RTRIM(View_Name));

	-- show all item ids
	OPEN my_cv FOR sql_stmt;
	LOOP
		FETCH my_cv INTO view_rec;
		EXIT WHEN my_cv%NOTFOUND;
		DBMS_OUTPUT.PUT_LINE(view_rec.itm_id);
	END LOOP;
	CLOSE my_cv;

EXCEPTION
	WHEN OTHERS THEN
		DBMS_OUTPUT.PUT_LINE('Error in proc SHOW_ALL_IID_VIEW('||View_Name||', '||Description||')');
END;
/


CREATE OR REPLACE FUNCTION GET_ITEM_ID(catalog_id INTEGER, pk VARCHAR2) RETURN NUMBER IS
    out_id NUMBER := 0;
    TYPE cur_typ IS REF CURSOR;
    c cur_typ;
    query_str VARCHAR2(200);
BEGIN
    query_str := 'select distinct itm_id from itm where itm_primary_key = :pk and itm_container_id = :cid';
    OPEN c FOR query_str USING pk, catalog_id;
    LOOP
        FETCH c INTO out_id;
        EXIT WHEN c%NOTFOUND;
    END LOOP;
    CLOSE c;
   RETURN out_id;
   EXCEPTION
     WHEN NO_DATA_FOUND THEN
       NULL;
     WHEN OTHERS THEN
       -- Consider logging the error and then re-raise
       RAISE;
END GET_ITEM_ID;
/


CREATE OR REPLACE FUNCTION GET_ITEM_PRIMARY_KEY(catalog_id INTEGER, item_id NUMBER) RETURN VARCHAR2 IS
    out_pk VARCHAR2(300) := ' '; -- default empty pk
    TYPE cur_typ IS REF CURSOR;
    c cur_typ;
    query_str VARCHAR2(200);
BEGIN
    query_str := 'select distinct itm_primary_key from itm where itm_id = :iid and itm_container_id = :cid';
    OPEN c FOR query_str USING item_id, catalog_id;
    LOOP
        FETCH c INTO out_pk;
        EXIT WHEN c%NOTFOUND;
    END LOOP;
    CLOSE c;
   RETURN out_pk;
   EXCEPTION
     WHEN NO_DATA_FOUND THEN
       NULL;
     WHEN OTHERS THEN
       -- Consider logging the error and then re-raise
       RAISE;
END GET_ITEM_PRIMARY_KEY;
/


CREATE OR REPLACE PROCEDURE BACKUP_ITEM_NEW(clnCoaId INTEGER, primary_key VARCHAR2, src_item_id NUMBER, ca_item_id NUMBER)
IS
-- Backup an item by pk, both from collaboration area and source catalog
-- Item may be in only one or both.  Specified by positive-valued ids passed.
BEGIN
  -- DBMS_OUTPUT.PUT_LINE(' ');
  DBMS_OUTPUT.PUT_LINE('   STARTING BACKUP_ITEM('||primary_key||', '||src_item_id||', '||ca_item_id||') ...');

  -- Do source item first 
  IF (src_item_id > 0) THEN
    DBMS_OUTPUT.PUT_LINE('     BACKUP SOURCE ITEM ID='||src_item_id);
    execute immediate 'insert into ITMRSV_CLNCOA (select * from itm where itm_id =' || src_item_id || ')';
    execute immediate 'insert into CEM_CLNCOA  (select * from cem where cem_src_entry_id =' || src_item_id || ')';
    execute immediate 'insert into CEH_CLNCOA (select * from ceh where ceh_entry_key =''' || primary_key||''')';
  END IF;

  -- DO CA item
  IF (ca_item_id > 0) THEN
    DBMS_OUTPUT.PUT_LINE('     BACKUP CA ITEM ID='||ca_item_id);
    execute immediate 'insert into ITM_CLNCOA (select * from itm where itm_id = ' || ca_item_id || ')' ;
    execute immediate 'insert into ITA_CLNCOA (select * from ita where ita_item_id = ' || ca_item_id || ')' ;
    execute immediate 'insert into ITD_CLNCOA (select * from itd where itd_item_id = ' || ca_item_id || ')' ;
    execute immediate 'insert into ICM_CLNCOA (select * from icm where icm_item_id = ' || ca_item_id || ')' ;
    execute immediate 'insert into CEM_CLNCOA (select * from cem where cem_ca_entry_id = ' || ca_item_id || ')' ;
    execute immediate 'insert into CAE_CLNCOA (select * from cae where cae_entry_id = ' || ca_item_id || ')' ;
    execute immediate 'insert into CEH_CLNCOA (select * from ceh where ceh_entry_key =''' || primary_key ||''')';
    execute immediate 'insert into CEL_CLNCOA (select * from cel where cel_entry_id = ' || ca_item_id || ')' ;
    -- 3.31.06 - why fails?
    --execute immediate 'insert into WEE_CLNCOA (select clnCoaId, wee_event_id, wee_entry_id, wee_event_entry_status from wee where wee_entry_id = ' ||ca_item_id||')';
  END IF;
  DBMS_OUTPUT.PUT_LINE('   FINISHED BACKUP_ITEM('||primary_key||', '||src_item_id||', '||ca_item_id||')');
-- 
EXCEPTION
	WHEN OTHERS THEN
		DBMS_OUTPUT.PUT_LINE('Error in proc BACKUP_ITEM_NEW('||primary_key||', '||src_item_id||', '||ca_item_id||')');
END;
/

CREATE OR REPLACE PROCEDURE BACKUP_CA_ITEM(clnCoaId INTEGER, primary_key VARCHAR2, ca_item_id NUMBER)
IS
-- Backup an item known in a collaboration area (i.e. not a source catalog item)
-- 
-- primary_key may be NULL, but ca_item_id should not be.
--
BEGIN
	--DBMS_OUTPUT.PUT_LINE(' ');
	DBMS_OUTPUT.PUT_LINE('   STARTING BACKUP_CA_ITEM('||primary_key||', '||ca_item_id||') ...');

	-- DO CA item
	IF (ca_item_id > 0) THEN
		DBMS_OUTPUT.PUT_LINE('     BACKUP CA ITEM ID='||ca_item_id);
    execute immediate 'insert into ITM_CLNCOA (select * from itm where itm_id =' || ca_item_id || ')';
    execute immediate 'insert into ITA_CLNCOA (select * from ita where ita_item_id =' || ca_item_id ||')';
    execute immediate 'insert into ITD_CLNCOA (select * from itd where itd_item_id = ' || ca_item_id || ')' ;
    execute immediate 'insert into ICM_CLNCOA (select * from icm where icm_item_id =' || ca_item_id ||')';
    execute immediate 'insert into CEM_CLNCOA (select * from cem where cem_ca_entry_id =' || ca_item_id || ')';
    execute immediate 'insert into CAE_CLNCOA (select * from cae where cae_entry_id =' || ca_item_id || ')';
    execute immediate 'insert into CEH_CLNCOA (select * from ceh where ceh_entry_key =''' ||  primary_key || ''')';
    execute immediate 'insert into CEL_CLNCOA (select * from cel where cel_entry_id = ' || ca_item_id || ')';
	-- 3.31.06 - why fails?
    --execute immediate 'insert into WEE_CLNCOA (select clnCoaId, wee_event_id, wee_entry_id, wee_event_entry_status from wee where wee_entry_id =' || ca_item_id  ||')';
	END IF;

	DBMS_OUTPUT.PUT_LINE('   FINISHED BACKUP_CA_ITEM('||primary_key||', '||ca_item_id||')');

EXCEPTION
	WHEN OTHERS THEN
		DBMS_OUTPUT.PUT_LINE('Error in proc BACKUP_CA_ITEM('||primary_key||', '||ca_item_id||')');
END;
/


CREATE OR REPLACE PROCEDURE BACKUP_SRC_ITEM(clnCoaId INTEGER, primary_key VARCHAR2, src_item_id NUMBER)
IS
-- Backup an item known to be in a source catalog (i.e. not a collaboration area item).
-- 
-- primary_key may be NULL, but src_item_id should not be.
--
BEGIN
	-- DBMS_OUTPUT.PUT_LINE(' ');
	DBMS_OUTPUT.PUT_LINE('   STARTING BACKUP_SRC_ITEM('||primary_key||', '||src_item_id||') ...');

	-- Do source item first 
	IF (src_item_id > 0) THEN
		DBMS_OUTPUT.PUT_LINE('     BACKUP SOURCE ITEM ID='||src_item_id);
    execute immediate 'insert into ITMRSV_CLNCOA (select * from itm where itm_id = ' || src_item_id || ' and itm_next_version_id=999999999)' ;
    execute immediate 'insert into CEM_CLNCOA  (select * from cem where cem_src_entry_id = ' || src_item_id || ')' ;
    execute immediate 'insert into CEH_CLNCOA (select * from ceh where ceh_entry_key =''' || primary_key || ''')';
	END IF;

	DBMS_OUTPUT.PUT_LINE('   FINISHED BACKUP_SRC_ITEM('||primary_key||', '||src_item_id||')');

EXCEPTION
	WHEN OTHERS THEN
		DBMS_OUTPUT.PUT_LINE('Error in proc BACKUP_SRC_ITEM('||primary_key||', '||src_item_id||')');
END;
/



CREATE OR REPLACE FUNCTION REMOVE_CA_FROM_COLLAB_INFO(collabInfo VARCHAR2, clnCoaId INTEGER) RETURN varchar2 IS
-- revert a checkout, i.e. remove the given clnCoaId from the given colllabId.  Return the modified collabId.
-- 2007 Jan 08, Dennis Arnon
-- sample args:
---     collabInfo = "691::807||667999::80799||-3::807||6543333::8073||1209::80||1222::807||668222::80722||1208::807||121022::807222222"
---     clnCoaId = 807
-- RetVal = 667999::80799||6543333::8073||1209::80||668222::80722||121022::807222222
-- 
    CHUNK_SEPARATOR CONSTANT VARCHAR(2) := '||';
	CHUNK_SEPARATOR_LENGTH CONSTANT INTEGER := 2;
	CHUNK_INTRNL_SEPARATOR CONSTANT VARCHAR(2) := '::';
	CHUNK_INTRNL_SEPARATOR_LENGTH CONSTANT INTEGER := 2;
	chunkSeparatorIndex INTEGER;
	thisCoaIdIndex INTEGER;
	chunk VARCHAR2(500);
	tail VARCHAR2(32767);
	newCollabInfo VARCHAR2(32767);
BEGIN
   --DBMS_OUTPUT.PUT_LINE('collabInfo='||collabInfo||', clnCoaId='||clnCoaId);
   tail := collabInfo;
   newCollabInfo := '';
   chunk := '';
   while (length(tail) > 0) LOOP
   	   
	   chunkSeparatorIndex := instr(tail, CHUNK_SEPARATOR, 1, 1);
	   
	   if (chunkSeparatorIndex = 0) then
	   	  chunk := tail;
		  tail := '';
	   else
	   	   chunk := substr(tail, 1, chunkSeparatorIndex - 1); -- the stuff up to, but not including, the chunk separator
		   tail := substr(tail, chunkSeparatorIndex + CHUNK_SEPARATOR_LENGTH); -- skip over chunk separator
	   end if;
	   
	   thisCoaIdIndex := instr(chunk, CHUNK_INTRNL_SEPARATOR||to_char(clnCoaId), 1, 1) + CHUNK_INTRNL_SEPARATOR_LENGTH;
	   		-- note that having CHUNK_INTRNL_SEPARATOR at start of match pattern addresses, and removes, the a priori need to 
			-- 		worry about clnCoaId being a substring of the attribute group id that is the initial portion of the chunk.
			-- note also that having the full "to_char(clnCoaId)" as the remaining portion of the match pattern removes the need to
			-- 		worry about "to_char(clnCoaId)" being a (false-positive-matching) superstring of some other, different, coaId.
			-- thus the only false-positive match that can occur, and that we will have to weed out (see below), is 
			--		"to_char(clnCoaId)" being a prefix of some other, different, coaId.
	   
	   --DBMS_OUTPUT.PUT_LINE('chunkSeparatorIndex='||chunkSeparatorIndex||', thisCoaIdIndex='||thisCoaIdIndex||', next chunk='||chunk||', next tail='||tail);
	   
	   -- Retain this chunk if it's for a different coaId.  
	   -- Here is where we detect case of (String value of) clnCoaId is prefix of (String value of) other, different, coaId.
	   if (thisCoaIdIndex = CHUNK_INTRNL_SEPARATOR_LENGTH OR (thisCoaIdIndex + length(to_char(clnCoaId)) - 1 < length(chunk)) ) then
	      if (length(newCollabInfo) > 0) then
		  	 newCollabInfo := newCollabInfo||CHUNK_SEPARATOR; -- need to insert a chunk separator;
	      end if;
	   	  newCollabInfo := newCollabInfo || chunk;
	   end if;   
 
	   --DBMS_OUTPUT.PUT_LINE('thisCoaIdIndex='||thisCoaIdIndex||', length(chunk)='||length(chunk)||', next newCollabInfo='||newCollabInfo);
	
	END LOOP;
	     
    return newCollabInfo;
	
   EXCEPTION
     WHEN NO_DATA_FOUND THEN
       NULL;
     WHEN OTHERS THEN
       -- Consider logging the error and then re-raise
       RAISE;
	   
END REMOVE_CA_FROM_COLLAB_INFO;
/

CREATE OR REPLACE PROCEDURE CLEAN_ITEM(clnCoaId INTEGER, primary_key VARCHAR2, src_item_id NUMBER, ca_item_id NUMBER, collabInfo VARCHAR2)
IS
-- CLEAN an item by pk, both from collaboration area and source catalog
-- Item may be in only one or both.  Specified by positive-valued ids passed.
	newCollabInfo VARCHAR2(32767);
BEGIN
	DBMS_OUTPUT.PUT_LINE(' ');
	DBMS_OUTPUT.PUT_LINE('STARTING CLEAN_ITEM('||primary_key||', '||src_item_id||', '||ca_item_id||') ...');

        BACKUP_ITEM_NEW(clnCoaId, primary_key, src_item_id, ca_item_id);

	-- Do source item first 
	IF (src_item_id > 0) THEN
		DBMS_OUTPUT.PUT_LINE('     CLEANING SOURCE ITEM ID='||src_item_id||', collabInfo='||collabInfo);
		newCollabInfo := REMOVE_CA_FROM_COLLAB_INFO(collabInfo, clnCoaId);
		update itm set itm_collab_info = newCollabInfo where itm_id = src_item_id and itm_next_version_id=999999999;
		delete from cem where cem_src_entry_id = src_item_id;
	END IF;

	-- DO CA item
	IF (ca_item_id > 0) THEN
		DBMS_OUTPUT.PUT_LINE('     CLEANING CA ITEM ID='||ca_item_id);
		delete from itm where itm_id = ca_item_id;
		delete from ita where ita_item_id = ca_item_id;
		delete from itd where itd_item_id = ca_item_id;
		delete from icm where icm_item_id = ca_item_id;
		delete from cem where cem_ca_entry_id = ca_item_id;
		delete from cae where cae_entry_id = ca_item_id;
		delete from ceh where ceh_entry_key = primary_key;
		delete from cel where cel_entry_id = ca_item_id;
		delete from wee where wee_entry_id = ca_item_id;
	END IF;

	DBMS_OUTPUT.PUT_LINE('FINISHED CLEAN_ITEM('||primary_key||', '||src_item_id||', '||ca_item_id||')');

EXCEPTION
	WHEN OTHERS THEN
		DBMS_OUTPUT.PUT_LINE('Error in proc CLEAN_ITEM('||primary_key||', '||src_item_id||', '||ca_item_id||')');
END;
/
CREATE OR REPLACE PROCEDURE CLEAN_CA_ITEM(clnCoaId INTEGER, primary_key VARCHAR2, ca_item_id NUMBER)
IS
-- CLEAN an item known in a collaboration area (i.e. not a source catalog item)
--
-- WARNING: be careful not to pass in the id of an item in a source catalog; it will be deleted !!!!!!!
--
BEGIN
	DBMS_OUTPUT.PUT_LINE(' ');
	DBMS_OUTPUT.PUT_LINE('STARTING CLEAN_CA_ITEM('||primary_key||', '||ca_item_id||') ...');

        BACKUP_CA_ITEM(clnCoaId, primary_key, ca_item_id);

	-- DO CA item
	IF (ca_item_id > 0) THEN
		DBMS_OUTPUT.PUT_LINE('     CLEANING CA ITEM ID='||ca_item_id);
		delete from itm where itm_id = ca_item_id;
		delete from ita where ita_item_id = ca_item_id;
		delete from itd where itd_item_id = ca_item_id;
		delete from icm where icm_item_id = ca_item_id;
		delete from cem where cem_ca_entry_id = ca_item_id;
		delete from cae where cae_entry_id = ca_item_id;
		delete from ceh where ceh_entry_key = primary_key;
		delete from cel where cel_entry_id = ca_item_id;
		delete from wee where wee_entry_id = ca_item_id;
	END IF;

	DBMS_OUTPUT.PUT_LINE('FINISHED CLEAN_CA_ITEM('||primary_key||', '||ca_item_id||')');

EXCEPTION
	WHEN OTHERS THEN
		DBMS_OUTPUT.PUT_LINE('Error in proc CLEAN_CA_ITEM('||primary_key||', '||ca_item_id||')');
END;
/
CREATE OR REPLACE PROCEDURE CLEAN_SRC_ITEM(clnCoaId INTEGER, primary_key VARCHAR2, src_item_id NUMBER, collabInfo VARCHAR2)
IS
-- CLEAN an item known to be in a source catalog (i.e. not a collaboration area item).
--
-- Passing a CA item by mistake should be benign.
--
	newCollabInfo VARCHAR2(32767);
BEGIN
	DBMS_OUTPUT.PUT_LINE(' ');
	DBMS_OUTPUT.PUT_LINE('STARTING CLEAN_SRC_ITEM('||primary_key||', '||src_item_id||') ...');

        BACKUP_SRC_ITEM(clnCoaId, primary_key, src_item_id);

	-- Do source item first 
	IF (src_item_id > 0) THEN
		DBMS_OUTPUT.PUT_LINE('     CLEANING SOURCE ITEM ID='||src_item_id||', collabInfo='||collabInfo);
		newCollabInfo := REMOVE_CA_FROM_COLLAB_INFO(collabInfo, clnCoaId);
		update itm set itm_collab_info = newCollabInfo  where itm_id = src_item_id and itm_next_version_id=999999999;
		delete from cem where cem_src_entry_id = src_item_id;
	END IF;

	DBMS_OUTPUT.PUT_LINE('FINISHED CLEAN_SRC_ITEM('||primary_key||', '||src_item_id||')');

EXCEPTION
	WHEN OTHERS THEN
		DBMS_OUTPUT.PUT_LINE('Error in proc CLEAN_SRC_ITEM('||primary_key||', '||src_item_id||')');
END;
/

CREATE OR REPLACE FUNCTION GET_ITM_COLLAB_INFO(itm_id INTEGER) RETURN VARCHAR2 IS
    collabInfo VARCHAR2(32767):= '';
    TYPE cur_typ IS REF CURSOR;
    c cur_typ;
    query_str VARCHAR2(300);
BEGIN
	query_str := 'select itm_collab_info from itm where itm_id = :iid and itm_next_version_id=999999999';
    OPEN c FOR query_str USING itm_id;
    LOOP
        FETCH c INTO collabInfo;
        EXIT WHEN c%NOTFOUND;
    END LOOP;
    CLOSE c;
   RETURN collabInfo;
   EXCEPTION
     WHEN NO_DATA_FOUND THEN
       NULL;
     WHEN OTHERS THEN
       -- Consider logging the error and then re-raise
       RAISE;
END GET_ITM_COLLAB_INFO;
/
CREATE OR REPLACE PROCEDURE CLEAN_ITEMS_OF_PK_VIEW(View_Name VARCHAR2, Collab_Id INTEGER, src_catalog_id INTEGER, ca_catalog_id INTEGER)
IS
	TYPE MyCurTyp IS REF CURSOR;
	my_cv MyCurTyp;
	TYPE view_rec_type IS RECORD(itm_primary_key VARCHAR2(300)); -- dependent on ITM ddl
	view_rec view_rec_type;
	sql_stmt VARCHAR2(200);
	src_item_id number(9);
	ca_item_id number(9);
	pk VARCHAR2(300);
	collabInfo VARCHAR2(32767);
BEGIN
	DBMS_OUTPUT.PUT_LINE(' ');
	DBMS_OUTPUT.PUT_LINE('*************************************************');
	DBMS_OUTPUT.PUT_LINE('STARTING CLEAN_ITEMS_OF_PK_VIEW('||View_Name||', '||Collab_Id||', '
		||src_catalog_id||', '||ca_catalog_id||') ...');
	DBMS_OUTPUT.PUT_LINE(' ');
	sql_stmt := 'SELECT * FROM ' || LTRIM(RTRIM(View_Name));

	-- do all primary keys
	OPEN my_cv FOR sql_stmt;
	LOOP
		FETCH my_cv INTO view_rec;
		EXIT WHEN my_cv%NOTFOUND;
		pk := view_rec.itm_primary_key;
		src_item_id := GET_ITEM_ID(src_catalog_id, pk);
		collabInfo := GET_ITM_COLLAB_INFO(src_item_id);
		ca_item_id := GET_ITEM_ID(ca_catalog_id, pk);
		CLEAN_ITEM(Collab_Id, pk, src_item_id, ca_item_id, collabInfo);
	END LOOP;
	CLOSE my_cv;
	DBMS_OUTPUT.PUT_LINE(' ');
	DBMS_OUTPUT.PUT_LINE('*************************************************');
	DBMS_OUTPUT.PUT_LINE('FINISHED CLEAN_ITEMS_OF_PK_VIEW('||View_Name||', '||Collab_Id||', '
		||src_catalog_id||', '||ca_catalog_id||')');
	DBMS_OUTPUT.PUT_LINE(' ');
EXCEPTION
	WHEN OTHERS THEN
		DBMS_OUTPUT.PUT_LINE('Error in proc CLEAN_ITEMS_OF_PK_VIEW('||View_Name||', '||Collab_Id||', '
		||src_catalog_id||', '||ca_catalog_id||')');
END;
/
CREATE OR REPLACE PROCEDURE CLEAN_CA_ITEMS_OF_IID_VIEW(View_Name VARCHAR2, Collab_Id INTEGER, ca_catalog_id INTEGER)
IS
--
-- WARNING: BE SURE View_Name is an ITEM_ID_VIEW consisting of CA, not source, Items !!!!!
--		Else you risk deleting source catalog items !!!!!
--
	TYPE MyCurTyp IS REF CURSOR;
	my_cv MyCurTyp;
	TYPE view_rec_type IS RECORD(itm_id NUMBER(9)); -- dependent on ITM ddl
	view_rec view_rec_type;
	sql_stmt VARCHAR2(200);
	ca_item_id NUMBER(9);
	pk VARCHAR2(300);
BEGIN
	DBMS_OUTPUT.PUT_LINE(' ');
	DBMS_OUTPUT.PUT_LINE('*************************************************');
	DBMS_OUTPUT.PUT_LINE('STARTING CLEAN_CA_ITEMS_OF_IID_VIEW('||View_Name||', '||Collab_Id||', '
		||ca_catalog_id||') ...');
	DBMS_OUTPUT.PUT_LINE(' ');
	sql_stmt := 'SELECT * FROM ' || LTRIM(RTRIM(View_Name));

	-- do all item ids
	OPEN my_cv FOR sql_stmt;
	LOOP
		FETCH my_cv INTO view_rec;
		EXIT WHEN my_cv%NOTFOUND;
		ca_item_id := view_rec.itm_id;
		pk := GET_ITEM_PRIMARY_KEY(ca_catalog_id, ca_item_id);
		CLEAN_CA_ITEM(Collab_Id, pk, ca_item_id);
	END LOOP;
	CLOSE my_cv;
	DBMS_OUTPUT.PUT_LINE(' ');
	DBMS_OUTPUT.PUT_LINE('*************************************************');
	DBMS_OUTPUT.PUT_LINE('FINISHED CLEAN_CA_ITEMS_OF_IID_VIEW('||View_Name||', '||Collab_Id||', '
		||ca_catalog_id||')');
	DBMS_OUTPUT.PUT_LINE(' ');
EXCEPTION
	WHEN OTHERS THEN
		DBMS_OUTPUT.PUT_LINE('Error in proc CLEAN_CA_ITEMS_OF_IID_VIEW('||View_Name||', '||Collab_Id||', '
		||ca_catalog_id||')');
END;
/
CREATE OR REPLACE PROCEDURE CLEAN_SRC_ITEMS_OF_IID_VIEW(View_Name VARCHAR2, Collab_Id INTEGER, src_catalog_id INTEGER)
IS
--
-- View_Name is an ITEM_ID_VIEW consisting of source, not CA, Items.
--
	TYPE MyCurTyp IS REF CURSOR;
	my_cv MyCurTyp;
	TYPE view_rec_type IS RECORD(itm_id NUMBER(9)); -- dependent on ITM ddl
	view_rec view_rec_type;
	sql_stmt VARCHAR2(200);
	src_item_id NUMBER(9);
	pk VARCHAR2(300);
	collabInfo VARCHAR2(32767);
BEGIN
	DBMS_OUTPUT.PUT_LINE(' ');
	DBMS_OUTPUT.PUT_LINE('*************************************************');
	DBMS_OUTPUT.PUT_LINE('STARTING CLEAN_SRC_ITEMS_OF_IID_VIEW('||View_Name||', '||Collab_Id||', '
		||src_catalog_id||') ...');
	DBMS_OUTPUT.PUT_LINE(' ');
	sql_stmt := 'SELECT * FROM ' || LTRIM(RTRIM(View_Name));

	-- do all item ids
	OPEN my_cv FOR sql_stmt;
	LOOP
		FETCH my_cv INTO view_rec;
		EXIT WHEN my_cv%NOTFOUND;
		src_item_id := view_rec.itm_id;
		collabInfo := GET_ITM_COLLAB_INFO(src_item_id);
		pk := GET_ITEM_PRIMARY_KEY(src_catalog_id, src_item_id);
		CLEAN_SRC_ITEM(Collab_Id, pk, src_item_id, collabInfo);
	END LOOP;
	CLOSE my_cv;
	DBMS_OUTPUT.PUT_LINE(' ');
	DBMS_OUTPUT.PUT_LINE('*************************************************');
	DBMS_OUTPUT.PUT_LINE('FINISHED CLEAN_SRC_ITEMS_OF_IID_VIEW('||View_Name||', '||Collab_Id||', '
		||src_catalog_id||')');
	DBMS_OUTPUT.PUT_LINE(' ');
EXCEPTION
	WHEN OTHERS THEN
		DBMS_OUTPUT.PUT_LINE('Error in proc CLEAN_SRC_ITEMS_OF_IID_VIEW('||View_Name||', '||Collab_Id||', '
		||src_catalog_id||')');
END;
/


CREATE OR REPLACE PROCEDURE RESTORE_itmrsv(clnSrcCtgId INTEGER)
IS
 -- assumes source items only checked out to one collab area, because restores all items of a given source catalog.
	CURSOR my_cv is select * from itmrsv_clncoa where itm_container_id = clnSrcCtgId;
	itm_rec itmrsv_clncoa%ROWTYPE;
BEGIN
	DBMS_OUTPUT.PUT_LINE(' ');
	DBMS_OUTPUT.PUT_LINE('*** BEGIN RESTORE OF itmrsv TABLE');

	-- show some primary keys
	OPEN my_cv;
	LOOP
		FETCH my_cv INTO itm_rec;
		EXIT WHEN my_cv%NOTFOUND;
		DBMS_OUTPUT.PUT_LINE('Next itm row = ' || itm_rec.itm_id||', '||itm_rec.itm_collab_info);
	
		-- select existing row if any
		delete from itm where (                                        
    itm_company_id = itm_rec.itm_company_id and
    itm_id = itm_rec.itm_id  and
    itm_container_id = itm_rec.itm_container_id  and
    itm_primary_key  = itm_rec.itm_primary_key  and
    itm_version_id = itm_rec.itm_version_id and
    itm_next_version_id = itm_rec.itm_next_version_id 
    -- and itm_status = itm_rec.status 
    -- and itm_collab_info  = itm_rec.itm_collab_info --- XXX varchar2(3000) compare?
    -- and itm_last_modified = itm_rec.itm_last_modified
		); 
		
		-- restore row
		insert into itm values (                                       
    itm_rec.itm_company_id,
    itm_rec.itm_id  ,
    itm_rec.itm_container_id  ,
    itm_rec.itm_primary_key  ,
    itm_rec.itm_version_id ,
    itm_rec.itm_next_version_id  ,
    itm_rec.itm_status  ,
    itm_rec.itm_collab_info,
    itm_rec.itm_last_modified
		);  

		
	END LOOP;


	CLOSE my_cv;
	commit;

EXCEPTION
	WHEN OTHERS THEN
		DBMS_OUTPUT.PUT_LINE('Error in proc RESTORE_itm');
END;
/


CREATE OR REPLACE PROCEDURE RESTORE_itm(clnCoaCtgId INTEGER)
IS
	CURSOR my_cv is select * from itm_clncoa where itm_container_id = clnCoaCtgId;
	itm_rec itm_clncoa%ROWTYPE;
BEGIN
	DBMS_OUTPUT.PUT_LINE(' ');
	DBMS_OUTPUT.PUT_LINE('*** BEGIN RESTORE OF itm TABLE');

	-- show some primary keys
	OPEN my_cv;
	LOOP
		FETCH my_cv INTO itm_rec;
		EXIT WHEN my_cv%NOTFOUND;
		DBMS_OUTPUT.PUT_LINE('Next itm row = ' || itm_rec.itm_container_id||', '||itm_rec.itm_primary_key);
	
		-- delete existing row if any
		delete from itm where (                                        
    itm_company_id = itm_rec.itm_company_id and
    itm_id = itm_rec.itm_id  and
    itm_container_id = itm_rec.itm_container_id  and
    itm_primary_key  = itm_rec.itm_primary_key  and
    itm_version_id = itm_rec.itm_version_id and
    itm_next_version_id = itm_rec.itm_next_version_id 
    -- and itm_status = itm_rec.itm_status
    -- and itm_collab_info  = itm_rec.itm_collab_info --- XXX varchar2(3000) compare?
    -- and itm_last_modified = itm_rec.itm_last_modified
		); 
		
		-- restore row
		insert into itm values (                                       
    itm_rec.itm_company_id,
    itm_rec.itm_id  ,
    itm_rec.itm_container_id  ,
    itm_rec.itm_primary_key  ,
    itm_rec.itm_version_id ,
    itm_rec.itm_next_version_id  ,
    itm_rec.itm_status  ,
    itm_rec.itm_collab_info,
    itm_rec.itm_last_modified
		); 

		
	END LOOP;


	CLOSE my_cv;
	commit;

EXCEPTION
	WHEN OTHERS THEN
		DBMS_OUTPUT.PUT_LINE('Error in proc RESTORE_itm');
END;
/


CREATE OR REPLACE PROCEDURE RESTORE_ita(clnCoaCtgId INTEGER)
IS
	CURSOR my_cv is select * from ita_clncoa where ita_catalog_id = clnCoaCtgId;
	ita_rec ita_clncoa%ROWTYPE;
BEGIN
	DBMS_OUTPUT.PUT_LINE(' ');
	DBMS_OUTPUT.PUT_LINE('*** BEGIN RESTORE OF ita TABLE');

	-- show some primary keys
	OPEN my_cv;
	LOOP
		FETCH my_cv INTO ita_rec;
		EXIT WHEN my_cv%NOTFOUND;
        -- no confirm output line; generates excess amount of output for Gap; 10/2/05 Dennis
		-- DBMS_OUTPUT.PUT_LINE('Next ita row = ' || ita_rec.ita_item_id||', '||ita_rec.ita_node_id);
	
		-- delete existing row if any; 
		delete from ita where (                                        
    ita_company_id = ita_rec.ita_company_id and
    ita_catalog_id = ita_rec.ita_catalog_id  and
    ita_item_id = ita_rec.ita_item_id  and
    ita_node_id  = ita_rec.ita_node_id  and
    -- ita_value_numeric = ita_rec.ita_value_numeric and -- avoid potentially problematical numerical equality testing
    ita_value_string = ita_rec.ita_value_string  and  
    ita_version_id = ita_rec.ita_version_id  and
    ita_next_version_id  = ita_rec.ita_next_version_id and
    ita_occurrence_id = ita_rec.ita_occurrence_id
    -- ita_value_string_ignorecase = ita_rec.ita_value_string_ignorecase
		); 
		
		-- restore row
		insert into ita values (                                       
    ita_rec.ita_company_id,
    ita_rec.ita_catalog_id  ,
    ita_rec.ita_item_id  ,
    ita_rec.ita_node_id  ,
    ita_rec.ita_value_numeric ,
    ita_rec.ita_value_string  ,
    ita_rec.ita_version_id ,
    ita_rec.ita_next_version_id ,
    ita_rec.ita_occurrence_id ,
    ita_rec.ita_value_string_ignorecase
		); 

		
	END LOOP;


	CLOSE my_cv;
	commit;

EXCEPTION
	WHEN OTHERS THEN
		DBMS_OUTPUT.PUT_LINE('Error in proc RESTORE_ita');
END;
/


CREATE OR REPLACE PROCEDURE RESTORE_itd(clnCoaCtgId INTEGER)
IS
	CURSOR my_cv is select * from itd_clncoa where itd_container_id = clnCoaCtgId;
	itd_rec itd_clncoa%ROWTYPE;
BEGIN
	DBMS_OUTPUT.PUT_LINE(' ');
	DBMS_OUTPUT.PUT_LINE('*** BEGIN RESTORE OF itd TABLE');

	-- show some primary keys
	OPEN my_cv;
	LOOP
		FETCH my_cv INTO itd_rec;
		EXIT WHEN my_cv%NOTFOUND;
		DBMS_OUTPUT.PUT_LINE('Next itd row = ' || itd_rec.itd_container_id||', '||itd_rec.itd_item_id);
	
		-- delete existing row if any
		delete from itd where (                                        
    itd_company_id = itd_rec.itd_company_id and
    itd_item_id = itd_rec.itd_item_id  and
    itd_container_id = itd_rec.itd_container_id  and
    -- itd_blob  = itd_rec.itd_blob  and
    itd_version_id = itd_rec.itd_version_id and
    itd_next_version_id = itd_rec.itd_next_version_id 
		); 
		
		-- restore row
		insert into itd values (                                       
    itd_rec.itd_company_id,
    itd_rec.itd_item_id  ,
    itd_rec.itd_container_id  ,
    itd_rec.itd_blob  ,
    itd_rec.itd_version_id ,
    itd_rec.itd_next_version_id,
    itd_rec.itd_bit_varchar
		); 

		
	END LOOP;


	CLOSE my_cv;
	commit;

EXCEPTION
	WHEN OTHERS THEN
		DBMS_OUTPUT.PUT_LINE('Error in proc RESTORE_itd');
END;
/


CREATE OR REPLACE PROCEDURE RESTORE_icm(clnCoaCtgId INTEGER)
IS
	CURSOR my_cv is select * from icm_clncoa where icm_catalog_id = clnCoaCtgId;
	icm_rec icm_clncoa%ROWTYPE;
BEGIN
	DBMS_OUTPUT.PUT_LINE(' ');
	DBMS_OUTPUT.PUT_LINE('*** BEGIN RESTORE OF icm TABLE');

	-- show some primary keys
	OPEN my_cv;
	LOOP
		FETCH my_cv INTO icm_rec;
		EXIT WHEN my_cv%NOTFOUND;
		DBMS_OUTPUT.PUT_LINE('Next icm row = ' || icm_rec.icm_item_id);
	
		-- delete existing rowand if any
		delete from icm where (                                        
    icm_company_id = icm_rec.icm_company_id and
    icm_catalog_id = icm_rec.icm_catalog_id  and
    icm_item_id = icm_rec.icm_item_id  and
    icm_cat_tree_id  = icm_rec.icm_cat_tree_id  and
	icm_category_id  = icm_rec.icm_category_id  and
	icm_version_id  = icm_rec.icm_version_id  and
    icm_next_version_id = icm_rec.icm_next_version_id 
		); 
		
		-- restore row
		insert into icm values (                                       
    icm_rec.icm_company_id,
    icm_rec.icm_catalog_id  ,
    icm_rec.icm_item_id  ,
    icm_rec.icm_cat_tree_id  ,
icm_rec.icm_category_id,
icm_rec.icm_version_id,
    icm_rec.icm_next_version_id 
		); 
	END LOOP;
	CLOSE my_cv;
    commit;

EXCEPTION
	WHEN OTHERS THEN
		DBMS_OUTPUT.PUT_LINE('Error in proc RESTORE_icm');
END;
/


CREATE OR REPLACE PROCEDURE RESTORE_cel(clnCoaId INTEGER)
IS
	CURSOR my_cv is select * from cel_clncoa where cel_container_id = clnCoaId;
		-- "container" id here is actually the CA id
	cel_rec cel_clncoa%ROWTYPE;
BEGIN
	DBMS_OUTPUT.PUT_LINE(' ');
	DBMS_OUTPUT.PUT_LINE('*** BEGIN RESTORE OF cel TABLE');

	-- show some primary keys
	OPEN my_cv;
	LOOP
		FETCH my_cv INTO cel_rec;
		EXIT WHEN my_cv%NOTFOUND;
		DBMS_OUTPUT.PUT_LINE('Next cel row = ' || cel_rec.cel_entry_id);
	
		-- delete existing row if any
		delete from cel where (                                        
    cel_cmp_id = cel_rec.cel_cmp_id and
    cel_id = cel_rec.cel_id  and
    cel_user_id = cel_rec.cel_user_id  and                  
    -- cel_time_acquired = cel_rec.cel_time_acquired  and      -- XXX Date compare not working?  
    -- cel_time_of_expiry = cel_rec.cel_time_of_expiry   and    -- XXX Date compare not working?       
    cel_container_id = cel_rec.cel_container_id  and         
    cel_container_type = cel_rec.cel_container_type  and 
    cel_entry_id = cel_rec.cel_entry_id  and
    cel_step_path_id = cel_rec.cel_step_path_id 
		); 
		
		-- restore row
		insert into cel values (                                       
    	cel_rec.cel_cmp_id,
    	cel_rec.cel_id  ,
	cel_rec.cel_user_id,
	cel_rec.cel_time_acquired,
	cel_rec.cel_time_of_expiry,
	cel_rec.cel_container_id,
	cel_rec.cel_container_type,
    	cel_rec.cel_entry_id  ,
    	cel_rec.cel_step_path_id 
		); 
	END LOOP;
	CLOSE my_cv;
    commit;

EXCEPTION
	WHEN OTHERS THEN
		DBMS_OUTPUT.PUT_LINE('Error in proc RESTORE_cel');
END;
/


CREATE OR REPLACE PROCEDURE RESTORE_cae(clnCoaId INTEGER)
IS
	CURSOR my_cv is select * from cae_clncoa where cae_ca_id = clnCoaId;
	cae_rec cae_clncoa%ROWTYPE;
BEGIN
	DBMS_OUTPUT.PUT_LINE(' ');
	DBMS_OUTPUT.PUT_LINE('*** BEGIN RESTORE OF cae TABLE');

	-- show some primary keys
	OPEN my_cv;
	LOOP
		FETCH my_cv INTO cae_rec;
		EXIT WHEN my_cv%NOTFOUND;
		DBMS_OUTPUT.PUT_LINE('Next cae row = ' || cae_rec.cae_step_path_id);
	
		-- delete existing row if any
		delete from cae where (                                        
    cae_cmp_id = cae_rec.cae_cmp_id and
    cae_ca_id = cae_rec.cae_ca_id  and
    cae_entry_id = cae_rec.cae_entry_id  and
    cae_step_path_id  = cae_rec.cae_step_path_id  and
    cae_deadline_step_path_id = cae_rec.cae_deadline_step_path_id and
    --cae_deadline = cae_rec.cae_deadline  and  -- dont use date XXX why 
    cae_data = cae_rec.cae_data  and
    cae_available  = cae_rec.cae_available  and
    cae_lock_id = cae_rec.cae_lock_id
		); 
		
		-- restore row
		insert into cae values (                                       
    cae_rec.cae_cmp_id,
    cae_rec.cae_ca_id  ,
    cae_rec.cae_entry_id  ,
    cae_rec.cae_step_path_id  ,
    cae_rec.cae_deadline_step_path_id ,
    cae_rec.cae_deadline  ,
    cae_rec.cae_data  ,
    cae_rec.cae_available  ,
    cae_rec.cae_lock_id 
		); 

		
	END LOOP;


	CLOSE my_cv;
	commit;

EXCEPTION
	WHEN OTHERS THEN
		DBMS_OUTPUT.PUT_LINE('Error in proc RESTORE_cae');
END;
/



CREATE OR REPLACE PROCEDURE RESTORE_cem(clnCoaId INTEGER)
IS
	CURSOR my_cv is select * from cem_clncoa where cem_ca_id = clnCoaId;
	cem_rec cem_clncoa%ROWTYPE;
BEGIN
	DBMS_OUTPUT.PUT_LINE(' ');
	DBMS_OUTPUT.PUT_LINE('*** BEGIN RESTORE OF cem TABLE');

	-- show some primary keys
	OPEN my_cv;
	LOOP
		FETCH my_cv INTO cem_rec;
		EXIT WHEN my_cv%NOTFOUND;
		DBMS_OUTPUT.PUT_LINE('Next cem row = ' || cem_rec.cem_ca_entry_id);
	
		-- delete existing row if any
		delete from cem where (                                        
    cem_cmp_id = cem_rec.cem_cmp_id and
    cem_ca_id = cem_rec.cem_ca_id  and
    cem_ca_entry_id = cem_rec.cem_ca_entry_id  and
    cem_src_ctg_id  = cem_rec.cem_src_ctg_id  and
    cem_src_entry_id = cem_rec.cem_src_entry_id 
		); 
		
		-- restore row
		insert into cem values (                                       
    cem_rec.cem_cmp_id,
    cem_rec.cem_ca_id  ,
    cem_rec.cem_ca_entry_id  ,
    cem_rec.cem_src_ctg_id  ,
    cem_rec.cem_src_entry_id 
		); 
	END LOOP;
	CLOSE my_cv;
    commit;

EXCEPTION
	WHEN OTHERS THEN
		DBMS_OUTPUT.PUT_LINE('Error in proc RESTORE_cem');
END;
/



CREATE OR REPLACE PROCEDURE RESTORE_ceh(clnCAName VARCHAR)
IS
	CURSOR my_cv is select * from ceh_clncoa where ceh_ca_name = clnCAName;
	ceh_rec ceh_clncoa%ROWTYPE;
BEGIN
	DBMS_OUTPUT.PUT_LINE(' ');
	DBMS_OUTPUT.PUT_LINE('*** BEGIN RESTORE OF ceh TABLE');

	-- show some primary keys
	OPEN my_cv;
	LOOP
		FETCH my_cv INTO ceh_rec;
		EXIT WHEN my_cv%NOTFOUND;
        -- no confirm output line; generates excess amount of output for Gap; 10/2/05 Dennis
		-- DBMS_OUTPUT.PUT_LINE('Next ceh row = ' || ceh_rec.ceh_event||', '||ceh_rec.ceh_entry_key);
	
		-- delete existing row if any
		delete from ceh where (                                        
    ceh_cmp_id = ceh_rec.ceh_cmp_id and
    ceh_id = ceh_rec.ceh_id   -- dont need anything more
    --and ceh_date = ceh_rec.ceh_date  and   -- XXX date compare
    -- ceh_entry_key  = ceh_rec.ceh_entry_key  and
    -- ceh_ca_name = ceh_rec.ceh_ca_name and
    -- ceh_wfl_name = ceh_rec.ceh_wfl_name  and  
    -- ceh_user_name = ceh_rec.ceh_user_name  and
    -- ceh_step_path  = ceh_rec.ceh_step_path and
    -- ceh_event = ceh_rec.ceh_event  and
    -- ceh_data  = ceh_rec.ceh_data
	-- ceh_row_order = ceh_rec.ceh_row_order
		); 
		
		-- restore row
		insert into ceh values (                                       
    ceh_rec.ceh_cmp_id,
    ceh_rec.ceh_id  ,
    ceh_rec.ceh_date  ,
    ceh_rec.ceh_entry_key  ,
    ceh_rec.ceh_ca_name ,
    ceh_rec.ceh_wfl_name  ,
    ceh_rec.ceh_user_name  ,
    ceh_rec.ceh_step_path  ,
    ceh_rec.ceh_event ,
    ceh_rec.ceh_data,
	ceh_rec.ceh_row_order
		); 

		
	END LOOP;


	CLOSE my_cv;
	commit;

EXCEPTION
	WHEN OTHERS THEN
		DBMS_OUTPUT.PUT_LINE('Error in proc RESTORE_ceh');
END;
/

CREATE OR REPLACE PROCEDURE RESTORE_wee(clnCoaId INTEGER)
IS
	CURSOR my_cv is select * from wee_clncoa where coa_id =  clnCoaId;
	wee_rec wee_clncoa%ROWTYPE;
BEGIN
	DBMS_OUTPUT.PUT_LINE(' ');
	DBMS_OUTPUT.PUT_LINE('*** BEGIN RESTORE OF wee TABLE');

	-- show some primary keys
	OPEN my_cv;
	LOOP
		FETCH my_cv INTO wee_rec;
		EXIT WHEN my_cv%NOTFOUND;
		DBMS_OUTPUT.PUT_LINE('Next wee row = ' || wee_rec.wee_entry_id);
	
		-- delete existing row if any
		delete from wee where (                                        
    wee_event_id = wee_rec.wee_event_id  and
    wee_entry_id = wee_rec.wee_entry_id
    -- and wee_event_entry_status = wee_rec.wee_event_entry_status -- XXX failing string compare
		); 
		
		-- restore row
		 insert into wee values (                                       
    wee_rec.wee_event_id,
    wee_rec.wee_entry_id,
    wee_rec.wee_event_entry_status
		); 
	END LOOP;
	CLOSE my_cv;
    commit;

EXCEPTION
	WHEN OTHERS THEN
		DBMS_OUTPUT.PUT_LINE('Error in proc RESTORE_wee');
END;
/

CREATE OR REPLACE PROCEDURE RESTORE_all(clnCoaId INTEGER)
IS
	clnCAName varchar2(100);
	clnSrcCtgId number(9);
	clnCoaCtgId number(9);
BEGIN
  clnSrcCtgId := GET_SRC_CTG_ID_FROM_CA_ID(clnCoaId);
  clnCAName := GET_CA_NAME_FROM_ID(clnCoaId);
  clnCoaCtgId := GET_CA_CATALOG_ID_FROM_CA_ID(clnCoaId);

RESTORE_wee(clnCoaId);
RESTORE_ceh(clnCAName);
RESTORE_cel(clnCoaId);
RESTORE_cem(clnCoaId);
RESTORE_cae(clnCoaId);
RESTORE_itm(clnCoaCtgId);
RESTORE_ita(clnCoaCtgId);
RESTORE_itd(clnCoaCtgId);
RESTORE_icm(clnCoaCtgId); 
RESTORE_itmrsv(clnSrcCtgId); -- assumes source items only checked out to one collab area


EXCEPTION
	WHEN OTHERS THEN
		DBMS_OUTPUT.PUT_LINE('Error in proc RESTORE_all');
END;
/


CREATE OR REPLACE FUNCTION GET_CATALOG_ID_FROM_NAME(ctg_name VARCHAR2) RETURN NUMBER IS
    out_id NUMBER := 0;
    TYPE cur_typ IS REF CURSOR;
    c cur_typ;
    query_str VARCHAR2(200);
BEGIN
    query_str := 'select distinct ctg_id from ctg where ctg_name = :name';
    OPEN c FOR query_str USING ctg_name;
    LOOP
        FETCH c INTO out_id;
        EXIT WHEN c%NOTFOUND;
    END LOOP;
    CLOSE c;
   RETURN out_id;
   EXCEPTION
     WHEN NO_DATA_FOUND THEN
       NULL;
     WHEN OTHERS THEN
       -- Consider logging the error and then re-raise
       RAISE;
END GET_CATALOG_ID_FROM_NAME;
/


CREATE OR REPLACE FUNCTION GET_COLLAB_ID_FROM_NAME(ca_name VARCHAR2) RETURN NUMBER IS
    out_id NUMBER := 0;
    TYPE cur_typ IS REF CURSOR;
    c cur_typ;
    query_str VARCHAR2(200);
BEGIN
    query_str := 'select distinct coa_id from coa where coa_name = :name';
    OPEN c FOR query_str USING ca_name;
    LOOP
        FETCH c INTO out_id;
        EXIT WHEN c%NOTFOUND;
    END LOOP;
    CLOSE c;
   RETURN out_id;
   EXCEPTION
     WHEN NO_DATA_FOUND THEN
       NULL;
     WHEN OTHERS THEN
       -- Consider logging the error and then re-raise
       RAISE;
END GET_COLLAB_ID_FROM_NAME;
/



CREATE OR REPLACE PROCEDURE REPORT_VIEWS(which_checks NUMBER, keys_to_show NUMBER)
IS
-- The Views are assumed to exist and contain data for the desired collaboration area.
BEGIN 
  DBMS_OUTPUT.enable(1000000);
  
-- The comment "--BRIEF--" asserts that this view is being built and could be displayed, but is suppressed for brevity of output
-- The comment "--BRIEF TOO BIG -" asserts the same, but tries to say that we REALLY don't want to display this view.
-- BRIEF --COUNT_SHOW_SOME_PK_VIEW('SRC_CHECKED_OUT_PRIMARY_KEY', 'Primary keys of all source catalog items checked out to this CA', keys_to_show); 
-- BRIEF --COUNT_SHOW_SOME_PK_VIEW('CA_ALL_PRIMARY_KEY', 'Primary keys of all items in the CA catalog', keys_to_show); 
-- BRIEF TOO BIG  -- COUNT_SHOW_SOME_PK_VIEW('SRC_ALL_PRIMARY_KEY', 'All primary keys of source catalog items', keys_to_show); 
--COUNT_SHOW_SOME_ITEM_ID_VIEW('ERROR_EVENT_ITEM_ID', 'Item ids of all collaboration area items in workflow events with ERROR status', keys_to_show); 
--COUNT_SHOW_SOME_ITEM_ID_VIEW('NEW_EVENT_ITEM_ID', 'Item ids of all collaboration area items in workflow events with NEW status', keys_to_show); 
--COUNT_SHOW_SOME_ITEM_ID_VIEW('DONE_EVENT_ITEM_ID', 'Item ids of all collaboration area items in workflow events with DONE status', keys_to_show); 
--COUNT_SHOW_SOME_ITEM_ID_VIEW('PROCESSING_EVENT_ITEM_ID', 'Item ids of all collaboration area items in workflow events with PROCESSING status', keys_to_show); 
--COUNT_SHOW_SOME_ITEM_ID_VIEW('GOOD_EVENT_ITEM_ID', 'Item ids of all collaboration area and source items that are only in NEW or DONE workflow events', keys_to_show); 
-- COUNT_SHOW_SOME_PK_VIEW('SRC_PRIMARY_KEY_IN_CEM', 'Primary keys of source items with corresponding CA items in CEM table', keys_to_show); 
-- BRIEF --COUNT_SHOW_SOME_PK_VIEW('SRC_PRIMARY_KEY_IN_CEM_CAE', 'Primary keys of source items with corresponding CA items that are in both the CEM and CAE tables in a state of integrity', keys_to_show);
-- BRIEF TOO BIG  -- COUNT_SHOW_SOME_PK_VIEW('SRC_PRIMARY_KEY_NOT_IN_CEM_CAE', 'All source catalog primary keys not in SRC_PRIMARY_KEY_IN_CEM_CAE', keys_to_show); 
--COUNT_SHOW_SOME_PK_VIEW('SRC_PRIMARY_KEY_EVENT_ONLY', 'Primary keys of source items absent from CAE, CEM, or both, but in either a NEW or DONE event', keys_to_show); 
--COUNT_SHOW_SOME_PK_VIEW('SRC_PRIMARY_KEY_OK_CEL', 'Primary keys of checked out source items which either have no rows, or only good rows, in CEL', keys_to_show);
--COUNT_SHOW_SOME_PK_VIEW('SRC_GOOD_PRIMARY_KEY', 'Primary keys of checked out source items which appear to be in a state of integrity', keys_to_show);
-- BRIEF --COUNT_SHOW_SOME_PK_VIEW('SRC_BAD_PRIMARY_KEY', 'Primary keys of checked out source items that are true ghost items', keys_to_show); 
-- BRIEF --COUNT_SHOW_SOME_PK_VIEW('ADD_PRIMARY_KEY', 'Primary keys of CA items NOT the pk of any (good or bad) checked-out source item', keys_to_show);
-- BRIEF --COUNT_SHOW_SOME_PK_VIEW('ADD_PRIMARY_KEY_IN_CEM_CAE', 'Primary keys of added CA items that are in both the CEM and CAE tables in a state of integrity', keys_to_show); 
--COUNT_SHOW_SOME_PK_VIEW('ADD_PRIMARY_KEY_NOT_IN_CEM_CAE', 'Primary keys of added CA items that are not in ADD_PRIMARY_KEY_IN_CEM_CAE', keys_to_show); 
--COUNT_SHOW_SOME_PK_VIEW('ADD_PRIMARY_KEY_EVENT_ONLY', 'Primary keys of added CA items that are NOT in CEM, CAE, but which have only good eventsXXX', keys_to_show); 
--COUNT_SHOW_SOME_PK_VIEW('ADD_PRIMARY_KEY_OK_CEL', 'Primary keys of added CA items which either have no rows, or only good rows, in CEL', keys_to_show);
--COUNT_SHOW_SOME_PK_VIEW('ADD_GOOD_PRIMARY_KEY', 'Primary keys of added CA items which appear to be in a state of integrity', keys_to_show);
-- BRIEF --COUNT_SHOW_SOME_PK_VIEW('ADD_BAD_PRIMARY_KEY', 'Primary keys of added CA items that are true ghost items', keys_to_show); 
--COUNT_SHOW_SOME_PK_VIEW('IN_INITIAL_PRIMARY_KEY', 'Primary keys of CA items in the workflow Initial step', keys_to_show); 
--COUNT_SHOW_SOME_PK_VIEW('CA_ITM_NO_ITA_PRIMARY_KEY', 'Primary keys of ITM rows of CA catalog items with no corresponding ITA rows', keys_to_show);
-- BRIEF --COUNT_SHOW_SOME_ITEM_ID_VIEW('CAE_ORPHAN_ITEM_ID', 'CAE orphan item ids - CA catalog item ids found in CAE with no corresponding ITM row', keys_to_show);
-- BRIEF --COUNT_SHOW_SOME_ITEM_ID_VIEW('CEM_SRC_ORPHAN_ITEM_ID', 'CEM source orphan item ids - Source catalog item ids found in CEM with no corresponding ITM row', keys_to_show);
-- BRIEF --COUNT_SHOW_SOME_ITEM_ID_VIEW('CEM_CA_ORPHAN_ITEM_ID', 'CEM CA orphan item ids - CA catalog item ids found in CEM with no corresponding ITM row', keys_to_show);
--COUNT_SHOW_SOME_ITEM_ID_VIEW('CEL_CA_ORPHAN_ITEM_ID', 'CA catalog item ids found in CEL with no corresponding ITM row', keys_to_show);
--COUNT_SHOW_SOME_ITEM_ID_VIEW('WEE_CA_ORPHAN_ITEM_ID', 'CA catalog item ids found in WEE with no corresponding ITM row', keys_to_show);
--COUNT_SHOW_SOME_ITEM_ID_VIEW('CA_ITA_NO_ITM', 'CA catalog ITA rows with no corresponding ITM row', keys_to_show);
--COUNT_SHOW_SOME_ITEM_ID_VIEW('CA_ITM_NO_ITA', 'CA catalog ITM rows with no corresponding ITA rows', keys_to_show);
--COUNT_SHOW_SOME_ITEM_ID_VIEW('TOTAL_BAD_ITEM_EVTQ', 'CA Item ids having workflow events in ERROR or PROCESSING or with orphan WEE rows', keys_to_show);
-- BRIEF --COUNT_SHOW_SOME_ITEM_ID_VIEW('ADDITIONAL_BAD_CA_ITEM_ID', 'All CA catalog orphan item ids', keys_to_show);
-- COUNT_SHOW_SOME_ITEM_ID_VIEW('ADDITIONAL_BAD_SRC_ITEM_ID', 'Source items that are CEM orphans', keys_to_show);
DBMS_OUTPUT.Put_Line(' ');
DBMS_OUTPUT.Put_Line(' ');
DBMS_OUTPUT.Put_Line(' ');
COUNT_SHOW_SOME_PK_VIEW('TOTAL_BAD_PRIMARY_KEY', 'Complete list of primary keys of true ghost items', keys_to_show);
COUNT_SHOW_SOME_ITEM_ID_VIEW('TOTAL_BAD_CA_ITEM_ID', 'Complete list of CA Catalog true ghost items item ids', keys_to_show);
COUNT_SHOW_SOME_ITEM_ID_VIEW('TOTAL_BAD_SRC_ITEM_ID', 'Complete list of Source catalog true ghost items item ids', keys_to_show);
DBMS_OUTPUT.Put_Line(' ');
DBMS_OUTPUT.Put_Line(' ');
DBMS_OUTPUT.Put_Line(' ');
-- BRIEF --COUNT_SHOW_SOME_PK_VIEW('TOTAL_GOOD_PRIMARY_KEY', 'Complete list of primary keys of good CA items, i.e. non-ghost items', keys_to_show);
-- BRIEF --COUNT_SHOW_SOME_ITEM_ID_VIEW('TOTAL_GOOD_CA_ITEM_ID', 'Complete list of CA Item ids of good CA items, i.e. non-ghost items', keys_to_show);
-- BRIEF --COUNT_SHOW_SOME_ITEM_ID_VIEW('TOTAL_GOOD_SRC_ITEM_ID', 'Complete list of source Item ids of good CA items, i.e. non-ghost items', keys_to_show);


  --DBMS_OUTPUT.Put_Line(' ');
  --DBMS_OUTPUT.Put_Line('*** REPORT - FULL LIST OF PRIMARY KEYS OF GOOD ITEMS, WHOSE PRIMARY KEYS ARE KNOWN');
  --SHOW_ALL_PK_VIEW( 'TOTAL_GOOD_PRIMARY_KEY', 'All bad Items, by primary key.' );
  --DBMS_OUTPUT.Put_Line(' ');
  --DBMS_OUTPUT.Put_Line('*** REPORT - FULL LIST OF PRIMARY KEYS OF BAD ITEMS, WHOSE PRIMARY KEYS ARE KNOWN');
  --SHOW_ALL_PK_VIEW( 'TOTAL_BAD_PRIMARY_KEY', 'All bad Items, by primary key.' );
  --DBMS_OUTPUT.Put_Line(' ');
  --DBMS_OUTPUT.Put_Line('*** REPORT - FULL LIST OF ITEM IDS OF BAD COLLABORATION AREA ITEMS, SOME KNOWN ALSO BY PK, SOME KNOWN ONLY BY ITEM ID');
  --SHOW_ALL_IID_VIEW( 'TOTAL_BAD_CA_ITEM_ID', 'All bad CA Items, by item id.' );
  --DBMS_OUTPUT.Put_Line(' ');
  --DBMS_OUTPUT.Put_Line('*** REPORT - FULL LIST OF ITEM IDS OF BAD SOURCE CATALOG ITEMS, SOME KNOWN ALSO BY PK, SOME KNOWN ONLY BY ITEM ID');
  --SHOW_ALL_IID_VIEW( 'TOTAL_BAD_SRC_ITEM_ID', 'All bad SRC Items, by item id.' );
  --DBMS_OUTPUT.Put_Line(' ');
  --DBMS_OUTPUT.Put_Line('*** DONE WITH REPORTS');
  --COMMIT; 
END; 
/

CREATE OR REPLACE FUNCTION GET_CA_CATALOG_ID_FROM_CA_ID(clnCoaId INTEGER) RETURN NUMBER IS
	TYPE MyCurTyp IS REF CURSOR;
	clnCoaCtgId number(9);
        c MyCurTyp;
BEGIN
  OPEN c FOR 'select COA_DST_CONTAINER_ID from coa where coa_id = ' || clnCoaId; FETCH c INTO clnCoaCtgId;
    CLOSE c;
   RETURN clnCoaCtgId;
   EXCEPTION
     WHEN NO_DATA_FOUND THEN
       NULL;
     WHEN OTHERS THEN
       -- Consider logging the error and then re-raise
       RAISE;
END GET_CA_CATALOG_ID_FROM_CA_ID;
/

CREATE OR REPLACE FUNCTION GET_SRC_CTG_ID_FROM_CA_ID(clnCoaId INTEGER) RETURN NUMBER IS
	TYPE MyCurTyp IS REF CURSOR;
	clnSrcCtgId number(9);
        c MyCurTyp;
BEGIN
  OPEN c FOR 'select COA_SRC_CONTAINER_ID from coa where coa_id = ' || clnCoaId; FETCH c INTO clnSrcCtgId;
    CLOSE c;
   RETURN clnSrcCtgId;
   EXCEPTION
     WHEN NO_DATA_FOUND THEN
       NULL;
     WHEN OTHERS THEN
       -- Consider logging the error and then re-raise
       RAISE;
END GET_SRC_CTG_ID_FROM_CA_ID;
/


CREATE OR REPLACE FUNCTION GET_CA_NAME_FROM_ID(clnCoaId INTEGER) RETURN varchar2 IS
	TYPE MyCurTyp IS REF CURSOR;
	clnCAName varchar2(100);
        c MyCurTyp;
BEGIN
    OPEN c FOR 'select COA_NAME from coa where coa_id = ' || clnCoaId; FETCH c INTO clnCAName;
    CLOSE c;
   RETURN clnCAName;
   EXCEPTION
     WHEN NO_DATA_FOUND THEN
       NULL;
     WHEN OTHERS THEN
       -- Consider logging the error and then re-raise
       RAISE;
END GET_CA_NAME_FROM_ID;
/


CREATE OR REPLACE PROCEDURE DELETE_CA_FROM_BACKUP_TABLES(clnCoaId INTEGER)
IS
-- The tables are assumed to exist and contain data for the desired collaboration area.
	clnCAName varchar2(100);
	clnSrcCtgId number(9);
	clnCoaCtgId number(9);
BEGIN
  clnSrcCtgId := GET_SRC_CTG_ID_FROM_CA_ID(clnCoaId);
  clnCAName := GET_CA_NAME_FROM_ID(clnCoaId);
  clnCoaCtgId := GET_CA_CATALOG_ID_FROM_CA_ID(clnCoaId);

  DBMS_OUTPUT.enable(1000000);

execute immediate 'delete ITMRSV_CLNCOA where itm_container_id =' || clnSrcCtgId;
execute immediate 'delete ITM_CLNCOA where itm_container_id =' || clnCoaCtgId;
execute immediate 'delete ITA_CLNCOA where ita_catalog_id = ' ||clnCoaCtgId;
execute immediate 'delete ICM_CLNCOA where icm_catalog_id =' || clnCoaCtgId;
execute immediate 'delete CEM_CLNCOA where cem_ca_id = ' ||clnCoaId;
execute immediate 'delete CAE_CLNCOA where cae_ca_id = ' || clnCoaId;
-- buggy Prabhakaran 3/31/06
-- execute immediate 'delete CEH_CLNCOA where ceh_ca_name = ' || clnCAName;
execute immediate 'delete CEH_CLNCOA where ceh_ca_name = ''' || clnCAName || '''';
execute immediate 'delete CEL_CLNCOA where cel_container_id =' ||  clnCoaId;
execute immediate 'delete WEE_CLNCOA where coa_id =' || clnCoaId;
  
COMMIT; 

END; 
/


CREATE OR REPLACE PROCEDURE CLEAN_AND_BACKUP_DATABASE_ROWS(clnCoaId INTEGER)
IS
-- The Views are assumed to exist and contain data for the desired collaboration area.
	clnSrcCtgId number(9);
	clnCoaCtgId number(9);
BEGIN
  clnSrcCtgId := GET_SRC_CTG_ID_FROM_CA_ID(clnCoaId);
  clnCoaCtgId := GET_CA_CATALOG_ID_FROM_CA_ID(clnCoaId);

  DBMS_OUTPUT.enable(1000000);

-- Remove pre-existing backup rows for this collab area, if any
DELETE_CA_FROM_BACKUP_TABLES(clnCoaId);


-- Now clean and backup

  CLEAN_ITEMS_OF_PK_VIEW('TOTAL_BAD_PRIMARY_KEY', clnCoaId, clnSrcCtgId, clnCoaCtgId);
  CLEAN_CA_ITEMS_OF_IID_VIEW('TOTAL_BAD_CA_ITEM_ID', clnCoaId, clnCoaCtgId);    -- note:  COLLAB AREA CATALOG ID ONLY
  
  
  -- 3/31/2006 - seems now redundant, produces duplicate rows in itmrsv_clncoa backup table
  -- CLEAN_SRC_ITEMS_OF_IID_VIEW('TOTAL_BAD_SRC_ITEM_ID', clnCoaId, clnSrcCtgId); -- note:  SOURCE CATALOG ID ONLY


--  Old way
--CLEAN_ITEMS_OF_PK_VIEW('TOTAL_BAD_PRIMARY_KEY', clnCoaId, clnSrcCtgId, clnCoaCtgId);

--CLEAN_CA_ITEMS_OF_IID_VIEW('ADDITIONAL_BAD_CA_ITEM_ID', clnCoaId, clnCoaCtgId);    -- note:  COLLAB AREA CATALOG ID ONLY

---- temporarily use just CEM_SRC_ORPHAN_ITEM_ID in place of ADDITIONAL_BAD_SRC_ITEM_ID (see create_views.sql)
---- CLEAN_SRC_ITEMS_OF_IID_VIEW('ADDITIONAL_BAD_SRC_ITEM_ID', clnCoaId, clnSrcCtgId); -- note:  SOURCE CATALOG ID ONLY
--CLEAN_SRC_ITEMS_OF_IID_VIEW('CEM_SRC_ORPHAN_ITEM_ID', clnCoaId, clnSrcCtgId); -- note:  SOURCE CATALOG ID ONLY


  DBMS_OUTPUT.Put_Line(' ');
  DBMS_OUTPUT.Put_Line('*********** DONE WITH CLEAN ************************');

  COMMIT; 
END; 
/

CREATE OR REPLACE PROCEDURE DELETE_SRC_CTG_FROM_CET_TABLE(srcCtgId INTEGER)
IS
BEGIN

  DBMS_OUTPUT.enable(1000000);

execute immediate 'delete CET_BADBLOB where cet_src_container_id =' || srcCtgId;
  
COMMIT; 

END DELETE_SRC_CTG_FROM_CET_TABLE;
/

CREATE OR REPLACE PROCEDURE REPORT_CET_BADBLOB(srcCtgId INTEGER)
IS
-- XXX produce console-suitable output report of CET table for this src ctg
	TYPE MyCurTyp IS REF CURSOR;
	my_cv MyCurTyp;
	TYPE view_rec_type IS RECORD(itm_primary_key VARCHAR2(300)); -- dependent on ITM ddl
	view_rec view_rec_type;
	sql_stmt VARCHAR2(200);
	-- src_item_id number(9);
	rows_fetched NUMBER;
   	TYPE primary_key_tab_type is table of VARCHAR2(300) index by binary_integer;
	primary_key_tab primary_key_tab_type;
	pk VARCHAR2(300);
BEGIN
	DBMS_OUTPUT.PUT_LINE(' ');
	DBMS_OUTPUT.PUT_LINE('*************************************************');
	DBMS_OUTPUT.PUT_LINE('STARTING REPORT OF ITEMS WITH BAD SERIALIZED FORMS FOR CATALOG ID('||srcCtgId||') ...');
	DBMS_OUTPUT.PUT_LINE(' ');
	sql_stmt := 'SELECT cet_primary_key FROM CET_BADBLOB WHERE CET_SRC_CONTAINER_ID =' || srcCtgID || ' and CET_STATUS = ''CORRUPT''';

	-- Report total count	
	OPEN my_cv FOR sql_stmt;
	FETCH my_cv BULK COLLECT INTO primary_key_tab;
	rows_fetched := my_cv%ROWCOUNT;
	DBMS_OUTPUT.PUT_LINE('Total number of bad items found = ' || rows_fetched);
	CLOSE my_cv;
	
	-- do all items individually
	OPEN my_cv FOR sql_stmt;
	LOOP
		FETCH my_cv INTO view_rec;
		EXIT WHEN my_cv%NOTFOUND;
		pk := view_rec.itm_primary_key;
		-- DBMS_OUTPUT.PUT_LINE('next bad item:  primary key= ' || pk ||', id = ' || src_item_id);
		DBMS_OUTPUT.PUT_LINE('Next bad item:  primary key= ' || pk );
	END LOOP;
	CLOSE my_cv;
	DBMS_OUTPUT.PUT_LINE(' ');
	DBMS_OUTPUT.PUT_LINE('*************************************************');
	DBMS_OUTPUT.PUT_LINE('FINISHED REPORT OF ITEMS WITH BAD SERIALIZED FORMS FOR CATALOG ID('||srcCtgId||') ...');
	DBMS_OUTPUT.PUT_LINE(' ');
EXCEPTION
	WHEN OTHERS THEN
		DBMS_OUTPUT.PUT_LINE('Error in proc REPORT_CET_BADBLOB('|| srcCtgId || ')');
END;
/

CREATE OR REPLACE PROCEDURE PURGE_SRC_ITEM(srcCtgItm INTEGER, primary_key VARCHAR2, src_item_id NUMBER)
IS
-- CLEAN an item known in a collaboration area (i.e. not a source catalog item)
--
-- WARNING: be careful not to pass in the id of an item in a source catalog; it will be deleted !!!!!!!
--
BEGIN
	DBMS_OUTPUT.PUT_LINE(' ');
	DBMS_OUTPUT.PUT_LINE('STARTING PURGE_SRC_ITEM('||srcCtgItm||', '||primary_key||', '||src_item_id||') ...');

        FULL_BACKUP_SRC_ITEM(srcCtgItm, primary_key, src_item_id);

	-- DO CA item
	IF (src_item_id > 0) THEN
		DBMS_OUTPUT.PUT_LINE('     CLEANING CA ITEM ID='||src_item_id);
		delete from itm where itm_next_version_id=999999999 and itm_id = src_item_id;
		delete from ita where ita_next_version_id=999999999 and ita_item_id = src_item_id;
		delete from itd where itd_next_version_id=999999999 and itd_item_id = src_item_id;
		delete from icm where icm_next_version_id=999999999 and icm_item_id = src_item_id;
	END IF;

	DBMS_OUTPUT.PUT_LINE('FINISHED PURGE_SRC_ITEM('||srcCtgItm||', '||primary_key||', '||src_item_id||')');

EXCEPTION
	WHEN OTHERS THEN
		DBMS_OUTPUT.PUT_LINE('Error in proc PURGE_SRC_ITEM('||srcCtgItm||', '||primary_key||', '||src_item_id||')');
END;
/
CREATE OR REPLACE PROCEDURE FULL_BACKUP_SRC_ITEM(srcCtgItm INTEGER, primary_key VARCHAR2, src_item_id NUMBER)
IS
-- Full backup (all db tables) of all source catalog information for an item in a source catalog
-- 
-- primary_key may be NULL, but src_item_id should not be.
-- Note: pk currently not used, but could be in future.
--
BEGIN
	--DBMS_OUTPUT.PUT_LINE(' ');
	DBMS_OUTPUT.PUT_LINE('   STARTING FULL_BACKUP_SRC_ITEM('||srcCtgItm||', '||primary_key||', '||src_item_id||') ...');

	-- DO  item
	IF (src_item_id > 0) THEN
		DBMS_OUTPUT.PUT_LINE('     FULL BACKUP SRC ITEM ID='||src_item_id);
    execute immediate 'insert into ITMRSV_CLNCOA (select * from itm where itm_id = ' || src_item_id || ' and itm_next_version_id=999999999)' ;
    execute immediate 'insert into ITA_CLNCOA (select * from ita where ita_item_id =' || src_item_id || ' and ita_next_version_id=999999999)' ;
    execute immediate 'insert into ITD_CLNCOA (select * from itd where itd_item_id = ' || src_item_id || ' and itd_next_version_id=999999999)' ;
    execute immediate 'insert into ICM_CLNCOA (select * from icm where icm_item_id =' || src_item_id || ' and icm_next_version_id=999999999)' ;

	END IF;

	DBMS_OUTPUT.PUT_LINE('   FINISHED FULL_BACKUP_SRC_ITEM('||srcCtgItm||', '||primary_key||', '||src_item_id||')');

EXCEPTION
	WHEN OTHERS THEN
		DBMS_OUTPUT.PUT_LINE('Error in proc FULL_BACKUP_SRC_ITEM('||srcCtgItm||', '||primary_key||', '||src_item_id||')');
END;
/

CREATE OR REPLACE PROCEDURE PURGE_SRC_ITEMS_FROM_CET(srcCtgId INTEGER)
IS
--
-- WARNING: BE SURE View_Name is an ITEM_ID_VIEW consisting of CA, not source, Items !!!!!
--		Else you risk deleting source catalog items !!!!!
--
	TYPE MyCurTyp IS REF CURSOR;
	my_cv MyCurTyp;
	TYPE view_rec_type IS RECORD(itm_id NUMBER(9)); -- dependent on ITM ddl
	view_rec view_rec_type;
	sql_stmt VARCHAR2(200);
	src_item_id NUMBER(9);
	pk VARCHAR2(300);
BEGIN
	DBMS_OUTPUT.PUT_LINE(' ');
	DBMS_OUTPUT.PUT_LINE('*************************************************');
	DBMS_OUTPUT.PUT_LINE('STARTING PURGE_SRC_ITEMS_FROM_CET('||srcCtgId||') ...');
	DBMS_OUTPUT.PUT_LINE(' ');
	sql_stmt := 'SELECT cet_src_entry_id FROM CET_BADBLOB where cet_src_container_id =' || srcCtgId;

	-- do all item ids
	OPEN my_cv FOR sql_stmt;
	LOOP
		FETCH my_cv INTO view_rec;
		EXIT WHEN my_cv%NOTFOUND;
		src_item_id := view_rec.itm_id;
		pk := GET_ITEM_PRIMARY_KEY(srcCtgId, src_item_id);
		PURGE_SRC_ITEM(srcCtgId, pk, src_item_id);
	END LOOP;
	CLOSE my_cv;
	DBMS_OUTPUT.PUT_LINE(' ');
	DBMS_OUTPUT.PUT_LINE('*************************************************');
	DBMS_OUTPUT.PUT_LINE('FINISHED PURGE_SRC_ITEMS_FROM_CET('||srcCtgId||')');
	DBMS_OUTPUT.PUT_LINE(' ');
EXCEPTION
	WHEN OTHERS THEN
		DBMS_OUTPUT.PUT_LINE('Error in proc PURGE_SRC_ITEMS_FROM_CET('||srcCtgId||')');
END;
/
