Запрос, чтобы получить все версии графа объекта
-
03-07-2019 - |
Вопрос
Я внедряю журнал аудита в базе данных, поэтому у всех есть столбцы CreatedAt и RemovedAt. Теперь я хочу иметь возможность перечислить все ревизии графа объектов, но лучший способ, которым я могу придумать для этого, состоит в том, чтобы использовать объединения. Мне нужно получить каждый уникальный идентификатор CreatedAt и RemovedAt.
Если я получу список стран с провинциями, профсоюз будет выглядеть следующим образом:
SELECT c.CreatedAt AS RevisionId from Countries as c where localId=@Country
UNION
SELECT p.CreatedAt AS RevisionId from Provinces as p
INNER JOIN Countries as c ON p.CountryId=c.LocalId AND c.LocalId = @Country
UNION
SELECT c.RemovedAt AS RevisionId from Countries as c where localId=@Country
UNION
SELECT p.RemovedAt AS RevisionId from Provinces as p
INNER JOIN Countries as c ON p.CountryId=c.LocalId AND c.LocalId = @Country
Для более сложных запросов это может быть довольно сложно и, возможно, работать очень плохо, поэтому я хотел посмотреть, сможет ли кто-нибудь придумать лучший подход. Это на сервере MSSQL.
Они нужны мне в одном списке, потому что они используются в предложении from, и реальные данные поступают из этого соединения.
Решение
Скорее всего, вы уже реализовали свое решение, но решили несколько вопросов; Я бы предложил рассмотреть решение Aleris или его производную.
Поля, содержащиеся в вашем журнале, оставлены на ваше усмотрение, но решение Aleris является прямым. Я могу создать таблицу действий и изменить тип поля с varchar на int, как ссылку на таблицу действий, что вынуждает разработчиков выполнять некоторые стандартизированные действия. Р>
Надеюсь, это поможет.
Другие советы
Альтернативой может быть создание журнала аудита, который может выглядеть следующим образом:
AuditLog table
EntityName varchar(2000),
Action varchar(255),
EntityId int,
OccuranceDate datetime
где EntityName - это имя таблицы (например, Contries, Provinces), Action - это действие аудита (например, Created, Removed и т. д.), а EntityId - первичный ключ измененной строки в исходной таблице. р>
Таблица должна быть синхронизирована при каждом действии над таблицами. Есть несколько способов сделать это:
1) Создайте триггеры для каждой таблицы, которые добавят строки в AuditTable
2) Из вашего приложения добавляйте строки в AuditTable каждый раз, когда вносятся изменения в reversetables
С помощью этого решения очень просто получить список журналов аудита.
Если вам нужно получить столбцы из исходной таблицы, можно также использовать такие объединения:
select *
from
Contries C
join AuditLog L on C.Id = L.EntityId and EntityName = 'Contries'
Возможно, вы могли бы сделать это с помощью перекрестного соединения и объединения, но объединение, вероятно, все еще лучше с точки зрения производительности. Вы можете попробовать проверить каждый из них.
SELECT
COALESCE(C.CreatedAt, P.CreatedAt)
FROM
dbo.Countries C
FULL OUTER JOIN dbo.Provinces P ON
1 = 0
WHERE
C.LocalID = @Country OR
P.LocalID = @Country