Принудительное оформление атрибутов классов / методов - PullRequest
16 голосов
/ 21 августа 2008

В продолжение моего недавнего вопроса о Большие, сложные объекты как результат веб-службы . Я думал о том, как обеспечить, чтобы все будущие дочерние классы были сериализуемыми в XML.

Теперь, очевидно, я мог бы реализовать интерфейс IXmlSerializable и затем привязать к нему читателя / писателя, но я бы хотел этого избежать, поскольку тогда это означает, что мне нужно создавать экземпляр читателя / писателя всякий раз, когда я хочу сделайте это, и в 99,99% случаев я буду работать со строкой , поэтому я могу просто написать свою собственную.

Однако, чтобы сериализовать в XML, я просто украшаю класс и его члены атрибутами Xml ??? ( XmlRoot , XmlElement и т. Д. ), а затем передав его в XmlSerializer и StringWriter , чтобы получить строку. Что все хорошо. Я намереваюсь поместить метод для возврата строки в универсальный служебный метод, поэтому мне не нужно беспокоиться о типе и т. Д.

Меня беспокоит следующее: если я не украшаю класс (ы) необходимыми атрибутами, ошибка не выдается до времени выполнения.

Есть ли способ принудительного оформления атрибутов? Можно ли это сделать с помощью FxCop? (я еще не использовал FxCop)

UPDATE:

Извините за задержку с этим, ребята, много дел!

Определенно, как идея использовать отражение, чтобы сделать это в тестовом примере, а не прибегать к FxCop (как сохранить все вместе). Ответ Фредрика Калсета был фантастическим, спасибо, что включил код в качестве наверное, мне понадобилось бы немного покопаться, чтобы понять, как это сделать самому!

+ 1 к другим парням за подобные предложения:)

Ответы [ 5 ]

19 голосов
/ 21 августа 2008

Я бы написал единичный / интеграционный тест, который проверяет, что любой класс, соответствующий некоторым заданным критериям (т. Е. Подкласс X), оформлен соответствующим образом. Если вы настроили сборку на запуск с тестами, вы можете потерпеть неудачу при сбое теста.

ОБНОВЛЕНИЕ: Вы сказали: «Похоже, мне просто нужно будет закатать рукава и убедиться, что юнит-тесты собраны вместе» - вам не нужно. Просто напишите общий тестовый класс, который использует отражение, чтобы найти все классы, которые должны быть утверждены. Примерно так:

[TestClass]
public class When_type_inherits_MyObject
{
    private readonly List<Type> _types = new List<Type>();

    public When_type_inherits_MyObject()
    {
        // lets find all types that inherit from MyObject, directly or indirectly
        foreach(Type type in typeof(MyObject).Assembly.GetTypes())
        {
            if(type.IsClass && typeof(MyObject).IsAssignableFrom(type))
            {
                _types.Add(type);
            }
        }
    }

    [TestMethod]
    public void Properties_have_XmlElement_attribute
    {
        foreach(Type type in _types)
        {
            foreach(PropertyInfo property in type.GetProperties())
            {
                object[] attribs = property.GetCustomAttributes(typeof(XmlElementAttribute), false);
                Assert.IsTrue(attribs.Count > 0, "Missing XmlElementAttribute on property " + property.Name + " in type " + type.FullName);
            }
        }
    }
}
1 голос
/ 21 августа 2008

Вы можете написать правило FxCop или даже проверить атрибуты, вызвав GetType () в конструкторе базового класса и размышляя над возвращаемым типом.

1 голос
/ 21 августа 2008

Вы можете написать модульные тесты для проверки такого рода вещей - в основном используется отражение.

Учитывая тот факт, что это возможно, я думаю, что было бы также возможно написать правило FxCop, но я никогда не делал такого.

0 голосов
/ 06 марта 2009

Вы также можете использовать эту концепцию / постпроцессор для обеспечения взаимосвязей между атрибутами и использовать аналогичный вход в систему для обеспечения взаимосвязей между классами и атрибутами во время компиляции:

http://www.st.informatik.tu -darmstadt.de / базы данных / публикации / данные / СЕРА-mezini-gpce04.pdf? ID = 92

0 голосов
/ 04 октября 2008

Хорошим правилом FXCop (и которое я нахожу нужным прямо сейчас) было бы проверить, что все объекты, добавляемые в сеанс ASP.NET, имеют атрибут Serializable. Я пытаюсь перейти из состояния сеанса InProc в SQL Server. Когда я впервые запросил страницу, мой сайт взорвался, потому что в Session хранились несериализуемые объекты. Затем возникла задача поиска по всему исходному коду для поиска каждого экземпляра, в котором объект установлен в сеансе ... FXCop было бы хорошим решением. Над чем поработать ...

...