Elimina tutte le tabelle i cui nomi iniziano con una determinata stringa


150

Come posso eliminare tutte le tabelle i cui nomi iniziano con una determinata stringa?

Penso che questo possa essere fatto con alcuni SQL dinamici e le INFORMATION_SCHEMAtabelle.

Risposte:


151

Potrebbe essere necessario modificare la query per includere il proprietario se ce ne sono più di una nel database.

DECLARE @cmd varchar(4000)
DECLARE cmds CURSOR FOR
SELECT 'drop table [' + Table_Name + ']'
FROM INFORMATION_SCHEMA.TABLES
WHERE Table_Name LIKE 'prefix%'

OPEN cmds
WHILE 1 = 1
BEGIN
    FETCH cmds INTO @cmd
    IF @@fetch_status != 0 BREAK
    EXEC(@cmd)
END
CLOSE cmds;
DEALLOCATE cmds

Questo è più pulito rispetto all'utilizzo di un approccio in due passaggi per generare script più esecuzione. Ma un vantaggio della generazione di script è che ti dà la possibilità di rivedere l'intero contenuto che verrà eseguito prima che venga effettivamente eseguito.

So che se avessi intenzione di farlo su un database di produzione, sarei stato il più attento possibile.

Esempio di modifica del codice risolto.


5
Potrebbe essere necessario eseguire questo script più volte a causa dei vincoli di chiave esterna tra le tabelle principale e di dettaglio.
Alexander Prokofyev il

7
In SQL Server 2005 ho dovuto modificare le ultime due righe in close cmds; deallocate cmds.
Hamish Grubijan,

Attenzione : questa soluzione può anche eliminare le tabelle create da SQL Server! La mia soluzione di seguito evita questo ed elimina le tabelle nell'ordine di dipendenza dalla chiave esterna.
Tony O'Hagan,

Questo non ha funzionato per me. La risposta a questa domanda ha funzionato: stackoverflow.com/questions/5116296/...
Ayushmati

115
SELECT 'DROP TABLE "' + TABLE_NAME + '"' 
FROM INFORMATION_SCHEMA.TABLES 
WHERE TABLE_NAME LIKE '[prefix]%'

Questo genererà uno script.

Aggiunta di una clausola per verificare l'esistenza della tabella prima di eliminare:

SELECT 'IF OBJECT_ID(''' +TABLE_NAME + ''') IS NOT NULL BEGIN DROP TABLE [' + TABLE_NAME + '] END;' 
FROM INFORMATION_SCHEMA.TABLES 
WHERE TABLE_NAME LIKE '[prefix]%'

10
Potrei aggiungere per rimuovere le parentesi quando si sostituisce "prefisso" con il prefisso di destinazione.
Levitikon,

10
MYSQL: SELECT concat ('DROP TABLE', TABLE_NAME, ";") come dati DA INFORMATION_SCHEMA.TABLES DOVE TABLE_NAME LIKE '[prefisso]%' --- per coloro che come me hanno trovato questa discussione
Andre

1
Il risultato contiene anche visualizzazioni
Ondra

1
Non dimenticare di scappare _ se fa parte del tuo prefisso, ad es. WHERE TABLE_NAME LIKE 'em\_%' ESCAPE '\';
EM0

3
Questo genera uno script, ma come si esegue lo script?
daOnlyBG

16

Questo ti porterà le tabelle in ordine di chiave esterna ed evita di eliminare alcune delle tabelle create da SQL Server. Il t.Ordinalvalore suddividerà le tabelle in livelli di dipendenza.

WITH TablesCTE(SchemaName, TableName, TableID, Ordinal) AS
(
    SELECT OBJECT_SCHEMA_NAME(so.object_id) AS SchemaName,
        OBJECT_NAME(so.object_id) AS TableName,
        so.object_id AS TableID,
        0 AS Ordinal
    FROM sys.objects AS so
    WHERE so.type = 'U'
        AND so.is_ms_Shipped = 0
        AND OBJECT_NAME(so.object_id)
        LIKE 'MyPrefix%'

    UNION ALL
    SELECT OBJECT_SCHEMA_NAME(so.object_id) AS SchemaName,
        OBJECT_NAME(so.object_id) AS TableName,
        so.object_id AS TableID,
        tt.Ordinal + 1 AS Ordinal
    FROM sys.objects AS so
        INNER JOIN sys.foreign_keys AS f
            ON f.parent_object_id = so.object_id
                AND f.parent_object_id != f.referenced_object_id
        INNER JOIN TablesCTE AS tt
            ON f.referenced_object_id = tt.TableID
    WHERE so.type = 'U'
        AND so.is_ms_Shipped = 0
        AND OBJECT_NAME(so.object_id)
        LIKE 'MyPrefix%'
)
SELECT DISTINCT t.Ordinal, t.SchemaName, t.TableName, t.TableID
FROM TablesCTE AS t
    INNER JOIN
    (
        SELECT
            itt.SchemaName AS SchemaName,
            itt.TableName AS TableName,
            itt.TableID AS TableID,
            Max(itt.Ordinal) AS Ordinal
        FROM TablesCTE AS itt
        GROUP BY itt.SchemaName, itt.TableName, itt.TableID
    ) AS tt
        ON t.TableID = tt.TableID
            AND t.Ordinal = tt.Ordinal
ORDER BY t.Ordinal DESC, t.TableName ASC


3
Correzione rapida: TableName appare alcune volte nelle clausole WHERE e deve essere sostituito con OBJECT_NAME (so.object_id). Bel copione!
witttness

6

Su Oracle XE funziona:

SELECT 'DROP TABLE "' || TABLE_NAME || '";'
FROM USER_TABLES
WHERE TABLE_NAME LIKE 'YOURTABLEPREFIX%'

Oppure, se vuoi rimuovere i vincoli e liberare spazio , usa questo:

SELECT 'DROP TABLE "' || TABLE_NAME || '" cascade constraints PURGE;'
FROM USER_TABLES
WHERE TABLE_NAME LIKE 'YOURTABLEPREFIX%'

Che genererà un mucchio di DROP TABLE cascade constraints PURGEdichiarazioni ...

Per VIEWSusare questo:

SELECT 'DROP VIEW "' || VIEW_NAME || '";'
FROM USER_VIEWS
WHERE VIEW_NAME LIKE 'YOURVIEWPREFIX%'

Ha funzionato perfettamente. Aveva 61.037 tabelle vuote da eliminare da un db utilizzato per il QA. Ho usato l'esempio dei vincoli in cascata. Generato l'output, quindi copiato tutto in uno script ed eseguito. Ha preso per sempre ma ha funzionato come un fascino! Grazie!
Tehbeardedone,

5

Ho visto questo post mentre cercavo un'istruzione mysql per eliminare tutte le tabelle di WordPress basate su @Xenph Yan, ecco cosa ho fatto alla fine:

SELECT CONCAT(  'DROP TABLE `', TABLE_NAME,  '`;' ) AS query
FROM INFORMATION_SCHEMA.TABLES
WHERE TABLE_NAME LIKE  'wp_%'

questo ti darà il set di query di rilascio per tutte le tabelle che iniziano con wp_


5

Ecco la mia soluzione:

SELECT CONCAT('DROP TABLE `', TABLE_NAME,'`;') 
FROM INFORMATION_SCHEMA.TABLES 
WHERE TABLE_NAME LIKE 'TABLE_PREFIX_GOES_HERE%';

E ovviamente è necessario sostituire TABLE_PREFIX_GOES_HEREcon il prefisso.


5
EXEC sp_MSforeachtable 'if PARSENAME("?",1) like ''%CertainString%'' DROP TABLE ?'

Modificare:

sp_MSforeachtable non è documentato, quindi non è adatto alla produzione perché il suo comportamento può variare a seconda della versione di MS_SQL.


One-liner fantastico! Questo dovrebbe essere votato al vertice.
user3413723

4
CREATE PROCEDURE usp_GenerateDROP
    @Pattern AS varchar(255)
    ,@PrintQuery AS bit
    ,@ExecQuery AS bit
AS
BEGIN
    DECLARE @sql AS varchar(max)

    SELECT @sql = COALESCE(@sql, '') + 'DROP TABLE [' + TABLE_NAME + ']' + CHAR(13) + CHAR(10)
    FROM INFORMATION_SCHEMA.TABLES
    WHERE TABLE_NAME LIKE @Pattern

    IF @PrintQuery = 1 PRINT @sql
    IF @ExecQuery = 1 EXEC (@sql)
END

2

La risposta di Xenph Yan è stata molto più chiara della mia, ma qui è la mia comunque.

DECLARE @startStr AS Varchar (20)
SET @startStr = 'tableName'

DECLARE @startStrLen AS int
SELECT @startStrLen = LEN(@startStr)

SELECT 'DROP TABLE ' + name FROM sysobjects
WHERE type = 'U' AND LEFT(name, @startStrLen) = @startStr

Passa tableNameai caratteri con cui vuoi cercare.


1

Questo ha funzionato per me.

DECLARE @sql NVARCHAR(MAX) = N'';

SELECT @sql += '
DROP TABLE ' 
    + QUOTENAME(s.name)
    + '.' + QUOTENAME(t.name) + ';'
    FROM sys.tables AS t
    INNER JOIN sys.schemas AS s
    ON t.[schema_id] = s.[schema_id] 
    WHERE t.name LIKE 'something%';

PRINT @sql;
-- EXEC sp_executesql @sql;

0
select 'DROP TABLE ' + name from sysobjects
where type = 'U' and sysobjects.name like '%test%'

- Test è il nome della tabella


questo in realtà non esegue nulla, restituisce solo un mucchio di comandi.
Stealth Rabbi

0
SELECT 'if object_id(''' + TABLE_NAME + ''') is not null begin drop table "' + TABLE_NAME + '" end;' 
FROM INFORMATION_SCHEMA.TABLES 
WHERE TABLE_NAME LIKE '[prefix]%'

0

Ho dovuto fare una leggera derivazione sulla risposta di Xenph Yan che sospetto perché avevo tabelle non nello schema predefinito.

SELECT 'DROP TABLE Databasename.schema.' + TABLE_NAME 
FROM INFORMATION_SCHEMA.TABLES 
WHERE TABLE_NAME LIKE 'strmatch%'

0

In caso di tabelle temporanee, potresti provare

SELECT 'DROP TABLE "' + t.name + '"' 
FROM tempdb.sys.tables t
WHERE t.name LIKE '[prefix]%'
Utilizzando il nostro sito, riconosci di aver letto e compreso le nostre Informativa sui cookie e Informativa sulla privacy.
Licensed under cc by-sa 3.0 with attribution required.