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

Rileva, elimina colonne vuote e aggiorna il database in sql, oracle

Stai interrogando una vista del dizionario di dati. Mostra metadati , informazioni sul database. Questa vista, ALL_TAB_COLUMNS, mostra le informazioni per ogni colonna di ogni tabella (su cui hai i privilegi). Necessariamente COLUMN_NAME non può essere nullo, quindi la tua query non restituisce righe.

Ora quello che vuoi fare è interrogare ogni tabella e trovare quali colonne non contengono dati. Ciò richiede SQL dinamico. Dovrai interrogare ALL_TAB_COLUMNS, quindi non eri completamente fuori base.

A causa dell'SQL dinamico, questa è una soluzione programmatica, quindi i risultati vengono visualizzati con DBMS_OUTPUT.

set serveroutput on size unlimited 

Ecco un blocco anonimo:l'esecuzione potrebbe richiedere del tempo. Il join a USER_TABLES è necessario perché le colonne delle viste sono incluse in TAB_COLUMNS e non le vogliamo nel set di risultati.

declare
    dsp varchar2(32767);
    stmt varchar2(32767);
begin
    << tab_loop >>
    for trec in ( select t.table_name
                 from user_tables t )
    loop
        stmt := 'select ';
        dbms_output.put_line('table name = '|| trec.table_name);
        << col_loop >>
        for crec in ( select c.column_name
                             , row_number() over (order by c.column_id) as rn
                      from user_tab_columns c
                      where c.table_name = trec.table_name  
                      and c.nullable = 'Y'
                      order by c.column_id )
        loop
            if rn > 1 then stmt := concat(stmt, '||'); end if;
            stmt := stmt||''''||crec.column_name||'=''||'
                        ||'to_char(count('||crec.column_name||')) ';
        end loop col_loop;
        stmt := stmt || ' from '||trec.table_name;
        execute immediate stmt into dsp;
        dbms_output.put_line(dsp);
    end loop tab_loop;
end;

output di esempio:

table name = MY_PROFILER_RUN_EVENTS
TOT_EXECS=0TOT_TIME=0MIN_TIME=0MAX_TIME=0
table name = LOG_TABLE
PKG_NAME=0MODULE_NAME=0CLIENT_ID=0

PL/SQL procedure successfully completed.

SQL> 

Qualsiasi colonna in cui COUNT=0 non contiene valori.

Ora, se vuoi davvero eliminare tali colonne è una questione diversa. Potresti interrompere i programmi che dipendono da loro. Quindi è necessaria prima un'analisi dell'impatto. Questo è il motivo per cui non ho prodotto un programma che elimina automaticamente le colonne vuote. Penso che sarebbe una pratica pericolosa.

È fondamentale che le modifiche alla struttura del nostro database siano prese in considerazione e verificate. Quindi, se dovessi mai intraprendere un esercizio come questo, modificherei l'output del programma sopra in modo da produrre uno script di istruzioni della colonna di trascinamento che potrei rivedere, modificare e tenere sotto il controllo del codice sorgente.