Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Oracle : How to have only one row active in a table?

Tags:

oracle

I have an Oracle table with a field Named Active. This field has a unique constraint, so only one row will be marked as Active.

Is there any way in the database layer to keep only one row active when adding a new row or updating old ones ?

Example

Current State of Table

ID        Active
----------------
1         yes

A new active row is added :

New State of the table

ID        Active
----------------
1         No
2         Yes

The row 1 is updated with Active = Yes

ID        Active
----------------
1         Yes
2         No

Of course I can not update the table using a trigger when a new row is beign inserted.

Does anyone have an idea on how to do that please ?

like image 221
Thomas Carlton Avatar asked Oct 20 '22 15:10

Thomas Carlton


1 Answers

You need to call this procedure with valid values as input parameter

CREATE OR REPLACE PROCEDURE t416493.set_tab
    (
     p_id IN tab.id%TYPE
    ,p_active_flag IN tab.active%TYPE
    ,p_dml_type    IN VARCHAR2
    )

    IS 

    CURSOR check_flag_exists
    IS 
    SELECT id 
    FROM tab
    WHERE active = p_active_flag;

    v_id tab.id%TYPE;
    v_active_flag VARCHAR2(3);

    BEGIN

        OPEN check_flag_exists;
          FETCH check_flag_exists INTO v_id;
            IF check_flag_exists%FOUND THEN 

              IF  p_active_flag ='Yes' THEN
                  v_active_flag :='No';
              ELSE
                 v_active_flag :='Yes';
              END IF;

                UPDATE tab
                 SET  active = v_active_flag
                WHERE id =v_id; 

            END IF; 
         CLOSE check_flag_exists;  

         IF p_dml_type ='INSERT' THEN 
          INSERT INTO tab 
           (id
           ,active
           )
           VALUES
           (p_id
           ,p_active_flag
           );
         ELSIF p_dml_type ='UPDATE' THEN
           UPDATE tab
           SET active =p_active_flag
           WHERE id =v_id; 
         END IF;  

    END set_tab;

You need to call your proc like this as shown below:

begin

 set_tab
       (
         p_id =>2
        ,p_active_flag =>'Yes'
        ,p_dml_type   =>'INSERT'
        );

end;
/
like image 66
Gaurav Soni Avatar answered Oct 27 '22 19:10

Gaurav Soni