Oracle
 sql >> Database >  >> RDS >> Oracle

Come reimpostare automaticamente il valore di una sequenza su 0 ogni anno in Oracle 10g?

Le sequenze non sono realmente progettate per essere ripristinate. Ma ci sono alcuni casi in cui è auspicabile reimpostare una sequenza, ad esempio quando si impostano i dati di test o si uniscono nuovamente i dati di produzione in un ambiente di test. Questo tipo di attività non normalmente fatto in produzione.

SE questo tipo di operazione deve essere messo in produzione, deve essere testato a fondo. (Ciò che causa la maggior preoccupazione è la possibilità che la procedura di ripristino venga eseguita accidentalmente nel momento sbagliato, ad esempio a metà anno.

Eliminare e ricreare la sequenza è un approccio. Come operazione, è abbastanza semplice per quanto riguarda la SEQUENZA:

    DROP SEQUENCE MY_SEQ;
    CREATE SEQUENCE MY_SEQ START WITH 1 INCREMENT BY 1 MINVALUE 0;

[EDIT] Come sottolinea correttamente Matthew Watson, ogni istruzione DDL (come DROP, CREATE, ALTER) causerà un commit implicito. [/MODIFICA]

Tuttavia, tutti i privilegi concessi su SEQUENCE verranno eliminati, quindi sarà necessario riassegnarli. Tutti gli oggetti che fanno riferimento alla sequenza verranno invalidati. Per ottenere questo più generalizzato, dovresti salvare i privilegi (prima di eliminare la sequenza) e quindi concederli nuovamente.

Un secondo approccio consiste nell'ALTERARE una SEQUENZA esistente, senza eliminarla e ricrearla. È possibile ripristinare la sequenza modificando il valore INCREMENT su un valore negativo (la differenza tra il valore corrente e 0), quindi eseguire esattamente un .NEXTVAL per impostare il valore corrente su 0, quindi riportare INCREMENT su 1. Ho usato lo stesso approccio in precedenza (manualmente, in un ambiente di test), per impostare una sequenza anche su un valore maggiore.

Naturalmente, affinché funzioni correttamente, è necessario assicurarsi nessun'altra sessione fa riferimento alla sequenza durante l'esecuzione di questa operazione. Un .NEXTVAL in più nell'istante sbagliato rovinerà il ripristino. (NOTA:ottenere ciò dal lato del database sarà difficile, se l'applicazione si connette come proprietario della sequenza, piuttosto che come utente separato.)

Per farlo accadere ogni anno, dovresti pianificare un lavoro. Il ripristino della sequenza dovrà essere coordinato con il ripristino della parte AAAA del tuo identificatore.

Ecco un esempio:

http://www.jaredstill.com/content/reset-sequence.html

[MODIFICA]

NON TESTATO segnaposto per una possibile progettazione di un blocco PL/SQL per reimpostare la sequenza

    declare
      pragma autonomous_transaction;
      ln_increment       number;
      ln_curr_val        number;
      ln_reset_increment number;
      ln_reset_val       number;
    begin

      -- save the current INCREMENT value for the sequence
      select increment_by
        into ln_increment
        from user_sequences
       where sequence_name = 'MY_SEQ';

      -- determine the increment value required to reset the sequence
      -- from the next fetched value to 0
      select -1 - MY_SEQ.nextval into ln_reset_increment from dual;

      -- fetch the next value (to make it the current value)
      select MY_SEQ.nextval into ln_curr from dual;

      -- change the increment value of the sequence to 
      EXECUTE IMMEDIATE 'alter sequence MY_SEQ increment by '
        || ln_reset_increment ||' minvalue 0';

      -- advance the sequence to set it to 0
      select MY_SEQ.nextval into ln_reset_val from dual;

      -- set increment back to the previous(ly saved) value
      EXECUTE IMMEDIATE 'alter sequence MY_SEQ increment by '
        || ln_increment ;
    end;
    /

NOTE:

  • come proteggere al meglio la sequenza dall'accesso durante il ripristino, rinominarla?
  • Diversi casi di test su cui lavorare qui.
  • Primo passaggio, verifica casi normativi di sequenza positiva, crescente, incremento 1.
  • Un approccio migliore sarebbe creare una nuova SEQUENZA, aggiungere autorizzazioni, rinominare le sequenze esistenti e nuove e quindi ricompilare le dipendenze?