Verifique se a tabela existe no SQL Server
-
03-07-2019 - |
Pergunta
Gostaria que esta seja a última discussão sobre como verificar se existe uma tabela no SQL Server 2000/2005 utilizando instruções SQL.
Quando você Google para a resposta, você tem tantas respostas diferentes. Existe uma forma oficial / para trás e para a frente compatível de fazê-lo?
Aqui estão duas maneiras possíveis de fazê-lo. Qual deles entre os dois é a melhor maneira standard / de fazê-lo?
Primeira maneira:
IF EXISTS (SELECT 1
FROM INFORMATION_SCHEMA.TABLES
WHERE TABLE_TYPE='BASE TABLE'
AND TABLE_NAME='mytablename')
SELECT 1 AS res ELSE SELECT 0 AS res;
A segunda maneira:
IF OBJECT_ID (N'mytablename', N'U') IS NOT NULL
SELECT 1 AS res ELSE SELECT 0 AS res;
MySQL fornece a simples
SHOW TABLES LIKE '%tablename%';
comunicado. Eu estou procurando algo semelhante.
Solução
Para consultas como este é sempre melhor usar uma visão INFORMATION_SCHEMA
. Estes pontos de vista são (principalmente) padrão em muitos bancos de dados diferentes e raramente mudança de versão para versão.
Para verificar se existe uma tabela uso:
IF (EXISTS (SELECT *
FROM INFORMATION_SCHEMA.TABLES
WHERE TABLE_SCHEMA = 'TheSchema'
AND TABLE_NAME = 'TheTable'))
BEGIN
--Do Stuff
END
Outras dicas
Observe também que, se por qualquer razão que você precisa para verificar se há uma tabela temporária que você pode fazer isso:
if OBJECT_ID('tempdb..#test') is not null
--- temp table exists
Nós sempre usar o estilo OBJECT_ID
por tanto tempo quanto eu me lembro
IF OBJECT_ID('*objectName*', 'U') IS NOT NULL
Por favor, veja a seguir abordagens,
Abordagem 1: Usando INFORMATION_SCHEMA.TABLES ver
Podemos escrever uma consulta como abaixo para verificar se um clientes tabela existe no banco de dados atual.
IF EXISTS (SELECT * FROM INFORMATION_SCHEMA.TABLES WHERE TABLE_NAME = N'Customers')
BEGIN
PRINT 'Table Exists'
END
Podemos usar a função OBJECT_ID () como a seguir para verificar se um clientes tabela existe no banco de dados atual.
IF OBJECT_ID(N'dbo.Customers', N'U') IS NOT NULL
BEGIN
PRINT 'Table Exists'
END
Abordagem 3: Usando sys.objects Catálogo Ver
Podemos usar a exibição do catálogo sys.objects para verificar a existência da tabela, como mostrado abaixo:
IF EXISTS(SELECT 1 FROM sys.Objects WHERE Object_id = OBJECT_ID(N'dbo.Customers') AND Type = N'U')
BEGIN
PRINT 'Table Exists'
END
Abordagem 4: Usando sys.tables Catálogo Ver
Podemos usar a exibição do catálogo sys.tables para verificar a existência da tabela, como mostrado abaixo:
IF EXISTS(SELECT 1 FROM sys.Tables WHERE Name = N'Customers' AND Type = N'U')
BEGIN
PRINT 'Table Exists'
END
Abordagem 5: Tabela Sistema de evitar o uso de sys.sysobjects
Devemos evitar o uso sys.sysobjects tabela do sistema diretamente, acesso direto a ele será obsoleto em algumas versões futuras do SQL Server. Como por ligação Microsoft BOL, a Microsoft está sugerindo usar as exibições do catálogo sys.objects / sys.tables em vez de tabela do sistema sys.sysobjects diretamente.
IF EXISTS(SELECT name FROM sys.sysobjects WHERE Name = N'Customers' AND xtype = N'U')
BEGIN
PRINT 'Table Exists'
END
encaminhados de: http://sqlhints.com/2014/04/13/how-to-check-if-a-table-exists-in-sql-server/
À procura de uma tabela em um banco de dados diferente:
if exists (select * from MyOtherDatabase.sys.tables where name = 'MyTable')
print 'Exists'
Apenas quis mencionar uma situação onde provavelmente seria um pouco mais fácil de usar o método OBJECT_ID
. Os pontos de vista INFORMATION_SCHEMA
são objetos sob cada banco de dados -
Os pontos de vista do esquema de informações são definidos em um esquema especial chamado INFORMATION_SCHEMA. Este esquema é contido em cada banco de dados.
https://msdn.microsoft.com/en-us/library/ ms186778.aspx
Portanto, todas as tabelas que você acessar utilizando
IF EXISTS (SELECT 1
FROM [database].INFORMATION_SCHEMA.TABLES
WHERE TABLE_TYPE='BASE TABLE'
AND TABLE_NAME='mytablename')
SELECT 1 AS res ELSE SELECT 0 AS res;
só vai refletir o que está em [database]
. Se você quiser verificar se as tabelas no outro exist banco de dados, sem alterar dinamicamente a [database]
cada vez, OBJECT_ID
vai deixar você fazer isso fora da caixa. Ex -
IF OBJECT_ID (N'db1.schema.table1', N'U') IS NOT NULL
SELECT 1 AS res ELSE SELECT 0 AS res;
funciona tão bem como
IF OBJECT_ID (N'db2.schema.table1', N'U') IS NOT NULL
SELECT 1 AS res ELSE SELECT 0 AS res;
SQL SERVER 2016 Editar :
A partir do 2016, Microsoft simplificou a capacidade de verificar a existência de objetos não-existentes antes de cair, adicionando as palavras-chave if exists
às demonstrações drop
. Por exemplo,
drop table if exists mytablename
irá fazer a mesma coisa que wrappers OBJECT_ID
/ INFORMATION_SCHEMA
, em 1 linha de código.
IF OBJECT_ID('mytablename') IS NOT NULL
Usando o esquema de informações é o caminho SQL padrão para fazê-lo, por isso deve ser usado por todos os bancos de dados que a suportam.
Se você precisa para trabalhar em bancos de dados diferentes:
DECLARE @Catalog VARCHAR(255)
SET @Catalog = 'MyDatabase'
DECLARE @Schema VARCHAR(255)
SET @Schema = 'dbo'
DECLARE @Table VARCHAR(255)
SET @Table = 'MyTable'
IF (EXISTS (SELECT * FROM INFORMATION_SCHEMA.TABLES
WHERE TABLE_CATALOG = @Catalog
AND TABLE_SCHEMA = @Schema
AND TABLE_NAME = @Table))
BEGIN
--do stuff
END
IF EXISTS
(
SELECT *
FROM sys.objects
WHERE object_id = OBJECT_ID(N'[dbo].[Mapping_APCToFANavigator]')
AND
type in (N'U')
)
BEGIN
-- Do whatever you need to here.
END
Aqui no código acima, o nome da tabela é Mapping_APCToFANavigator
.
Eu sei que é uma questão antiga, mas eu descobri essa possibilidade, se você pretende chamá-lo muitas vezes.
create procedure Table_Exists
@tbl varchar(50)
as
return (select count(*) from sysobjects where type = 'U' and name = @tbl)
go
Apenas adicionando aqui, para o benefício dos desenvolvedores e DBAs companheiros
um script que recebe @TableName como parâmetro
(que pode ou não pode conter o schemaname) e retorna as informações abaixo se existe a esquema.tabela:
the_name object_id the_schema the_table the_type
[Facts].[FactBackOrder] 758293761 Facts FactBackOrder Table
Eu produzi esse script para ser usado dentro de outros scripts cada vez que eu preciso para testar se ou não uma tabela ou exibição existe, e quando isso acontecer, obter o seu object_id para ser usado para outros fins.
Ele dispara um erro quando quer que você passou uma cadeia vazia, nome do esquema errado ou nome da tabela errada.
esta pode estar dentro de um procedimento e de retorno, por exemplo, -1.
Como um exemplo, eu tenho uma tabela chamada "Facts.FactBackOrder" em um dos meus bancos de dados Data Warehouse.
Isto é como eu conseguido isso:
PRINT 'THE SERVER IS ' + @@SERVERNAME
--select db_name()
PRINT 'THE DATABASE IS ' + db_NAME()
PRINT ''
GO
SET NOCOUNT ON
GO
--===================================================================================
-- @TableName is the parameter
-- the object we want to deal with (it might be an indexed view or a table)
-- the schema might or might not be specified
-- when not specified it is DBO
--===================================================================================
DECLARE @TableName SYSNAME
SELECT @TableName = 'Facts.FactBackOrder'
--===================================================================================
--===================================================================================
DECLARE @Schema SYSNAME
DECLARE @I INT
DECLARE @Z INT
SELECT @TableName = LTRIM(RTRIM(@TableName))
SELECT @Z = LEN(@TableName)
IF (@Z = 0) BEGIN
RAISERROR('Invalid @Tablename passed.',16,1)
END
SELECT @I = CHARINDEX('.',@TableName )
--SELECT @TableName ,@I
IF @I > 0 BEGIN
--===================================================================================
-- a schema and table name have been passed
-- example Facts.FactBackOrder
-- @Schema = Fact
-- @TableName = FactBackOrder
--===================================================================================
SELECT @Schema = SUBSTRING(@TABLENAME,1,@I-1)
SELECT @TableName = SUBSTRING(@TABLENAME,@I+1,@Z-@I)
END
ELSE BEGIN
--===================================================================================
-- just a table name have been passed
-- so the schema will be dbo
-- example Orders
-- @Schema = dbo
-- @TableName = Orders
--===================================================================================
SELECT @Schema = 'DBO'
END
--===================================================================================
-- Check whether the @SchemaName is valid in the current database
--===================================================================================
IF NOT EXISTS ( SELECT * FROM INFORMATION_SCHEMA.SCHEMATA K WHERE K.[SCHEMA_NAME] = @Schema ) BEGIN
RAISERROR('Invalid Schema Name.',16,1)
END
--SELECT @Schema as [@Schema]
-- ,@TableName as [@TableName]
DECLARE @R1 TABLE (
THE_NAME SYSNAME
,THE_SCHEMA SYSNAME
,THE_TABLE SYSNAME
,OBJECT_ID INT
,THE_TYPE SYSNAME
,PRIMARY KEY CLUSTERED (THE_SCHEMA,THE_NAME)
)
;WITH RADHE_01 AS (
SELECT QUOTENAME(SCHEMA_NAME(O.schema_id)) + '.' + QUOTENAME(O.NAME) AS [the_name]
,the_schema=SCHEMA_NAME(O.schema_id)
,the_table=O.NAME
,object_id =o.object_id
,[the_type]= CASE WHEN O.TYPE = 'U' THEN 'Table' ELSE 'View' END
from sys.objects O
where O.is_ms_shipped = 0
AND O.TYPE IN ('U','V')
)
INSERT INTO @R1 (
THE_NAME
,THE_SCHEMA
,THE_TABLE
,OBJECT_ID
,THE_TYPE
)
SELECT the_name
,the_schema
,the_table
,object_id
,the_type
FROM RADHE_01
WHERE the_schema = @Schema
AND the_table = @TableName
IF (@@ROWCOUNT = 0) BEGIN
RAISERROR('Invalid Table Name.',16,1)
END
ELSE BEGIN
SELECT THE_NAME
,THE_SCHEMA
,THE_TABLE
,OBJECT_ID
,THE_TYPE
FROM @R1
END
Em SQL Server 2000 você pode tentar:
IF EXISTS(SELECT 1 FROM sysobjects WHERE type = 'U' and name = 'MYTABLENAME')
BEGIN
SELECT 1 AS 'res'
END
IF EXISTS
(
SELECT *
FROM INFORMATION_SCHEMA.TABLES
WHERE TABLE_SCHEMA = 'PutSchemaHere'
AND
TABLE_NAME = 'PutTableNameHere'
)
IF OBJECT_ID (N'dbo.T', N'U') IS NOT NULL BEGIN print 'deleted table'; drop table t END else begin print 'table not found' end Create table t (id int identity(1,1) not null, name varchar(30) not null, lastname varchar(25) null) insert into t( name, lastname) values('john','doe'); insert into t( name, lastname) values('rose',NULL); Select * from t 1 john doe 2 rose NULL -- clean drop table t
Algo importante saber para quem não tenha encontrado a sua solução ainda: servidor SQL! = MYSQL . Se você quiser fazê-lo com MYSQL , é bastante simples
$sql = "SELECT 1 FROM `db_name`.`table_name` LIMIT 1;";
$result = mysql_query($sql);
if( $result == false )
echo "table DOES NOT EXIST";
else
echo "table exists";
postando isso aqui porque é o top hit no Google.
select name from SysObjects where xType='U' and name like '%xxx%' order by name
- - criar procedimento para verificar se existe uma tabela
DELIMITER $$
DROP PROCEDURE IF EXISTS `checkIfTableExists`;
CREATE PROCEDURE checkIfTableExists(
IN databaseName CHAR(255),
IN tableName CHAR(255),
OUT boolExistsOrNot CHAR(40)
)
BEGIN
SELECT count(*) INTO boolExistsOrNot FROM information_schema.TABLES
WHERE (TABLE_SCHEMA = databaseName)
AND (TABLE_NAME = tableName);
END $$
DELIMITER ;
- - como usar: verificação se as migrações de mesa existe
CALL checkIfTableExists('muDbName', 'migrations', @output);
IF EXISTS ( SELECT * FROM dbo.sysobjects WHERE id = OBJECT_ID(N'dbo.TableName') AND OBJECTPROPERTY(id, N'IsUserTable') = 1 )
BEGIN
SELECT * FROM dbo.TableName;
END
GO
Se alguém está tentando fazer a mesma coisa em LINQ to SQL (ou especialmente LINQPad) ligar opção para incluir as tabelas do sistema e pontos de vista e fazer este código:
let oSchema = sys.Schemas.FirstOrDefault(s=>s.Name==a.schema )
where oSchema !=null
let o=oSchema!=null?sys.Objects.FirstOrDefault (o => o.Name==a.item && o.Schema_id==oSchema.Schema_id):null
where o!=null
dado que você tem um objeto com o nome de um item de propriedade chamada, e o esquema em uma propriedade chamada esquema onde o nome da variável fonte é a
Se isto é ser a discussão 'final', em seguida, deve-se notar que o roteiro de Larry Leonard pode consultar um servidor remoto, bem como se os servidores estão ligados.
if exists (select * from REMOTE_SERVER.MyOtherDatabase.sys.tables where name = 'MyTable')
print 'Exists'
Eu tive alguns problemas, quer com a seleção de INFORMATIONAL_SCHEME e OBJECT_ID. Eu não sei se é um problema de driver ODBC ou algo .. Consultas de estúdio de gerenciamento do SQL, ambos, estavam bem.
Aqui está a solução:
SELECT COUNT(*) FROM <yourTableNameHere>
Assim, se a consulta falhar, há, provavelmente, nenhuma tabela no banco de dados (ou você não tem permissões de acesso a ele).
A verificação é feita comparando o valor (inteiro no meu caso) devolvido pelo executor SQL que lida com driver ODBC ..
if (sqlexec(conectionHandle, 'SELECT COUNT(*) FROM myTable') == -1) {
// myTable doesn't exist..
}
Executar esta consulta para verificar se a tabela existe no banco de dados:
IF(SELECT TABLE_NAME from INFORMATION_SCHEMA.TABLES where TABLE_NAME = 'YourTableName') IS NOT NULL
PRINT 'Table Exists';
IF EXISTS (
SELECT *
FROM INFORMATION_SCHEMA.TABLES
WHERE
TABLE_CATALOG = 'Database Name' and
TABLE_NAME = 'Table Name' and
TABLE_SCHEMA = 'Schema Name') -- Database and Schema name in where statement can be deleted
BEGIN
--TABLE EXISTS
END
ELSE BEGIN
--TABLE DOES NOT EXISTS
END
considerar em um banco de dados você tem uma tabela t1. que deseja executar script em outro banco de dados como - se t1 existem em seguida, fazer mais nada criar t1. Para fazer isso visual studio aberto e faça o seguinte:
Botão direito do mouse em t1, então a tabela Script como, em seguida, cair e Criar Para, em seguida, New Query Editor
Você vai encontrar a sua consulta desejada. Mas antes de executar esse script não se esqueça de comentar a instrução de queda na consulta que você não quer criar novo, se já existe um.
Graças