Вы можете сделать одно из следующих действий:
Мои личные предпочтения - последний вариант, но первые два могут быть проще для вас.
Для первых двух опций вам нужно создать задание Агент SQL Server , чтобы запускать его по ночам и делать снимки. Третий вариант работает автоматически.
Допустим, ваша таблица называется MyTable
и имеет первичный ключ ID int
и поле Name varchar(50)
.
Для первого варианта вам нужно использовать динамический SQL, потому что каждый раз имя вашей новой таблицы будет отличаться:
declare @sql nvarchar(max) = N'select ID, Name into MyTable_' +
convert(nvarchar(10), getdate(), 112) + N' from MyTable'
exec (@sql)
При выполнении этого оператора будет создана новая таблица с той же структурой, что и у вас. существующая таблица, но названная с текущей датой как суффикс, например MyTable_20190116
и скопировать MyTable
к нему.
Для второго варианта вам нужно создать одну таблицу, подобную приведенной ниже, и скопировать в нее данные, используя следующий скрипт:
create table MyTableDailySnapshots(
SnapshotDate date not null
, ID int not null
, Name varchar(50)
, constraint PK_MyTableDailySnapshots primary key clustered (SnapshotDate, ID)
)
insert into MyTableDailySnapshots(SnapshotDate, ID, Name)
select GETDATE(), ID, Name
from MyTable
Если вы выберете третий вариант, никаких действий не требуется для поддержания моментальные снимки. Просто используйте запрос, подобный этому, чтобы получить состояние таблицы за период времени:
select ID, Name from MyTable
for system_time between '2019-01-16 00:00:00.0000000' and '2019-01-16 23:59:59.9999999'
Первый вариант более гибок, если схема таблицы изменяется во времени, потому что каждый день вы можете создавать таблицу с другой схемой. Варианты 2 и 3 имеют только 1 таблицу для хранения снимков, поэтому вам может потребоваться проявить творческий подход, если необходимо изменить схему таблицы. Но недостатком первого варианта является большое количество таблиц, созданных в вашей базе данных.
Так что вам решать, что лучше для вашего случая.
Возможно, рассмотрите сериализатор, который не связывается с типом и именами полей? Например, protobuf-сеть является двоичным сериализатором, но использует числовой набор тегов (через атрибут) против каждого участника. Это означает:
Например:
[ProtoContract]
public class Foo {
[ProtoMember(1)]
public string Bar {get;set;}
}
Здесь, 1
все, что идентифицировало участника в файле. Ключ здесь - то, что это основано на контракте, так может быть десериализован позже с несвязанным типом:
[ProtoContract]
public class a12 {
[ProtoMember(1)]
public string a {get;set;}
}
(который прекрасен, так как путаница сохраняет метаданные, IIRC).
Контрастируйте это с другими основанными на контракте сериализаторами (такой как XmlSerializer
или DataContractSerializer
) - где Вы были бы вынуждены поместить имя элемента в атрибуты, которые в значительной степени представят бессмысленную путаницу:
[DataContract]
public class a12 {
[DataMember(Name="Bar")]
public string a {get;set;}
}
Путаница не обеспечивает безопасность во-первых. Так, можно хотеть рассмотреть отбрасывание его, период.
Эти две опции, которые я вижу:
Так как Вы ничего не получаете путем запутывания, я пошел бы с № 1.