Domanda

Vorrei uno script per eliminare tutte le tabelle il cui nome inizia con una determinata stringa.Sono sicuro che questo può essere fatto con alcuni SQL dinamici e il INFORMATION_SCHEMA tavoli.

Se qualcuno ha uno script, o riesce a crearne uno velocemente, lo pubblichi.

Se nessuno pubblica una risposta prima che io la capisca da solo, pubblicherò la mia soluzione.

È stato utile?

Soluzione

Potrebbe essere necessario modificare la query per includere il proprietario se ce n'è più di uno 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 di generazione di script ed esecuzione.Ma un vantaggio della generazione dello script è che ti dà la possibilità di rivedere l'intero ciò che verrà eseguito prima che venga effettivamente eseguito.

So che se dovessi farlo su un database di produzione, starei il più attento possibile.

Modificare Esempio di codice corretto.

Altri suggerimenti

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 dell'eliminazione:

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

Ciò ti consentirà di ottenere le tabelle in ordine di chiave esterna ed eviterà di eliminare alcune delle tabelle create da SQL Server.IL t.Ordinal Il valore 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

Su Oracle XE funziona:

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

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

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

Che genererà un sacco di DROP TABLE cascade constraints PURGE dichiarazioni...

Per VIEWS Usa questo:

SELECT 'DROP VIEW "' || VIEW_NAME || '";'
FROM USER_VIEWS
WHERE VIEW_NAME LIKE 'YOURVIEWPREFIX%'
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.

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

Ho visto questo post mentre cercavo l'istruzione mysql per eliminare tutte le tabelle 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à l'insieme di query di rilascio per tutte le tabelle che iniziano con wp_

Ecco la mia soluzione:

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

E ovviamente devi sostituirlo TABLE_PREFIX_GOES_HERE con il tuo prefisso

Xenph YanLa risposta di è stata molto più pulita della mia, ma ecco la mia lo stesso.

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

Cambia e basta tableName ai caratteri con cui vuoi effettuare la ricerca.

Grazie Curt, è lo stesso tipo di soluzione che avevo a metà strada.

Il tuo però è più carino del mio: si presta a facili modifiche.Ho aggiunto un'unione alla selezione e ho cancellato anche alcune visualizzazioni ;)

declare @cmd varchar(4000)
declare cmds cursor for 
Select 'drop table [' + Table_Name + ']'
From    INFORMATION_SCHEMA.TABLES
Where   Table_Name like 'prefix%'
union
Select 'drop view [' + Table_Name + ']'
From    INFORMATION_SCHEMA.VIEWS
Where   Table_Name like 'prefix%'
open cmds
while 1=1
begin
    fetch cmds into @cmd
    if @@fetch_status != 0 break
    exec(@cmd)
end
close local
deallocate local

Non preoccuparti, non è un database di produzione: serve solo per pulire facilmente il mio database di sviluppo mentre provo le cose.

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

-- Test è il nome della tabella

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

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

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

In caso di tabelle temporanee, potresti provare

SELECT 'DROP TABLE "' + t.name + '"' 
FROM tempdb.sys.tables t
WHERE t.name LIKE '[prefix]%'
Autorizzato sotto: CC-BY-SA insieme a attribuzione
Non affiliato a StackOverflow
scroll top