2009-09-15 3 views
6

Как вы можете запросить SQL Server для даты создания столбца таблицы SQL Server 2005?Найти дату/время, когда был создан столбец таблицы

Я попробовал sp_columns [tablename], чтобы получить эту информацию, но дата создания не была включена в эту хранимую процедуру.

Как это можно сделать?

+0

Вам нужно будет посмотреть SYS.OBJECTS, подключенный к SYS.COLUMNS. SYS.OBJECTS имеет поле create_date: http://technet.microsoft.com/en-us/library/ms190324.aspx –

ответ

5

Существует эта системная таблица с именем sys.Columns, в которой вы можете получить информацию о столбцах. если вы хотите увидеть столбцы определенной таблицы можно сделать следующим образом:

SELECT col.* from sys.objects obj 
inner join sys.columns col 
on obj.object_Id=col.object_Id 
and [email protected] 

Или вы можете получить информацию таблицы вроде этого:

SELECT * FROM sys.objects WHERE [email protected] 

, но я не смог найти какую-либо информацию о создании дата столбца.

Обновлено: This может помочь.

+0

Почему бы не использовать «sys.tables» для информации таблицы? Зачем всегда идти в sys.objects ??? –

+0

Я не знаю! Это старая привычка, я думаю :) – Beatles1692

+2

+1 - дата создания столбца не представляется доступной, а для ссылки предоставлена ​​ – AdaTheDev

0
SELECT obj.create_date 
from sys.objects obj 
inner join sys.columns col on obj.object_Id=col.object_Id 
WHERE col.name = @columnName 
and [email protected] 

здание на предыдущем ответ, но дает только создать дату столбца

+0

да, это выглядит правильно – CRice

+0

Если я ищу информацию о таблице, я обычно предпочитаю использовать sys.tables вместо sys.objects - это более сфокусировано, и вы случайно не выбираете что-то еще, как триггер или такой :-) –

+8

Это дата создания таблицы, а не дата создания столбца. Я считаю, что Beatles1692 верен, в SQL 2005 вам нужно будет использовать триггеры DDL по его ссылке. – AdaTheDev

1

Я думаю, что нет никакого способа получения модификации или даты создания отдельных столбцов таковых. Запросы, указанные в ответах this и this, возвращают даты, связанные с таблицей, содержащей столбец, а не столбец. Поскольку таблица sys.columns имеет одинаковый идентификатор для всех столбцов в таблице. Вы можете проверить это, запустив этот запрос

select col.object_id, col.name, col.column_id 
from sys.columns col 
where col.object_id = 
(select o.object_id from sys.objects o where o.Name = @tableName) 
+1

или: где col.object_id = OBJECT_ID ('table_name') - мне кажется мне легче –

0

Я не думаю, что эта информация доступна, если у вас есть что-то, что может просматривать журналы транзакций, как Log Explorer. Это не вещь tsql.

1

Бит опоздал на вечеринку, но нашел что-то, что помогло мне. Если вы можете сказать, что столбец является последним изменением таблицы, то sys.tables(modify_date) работоспособен.

6

SQL Server не отслеживает конкретные изменения таблиц. Если вам нужен или нужен этот уровень детализации, вам необходимо создать триггер DDL (введенный в SQL Server 2005), который может захватывать определенные события или даже классы событий и записывать эти изменения в созданную таблицу истории.

DDL Триггеры являются «после» триггерами; нет опции «вместо». Однако, если вы хотите запретить действие, вы можете просто выдать ROLLBACK и отменить то, что произошло.

страницы MSDN для DDL Triggers имеет много полезной информацию о том, как ловушке либо конкретные события (т.е. ALTER TABLE) и с помощью функции EVENTDATA, которая возвращает XML, чтобы получить особенности, какие события произвели на спусковой крючок, в том числе точного SQL-запрос, который был выполнен. Фактически, на странице MSDN для Use the EVENTDATA Function даже есть простые примеры создания триггера DDL для записи операторов ALTER TABLE (в разделе « ALTER TABLE и ALTER DATABASE Events») и создания триггера DDL для захвата событий в таблицу журналов (в раздел «Пример»). Поскольку все команды ALTER TABLE будут запускать этот триггер, вам необходимо проанализировать, какие из них относятся к тому, что вы ищете. И, возможно, теперь, когда вы знаете, что это вариант, требуется больше, чем просто добавлять столбцы (например, удаление столбцов, изменение типа данных и/или NULLability и т. Д.).

Следует отметить, что вы можете создать триггер DLL ON ALL SERVER для событий с областью базы данных, таких как ALTER_TABLE.

Если вы хотите увидеть структуру XML для любого события или класса событий, перейдите к:

http://schemas.microsoft.com/sqlserver/2006/11/eventdata/

и нажмите на кнопку «Текущая версия:» ссылку. Если вы хотите увидеть конкретное событие или класс событий, просто выполните поиск (обычно Control-F в браузере) имени события, которое будет использоваться в предложении триггера «FOR» (включая подчеркивание). Ниже приводится схема для ALTER_TABLE события:

<xs:complexType name="EVENT_INSTANCE_ALTER_TABLE"> 
<xs:sequence> 
<!-- Basic Envelope --> 
<xs:element name="EventType" type="SSWNAMEType"/> 
<xs:element name="PostTime" type="xs:string"/> 
<xs:element name="SPID" type="xs:int"/> 
<!-- Server Scoped DDL --> 
<xs:element name="ServerName" type="PathType"/> 
<xs:element name="LoginName" type="SSWNAMEType"/> 
<!-- DB Scoped DDL --> 
<xs:element name="UserName" type="SSWNAMEType"/> 
<!-- Main Body --> 
<xs:element name="DatabaseName" type="SSWNAMEType"/> 
<xs:element name="SchemaName" type="SSWNAMEType"/> 
<xs:element name="ObjectName" type="SSWNAMEType"/> 
<xs:element name="ObjectType" type="SSWNAMEType"/> 
<xs:element name="Parameters" type="EventTag_Parameters" minOccurs="0"/> 
<xs:element name="AlterTableActionList" type="AlterTableActionListType" minOccurs="0"/> 
<xs:element name="TSQLCommand" type="EventTag_TSQLCommand"/> 
</xs:sequence> 
</xs:complexType> 

Вот очень простой тест, чтобы увидеть, как это работает, и что в результате EventData XML выглядит следующим образом:

IF (EXISTS(
    SELECT * 
    FROM sys.server_triggers sst 
    WHERE sst.name = N'CaptureAlterTable' 
    )) 
BEGIN 
    DROP TRIGGER CaptureAlterTable ON ALL SERVER; 
END; 
GO 

CREATE TRIGGER CaptureAlterTable 
ON ALL SERVER -- capture events for all databases 
FOR ALTER_TABLE -- only capture ALTER TABLE events 
AS 
    PRINT CONVERT(NVARCHAR(MAX), EVENTDATA()); -- Display in "Messages" tab in SSMS 
GO 

Сначала мы создаем простой, реальная таблица в tempdb (эти события не фиксируются для временных таблиц):

USE [tempdb]; 
CREATE TABLE dbo.MyAlterTest (Col2 INT NULL); 

Затем мы добавим столбец. Мы делаем это из другой базы данных, чтобы убедиться, что XML захватывает базу данных, где объект существует, а не текущая база данных. Обратите внимание на обложку слов alTeR Table tempDB.dbo.MyALTERTest ... DATEcreated для сравнения с тем, что есть в XML.

USE [master]; 
alTeR Table tempDB.dbo.MyALTERTest ADD DATEcreated DATETIME NOT NULL; 

Вы должны увидеть следующее на вкладке «Сообщения» (комментарии, добавленные мной):

<EVENT_INSTANCE> 
    <EventType>ALTER_TABLE</EventType> 
    <PostTime>2014-12-15T10:53:04.523</PostTime> 
    <SPID>55</SPID> 
    <ServerName>_{server_name}_</ServerName> 
    <LoginName>_{login_name}_</LoginName> 
    <UserName>dbo</UserName> 
    <DatabaseName>tempdb</DatabaseName> <!-- casing is based on database definition --> 
    <SchemaName>dbo</SchemaName> 
    <ObjectName>MyAlterTest</ObjectName> <!-- casing is based on object definition --> 
    <ObjectType>TABLE</ObjectType> 
    <AlterTableActionList> 
    <Create> 
     <Columns> 
     <Name>DATEcreated</Name> <!-- casing is taken from executed query --> 
     </Columns> 
    </Create> 
    </AlterTableActionList> 
    <TSQLCommand> 
    <SetOptions ANSI_NULLS="ON" ANSI_NULL_DEFAULT="ON" ANSI_PADDING="ON" QUOTED_IDENTIFIER="ON" ENCRYPTED="FALSE"/> 
    <CommandText>alTeR Table tempDB.dbo.MyALTERTest ADD DATEcreated DATETIME NOT NULL;&#x0D; 
</CommandText> 
    </TSQLCommand> 
</EVENT_INSTANCE> 

Было бы хорошо, если за колонкой детали (т.е. NULL/NOT NULL, тип данных и т. д.), а не только имя, но при необходимости они могут быть проанализированы из элемента CommandText.

1
SELECT so.name,so.modify_date 
FROM sys.objects as so 
    INNER JOIN INFORMATION_SCHEMA.TABLES as ist 
ON ist.TABLE_NAME=so.name where ist.TABLE_TYPE='BASE TABLE' AND 
TABLE_CATALOG='dbName' order by so.modify_date desc; 
Смежные вопросы