SQL для LINQ сравнить 2 сущностей на предмет изменений - создание контрольного журнала - PullRequest
1 голос
/ 28 августа 2010

Я нахожусь в гипотетической фазе размышлений о том, как что-то сделать в коде, поэтому у меня пока нет конкретных примеров кода.Но давайте предположим, что у вас есть тип сущности Person (с такими атрибутами, как имя, фамилия, DOB и т. Д.).Когда требуется редактировать сущность человека, вы можете обновить только одно или два поля (возможно, все, но обычно нет).Думайте об этом как о внедрении контрольного журнала (хотя и не юридического, а только информационного), то есть Томми сменил фамилию с Джонса на Смита 28.08.2010.

Вопрос в том, предоставляет ли LINQ интерфейс для сравнения того, что было изменено на сущности человека со старой, существующей и вновь представленной?

Или один цикл должен пройти через свойства старой и новой сущностей и выполнить сравнение каждого из них вручную?

Псевдо:

For each p as property in person
   If oldEntity.p <> newEntity.p then
       auditEntry = new auditEntry(oldEntity.p, newEntity.p)
   end If
Next

Или есть другой/ лучший способ (реализовать интерфейс IComparable для каждого объекта в частичном классе), который может сделать это?

Ответы [ 3 ]

1 голос
/ 28 августа 2010

Это не совсем то, что вы ищете, но я разместил образец решения, которое я использовал для приложения, созданного несколько лет назад (до LINQ дней), в этой теме:

подсказкадля подхода к журналу аудита

Это может помочь вам и немного подумать о решении.

0 голосов
/ 29 августа 2010

С учетом следующих процедур:

    public static void CompareProperties<T>(object source, object target)
    {
        Type type = typeof(T);

        CompareProperties(type, source, target);

        if (type.IsInterface)
        {
            Type[] baseTypes = type.GetInterfaces();
            foreach (var baseType in baseTypes)
            {
                CompareProperties(baseType, source, target);
            }
        }
        else
        {
            type = type.BaseType;
            while (type != null)
            {
                CompareProperties(type, source, target);
                type = type.BaseType;
            }
        }
    }

    private static void CompareProperties(Type type, object source, object target)
    {
        PropertyInfo[] props = type.GetProperties(
            BindingFlags.NonPublic | BindingFlags.Public | BindingFlags.Instance);

        PropertyInfo[] props1 = source.GetType().GetProperties(
            BindingFlags.NonPublic | BindingFlags.Public | BindingFlags.Instance);

        PropertyInfo[] props2 = target.GetType().GetProperties(
                        BindingFlags.NonPublic | BindingFlags.Public | BindingFlags.Instance);

        foreach (PropertyInfo pi in props)
        {
            if (!pi.CanRead || !pi.CanWrite)
                continue;
            var name = pi.Name;
            var pi1 = props1.Where(x => x.Name == name).FirstOrDefault();
            var pi2 = props2.Where(x => x.Name == name).FirstOrDefault();
            if(pi1 == null || pi2 == null)
                continue;

            var expected = pi1.GetValue(source, null);
            var actual = pi2.GetValue(target, null);

            if(pi.PropertyType == typeof(int?))
            {
                expected = expected ?? 0;
                actual = actual ?? 0;
            }
            if (pi2.PropertyType.IsEnum && !pi.PropertyType.IsEnum)
            {
                continue;
                expected = (int)expected;
                actual = (int)actual;
            }
            Assert.AreEqual(expected, actual, "The property '" + pi.Name + "' was not saved for the " + source.GetType().Name);

        }
    }

Вы можете сравнить два объекта следующим образом:

CompareProperties<CustomerProduct>(product1, productFromDb)
0 голосов
/ 29 августа 2010

DataContext.GetChangeSet и Table.GetOriginalEntityState - это то, что вы ищете -

http://msdn.microsoft.com/en-us/library/system.data.linq.datacontext.getchangeset.aspx

http://msdn.microsoft.com/en-us/library/bb548700.aspx

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...