[Насмешка запечатанных классов] [1] может быть настоящей болью. Я в настоящее время одобряю Образец адаптера, чтобы обращаться с этим, но что-то о просто сохраняет чувства странными.
Так, Каков лучший способ, которым Вы дразните запечатанные классы?
Явские ответы - больше, чем welcome. На самом деле я ожидал бы, что Явское сообщество имело дело с этим дольше и имеет много, чтобы предложить.
Но вот некоторые.NET мнения:
[1]: http://www.google.com/search? q=how%20to%20mock%20sealed%20class
Я полагаю, что Родинки, от Microsoft Research, позволяют Вам делать это. Со страницы Родинок:
Родинки могут использоваться, чтобы идти в обход любой.NET метод, включая non-virtual/static методы в запечатанных типах.
ОБНОВЛЕНИЕ: есть новая структура, названная " Fakes" в предстоящем ПРОТИВ 11 выпусков, которые разработаны, чтобы заменить Родинки:
[Фальсифицирует Структуру в Визуальной Студии 11] (http://aka.ms/vs11-fakes), следующее поколение Родинок & Окурки, и в конечном счете заменят его. Фальшивки отличаются от Родинок, однако, таким образом перемещаться от Родинок к Фальшивкам потребует некоторых модификаций к Вашему кодексу. Руководство для этой миграции будет доступно позднее.
требования : визуальная студия 11 окончательных.NET 4.5
Мое общее правило большого пальца состоит в том, который возражает, что я должен дразнить, должен иметь общий интерфейс также. Я думаю, что это правильно мудрый дизайном и делает тесты намного легче (и обычно, что Вы получаете, если Вы делаете TDD). Больше об этом может быть прочитан в Google Testing Blog последняя почта (См. пункт 9).
Кроме того, I' ve, работая, главным образом, на Яве за прошлые 4 года и я могу сказать, что могу посчитать с одной стороны количество раз I' ve создал (запечатанный) класс финала. Другое правило здесь, у меня должно всегда быть серьезное основание запечатать класс, в противоположность запечатыванию его по умолчанию.
Я почти всегда стараюсь не иметь зависимости от внешних классов глубоко в рамках моего кодекса. Вместо этого I' d очень скорее используют адаптер/мост, чтобы говорить с ними. Тем путем, I' m контакт с моей семантикой и боль перевода изолирован в одном классе.
Это также облегчает переключать мои зависимости в конечном счете.
Проблема с TypeMock состоит в том, что он извиняет плохой дизайн. Теперь, я знаю, что это часто кто-то else' s плохо проектируют это it' s сокрытие, но разрешение его в Ваш процесс развития может привести очень легко к разрешению Ваших собственных плохих проектов.
Я думаю если you' ре, собирающееся использовать структуру насмешки, Вы должны использовать традиционную (как Moq) и создать слой изоляции вокруг unmockable вещи и дразнить слой изоляции вместо этого.
Я столкнулся с этой проблемой недавно и после чтения / ищущая сеть, кажется, что нет никакого легкого способа вокруг кроме использовать другой инструмент, как упомянуто выше. Или сырая нефть обработки вещей, как я сделал:
Создайте случай запечатанного класса, не получая вызванного конструктора.
Система. Время выполнения. Преобразование в последовательную форму. FormatterServices. GetUninitializedObject (instanceType);
Назначьте ценности на свою недвижимость / области через отражение
YourObject. GetType ().GetProperty (" PropertyName").SetValue (dto, newValue, пустой указатель);
YourObject. GetType ().GetField (" FieldName").SetValue (dto, newValue);
Совершенно разумно дразнить запечатанный класс, потому что запечатаны много классов структуры.
В моем случае I' m пытающийся дразнить.Net' s класс MessageQueue так, чтобы я мог TDD моя изящная логика обработки исключений.
Если у кого-либо есть идеи о том, как преодолеть Moq' s ошибка относительно " Недействительная установка на member", несверхпригодном для верховой езды; пожалуйста, сообщите мне.
кодекс:
[TestMethod]
public void Test()
{
Queue<Message> messages = new Queue<Message>();
Action<Message> sendDelegate = msg => messages.Enqueue(msg);
Func<TimeSpan, MessageQueueTransaction, Message> receiveDelegate =
(v1, v2) =>
{
throw new Exception("Test Exception to simulate a failed queue read.");
};
MessageQueue mockQueue = QueueMonitorHelper.MockQueue(sendDelegate, receiveDelegate).Object;
}
public static Mock<MessageQueue> MockQueue
(Action<Message> sendDelegate, Func<TimeSpan, MessageQueueTransaction, Message> receiveDelegate)
{
Mock<MessageQueue> mockQueue = new Mock<MessageQueue>(MockBehavior.Strict);
Expression<Action<MessageQueue>> sendMock = (msmq) => msmq.Send(It.IsAny<Message>()); //message => messages.Enqueue(message);
mockQueue.Setup(sendMock).Callback<Message>(sendDelegate);
Expression<Func<MessageQueue, Message>> receiveMock = (msmq) => msmq.Receive(It.IsAny<TimeSpan>(), It.IsAny<MessageQueueTransaction>());
mockQueue.Setup(receiveMock).Returns<TimeSpan, MessageQueueTransaction>(receiveDelegate);
return mockQueue;
}
Я обычно следую маршрутом создания класс интерфейса и адаптера/полномочия, чтобы облегчить насмешку запечатанного типа. Однако I' ve также экспериментировал с тем, чтобы пропускать создание интерфейса и создание типа по доверенности, незапечатанного с виртуальными методами. Это работало хорошо, когда полномочие - действительно естественный базовый класс, который заключает в капсулу и пользовательская часть запечатанного класса.
Имея дело с кодексом, который потребовал этой адаптации, я устал от выполнения тех же действий, чтобы создать интерфейсный и тип по доверенности, таким образом, я осуществил библиотеку, чтобы автоматизировать задачу.
Кодекс несколько более сложен, чем образец, данный в статье, на которую Вы ссылаетесь, поскольку это производит собрание (вместо исходного кода), позволяет, чтобы генерация объектного кода была выполнена на любом типе и doesn' t требуют такой же конфигурации.
Для получения дополнительной информации, пожалуйста, обратитесь к [эта страница] [1].
[1]: http://jolt.codeplex.com/wikipage? title=Jolt. Тестирование. CodeGeneration. Proxy& referringTitle=Jolt. Тестирование
Хотя ее в настоящее время единственное доступное в бете-версии, я думаю его стоящий учет [прокладка] (http://msdn.microsoft.com/en-us/library/hh549176%28v=vs.110%29.aspx), особенность нового [Фальсифицирует структуру] (http://aka.ms/vs11-fakes) (часть [Визуальная Студия 11] (http://www.microsoft.com/visualstudio/11/en-us) Бета-версия).
типы Прокладки обеспечивают механизм, чтобы идти в обход, любой.NET метод пользователю определил делегата. Типы прокладки произведены кодексом генератором Фальшивок, и они используют делегатов, которых мы называем типами прокладки, чтобы определить новые внедрения метода. Под капотом прокладка печатает отзывы использования, которые были введены во времени выполнения в методе тела MSIL.
Лично я смотрел на использование этого, чтобы дразнить методы на запечатанных классах структуры, таких как DrawingContext.
Есть ли способ осуществить запечатанный класс от интерфейса... и дразнить интерфейс вместо этого?
Что-то во мне чувствует, что запечатывавший классы неправильное во-первых, но that' s просто я:)