Adicione uma coluna a uma tabela, se ela ainda não existir


188

Quero escrever uma consulta para o MS SQL Server que adicione uma coluna em uma tabela. Mas não quero exibir nenhum erro quando executo / executo a seguinte consulta.

Estou usando esse tipo de consulta para adicionar uma tabela ...

IF EXISTS (
       SELECT *
       FROM   sys.objects
       WHERE  OBJECT_ID = OBJECT_ID(N'[dbo].[Person]')
              AND TYPE IN (N'U')
   )

Mas não sei como escrever esta consulta para uma coluna.



Você deve usar sys.tablesem vez do "genérico" sys.objects- então você não tem que especificar o tipo explicitamente (é óbvio a partir do sys.tablesjá ....)
marc_s

COL_LENGTH A alternativa funciona apenas no SQL-Server 2008, mas funciona.
Paul-Henri

Respostas:


219

Você pode usar uma construção semelhante usando a sys.columnstabela io sys.objects.

IF NOT EXISTS (
  SELECT * 
  FROM   sys.columns 
  WHERE  object_id = OBJECT_ID(N'[dbo].[Person]') 
         AND name = 'ColumnName'
)

42
Observe que, neste caso, você deseja usar SE NÃO EXISTE no seu código real.
Nac

2
Para otimizado consulta que você pode usar top 1 com select
Banketeshvar Narayan

11
@BanketeshvarNarayan isso está incorreto. Os planos de execução para subconsultas em uma EXISTScláusula são idênticos. Coisas como SELECT 1ou SELECT TOP 1são desnecessárias. A EXISTSprópria cláusula informa ao otimizador de consulta para executar apenas as leituras mínimas necessárias para avaliar o EXISTS... pelo menos no SQL Server. Outros mecanismos de banco de dados podem ter um otimizador de consulta mais ou menos eficiente.
21915 Kenneth Cochran

9
@BanketeshvarNarayan Se você está otimizando suas ADD Columnconsultas ... deve executá-las com muita frequência!
Fenton

1
@ user391339 - Publiquei uma construção semelhante à do OP, mas sim, se você quiser executar uma ação se a coluna não existir, a instrução será SE NÃO EXISTIR. Eu realmente não sinto a necessidade de editar a resposta para isso, mas sinta-se à vontade para editar a si mesmo se você acha que isso é uma melhoria.
Lieven Keersmaekers

91
IF COL_LENGTH('table_name', 'column_name') IS NULL
BEGIN
    ALTER TABLE table_name
    ADD [column_name] INT
END

1
Eu tentei fazer isso, mas ele retorna um erro que afirma que a função COL_LENGTH não existe.
ThEpRoGrAmMiNgNoOb

3
Requer SQL Server 2008
Robert Brown

6
Pequena adição - não se deve usar colchetes no nome da coluna, pois COL_LENGTH('table_name', '[column_name]')sempre retorna nulo no SQL Server 2016 ( COL_LENGTH('[table_name]', 'column_name') works as expected).
stop-cran

33

Outra alternativa. Eu prefiro essa abordagem porque é menos escrita, mas as duas realizam a mesma coisa.

IF COLUMNPROPERTY(OBJECT_ID('dbo.Person'), 'ColumnName', 'ColumnId') IS NULL
BEGIN
    ALTER TABLE Person 
    ADD ColumnName VARCHAR(MAX) NOT NULL
END

Notei também que o seu está procurando onde existe uma tabela que obviamente é exatamente essa

 if COLUMNPROPERTY( OBJECT_ID('dbo.Person'),'ColumnName','ColumnId') is not null

2
Eu gosto disso. Acho que a melhor parte de postar aqui é encontrar joias como essa.
precisa saber é o seguinte

2
O que é 'ColumnId'?
Marius Stănescu

'ColumnId' é o nome da propriedade da coluna na qual você está verificando. Você provavelmente poderia ter usado qualquer nome de propriedade que exista em uma coluna, como nome etc.
Jacques Bosch

5

Aqui está outra variação que funcionou para mim.

IF NOT EXISTS (SELECT 1
        FROM INFORMATION_SCHEMA.COLUMNS
        WHERE upper(TABLE_NAME) = 'TABLENAME'
        AND upper(COLUMN_NAME) = 'COLUMNNAME')
BEGIN
    ALTER TABLE [dbo].[Person] ADD Column
END
GO

EDIT: observe que as INFORMATION_SCHEMAvisualizações nem sempre podem ser atualizadas, use SYS.COLUMNS:

IF NOT EXISTS (SELECT 1 FROM SYS.COLUMNS....



0

Ao procurar uma coluna em outro banco de dados, você pode simplesmente incluir o nome do banco de dados:

IF NOT EXISTS (
  SELECT * 
  FROM   DatabaseName.sys.columns 
  WHERE  object_id = OBJECT_ID(N'[DatabaseName].[dbo].[TableName]') 
         AND name = 'ColumnName'
)

-1
IF NOT EXISTS (SELECT 1  FROM SYS.COLUMNS WHERE  
OBJECT_ID = OBJECT_ID(N'[dbo].[Person]') AND name = 'DateOfBirth')
BEGIN
ALTER TABLE [dbo].[Person] ADD DateOfBirth DATETIME
END
Ao utilizar nosso site, você reconhece que leu e compreendeu nossa Política de Cookies e nossa Política de Privacidade.
Licensed under cc by-sa 3.0 with attribution required.