为启动外部EXE的类编写单元测试


9

我编写了一个C#类,用于启动EXE列表(不是我的一个-我必须运行的第三方EXE)并使其保持运行状态(偶尔检查以确保它仍在运行,如果没有,则启动它们) 。

我能够测试添加,删除等的基本逻辑。如何对保持EXE的实际工作进行单元测试?

我最初的想法是启动一些虚拟EXE,该EXE在1秒后关闭,然后使用它进行测试。这是否超出了单元测试的范围?

Answers:


12

我最初的想法是启动一些虚拟EXE,该EXE在1秒后关闭,然后使用它进行测试。这是否超出了单元测试的范围?

这是一个很好的测试吗?当然可以,创建它。真正意义上的“单元测试”吗?我不这么认为,我将其称为“系统测试”或类似的东西,但这并不会降低测试的价值。


9

在更高的水平上进行模拟。在周围创建一个代理类Process.Start(),在测试中伪造该代理类并检查输入。

public interface IProcessProxy
{
     ProcessInfo Start(string application, string[] arguments);
}

public class ProcessProxy : IProcessProxy
{
    public ProcessInfo Start(string application, string[] arguments)
    {
        return Process.Start(application, arguments);
    }
}

// You could use a mocking framework for this, but for the purposes
// of this example ...
public class FakeProcessProxy : IProcessProxy
{
    private string _expectedApplication;
    private string[] _expectedArguments;
    private ProcessInfo response;

    public FakeProxy(string expectedApplication, string[] expectedArguments, ProcessInfo response)
    {
         _expectedApplication = expectedApplication;
         _expectedArguments = expectedArguments;
    }

    public ProcessInfo Start(string application, string[] arguments)
    {
         // compare input to expectations and throw exception if not matching
         return _response;
    }
}

// You can also use an IoC framework to inject your IProcessProxy, but I won't.
public class ClassUnderTest
{
    public ClassUnderTest(IProcessProxy proxy)
    {
        _proxy = proxy;
    }

    public ClassUnderTest() : this(new ProcessProxy())
    {
    }

    public void MethodUnderTest()
    {
        // Do stuff

        ProcessInfo process = _proxy.Start(@"C:\Program Files\App\App.exe", new[] { "arg1", "arg2" });
        process.WaitForExit();

        if (process.ExitCode == 0)
        {
            // Act on success
        }
        else
        {
            // Act on failure
        }
    }   
}

在需要在应用程序代码中使用ClassUnderTest的任何地方,请使用默认构造函数。在您的测试中,使用预期的Proxy Start参数并将测试结果传递到假的构造函数中,将FakeProcessProxy传递给其他构造函数。


4

严格遵循单元测试的原理(强调unit)时,您不应创建Exe文件,而应测试您的类是否调用接口以正确生成和监视该过程。毕竟,您只想测试您的类,而不是负责处理过程的库。

但是从务实的角度来看,您的方法很好,尽管1秒似乎有点长。


1

我做了类似的事情,只是打电话给ping localhost。节省了将可执行文件放到构建服务器上的麻烦

By using our site, you acknowledge that you have read and understand our Cookie Policy and Privacy Policy.
Licensed under cc by-sa 3.0 with attribution required.