2016-11-30 5 views
-1

Я пытаюсь написать единичный тестовый пример класса, который использует Dll импорта, как показано нижеКак издеваются в DLL Импорт

[DllImport("user32.dll")] 
public static extern IntPtr FindWindow(string name, string windowName); 

Для того, чтобы проверить класс я хочу издеваться выше заявление, используя MOQ, но не в состоянии понять, как настроить макет для него.

Также хотелось бы знать, является ли вышеизложенное возможным или нет. Если нет, то что нужно сделать, чтобы сделать его проверяемым.

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

Хотел бы знать, есть ли другой вариант для достижения того же.

+0

Но с DLL импорта статики является обязательным –

+0

Конечно, но вы можете просто скрыть вызов этого статического метода в вызове другому методу. – HimBromBeere

+0

Да .. но тогда, когда я попробую написать модульный тест для этого класса обертки, я буду в той же ситуации –

ответ

1

Вы не можете издеваться над статическим методом, а только с интерфейсами или классами с виртуальными членами. Однако вы можете обернуть метод в виртуальную, что вы можете обернуть:

interface StaticWrapper 
{ 
    InPtr WrapStaticMethod(string name, string windowName); 
} 
class MyUsualBehaviour : IStaticWrapper 
{ 
    public InPtr WrapStatic(string name, string windowName) 
    { 
     // here we do the static call from extern DLL 
     return FindWindow(name, widnowName); 
    } 
} 

Однако теперь вы можете издеваться этот интерфейс вместо статического метода:

var mock = new Moq<IStaticWrapper>(); 
mock.Setup(x => x.WrapStatic("name", "windowName")).Returns(whatever); 

Кроме того, вы aren't вызова EXTERN в вашем коде, но только оболочка, которая уменьшает кодовое связывание с этой конкретной библиотекой.

Смотрите эту ссылку для дальнейшего объяснения идея: http://adventuresdotnet.blogspot.de/2011/03/mocking-static-methods-for-unit-testing.html

+0

Я знаю ... это то, что я упомянул в моем вопросе также. –

+1

@RishiTiwari почему бы вам не сделать это тогда? То, что вы просите, эквивалентно «Как я могу высмеять ссылку на сборку»? DllImport - это не метод для фальсификации, это * объявление * - ссылка на конкретную точку входа в библиотеке. На самом деле хорошей практикой является сбор деклараций DllImport в одном классе. –

+0

Я просто хочу знать, можно ли или нет издеваться над импортом DLL ... чтобы проверить его. Я знаю, что требуется оболочка. Спасибо anyways –

2

на самом деле вы можете издеваться методы из экспортируемых DLLS с помощью TypeMock Изолятор, и без каких-либо ненужных изменений в коде. вам просто нужно экспортировать Dll и издеваться метод, как и любой другой статический метод, , например:

public class ClassUnderTest 
    { 

     public bool foo() 
     { 
      if(Dependecy.FindWindow("bla","bla") == null) 
      { 
       throw new Exception(); 
      } 
      return true; 
     } 
    } 

public class Dependecy 
{//imported method from dll 
    [DllImport("user32.dll")] 
    public static extern IntPtr FindWindow(string name, string windowName); 
} 

     [TestMethod] 
     public void TestMethod1() 
     { 
      //setting a mocked behavior for when the method will be called 
      Isolate.WhenCalled(() => Dependecy.FindWindow("", "")).WillReturn(new IntPtr(5)); 

      ClassUnderTest classUnderTest = new ClassUnderTest(); 
      var res = classUnderTest.foo(); 

      Assert.IsTrue(res); 
     } 

Вы можете увидеть больше о методах Pinvoked here

+0

Я хочу сделать то же самое с помощью MOQ .. мы используем среду MOQ, чтобы издеваться над нашими зависимостями ...не может использовать какие-либо другие рамки ... но спасибо за то, что если мы используем Type mocks, мы можем на самом деле высмеять вызовы на импорт DLL. Ответ проголосовал за ваш ответ, но не может отметить его как ответ. –