您如何模拟虚拟二进制文件,以便可以测试exec()/system()/passthru()函数的输出? [英] How do you mock a virtual binary file so that exec() / system() / passthru() function output can be tested?

查看:93
本文介绍了您如何模拟虚拟二进制文件,以便可以测试exec()/system()/passthru()函数的输出?的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

我有一个有趣的问题,已经在互联网上搜索了,但是还没有找到答案.

I have an interesting problem and have searched the internet, but haven't yet found an answer.

我在一家不允许员工使用OOP的公司工作,这很荒谬,但是工作经验很有价值.

I work for a company that doesn't allow it's workers to utilize OOP, it is kind of ridiculous, but the working experience is valuable.

考虑以下功能:

function get_setting_values_from_file( $parameter )
{
    exec("/usr/var/binary --options $parameter", $output, $return);
    $settings = file( $output[0] );
    foreach( $settings as $setting ) {
        if( strstr( $setting, "color") ) {
            $setting = explode( ":", $setting );
            return $setting[1];
        }
    }
    return false;
}

我需要对相似的功能进行单元测试.我目前正在使用phpUnit进行测试,并使用vfsStream库来模拟文件系统,但是当我在无法访问实际系统的情况下进行开发时,如何模拟对exec("/usr/var/binary --options $parameter", $output, $return)的调用?推荐的处理此类测试用例的方法是什么?

I need to unit test a similar function. I am currently using phpUnit for my tests and the vfsStream libraries to mock the file system, but how do you mock the call to exec("/usr/var/binary --options $parameter", $output, $return) when I'm developing with no access to the actual system? What is the recommend approach for dealing with test cases like this?

感谢所有反馈.

推荐答案

简单地模拟此函数即可返回要进入$ settings的文本.您无需调用可执行文件,只需创建文件或返回即可.

Simply mock this function to return the text that you are trying to get into $settings. You do not need to call the executable, simply create the file or return.

例如,假设函数get_setting_values_from_file()将设置作为数组返回,则可以在测试中简单地模拟该函数以将设置作为数组返回.创建一个测试存根以模拟包含get_setting_values_from_file()方法的对象,并使该模拟简单返回测试假定的相同FALSE(1或2).

For instance, assuming the function get_setting_values_from_file() returns the settings as an array, you can simply mock the function in your test to return the settings as an array. Create a test stub to mock the object that contains the get_setting_values_from_file() method, and have that mock simply return the same FALSE, 1 or 2 that the test assumed.

$stub = $this->getMock('GetSettingsClass');
    $stub->expects($this->any())
         ->method('get_settings_from_file')
         ->will($this->returnValue(0));

这来自PHPUnit手册-> http: //phpunit.de/manual/3.8/en/test-doubles.html#test-doubles.stubs

This is from the PHPUnit manual -> http://phpunit.de/manual/3.8/en/test-doubles.html#test-doubles.stubs

(可选)您甚至可以绕过调用,并通过创建数组并将其传递给那些函数来简单地测试对返回值起作用的函数/代码. 在主代码中假设为示例:

Optionally, you could even bypass the call, and simply test the functions/code that works on the returns by creating the array and passing it to those functions. Assumed Example in the main code:

...
$settings = get_setting_values_from_file( 'UserType' );
$UserType = get_user_type($settings);
return $UserType;

function get_user_type($settings)
{
    if($settings !== FALSE)         // Returned from your function if parameter is not found
    {
        switch($settings)
        {
            case 1:
                return 'User';      // Best to use Constants, but for example here only
                break;
            case 2:
                return 'Admin';
                break;
            ...
         }
    }
    else
    {
        return FALSE;
    }
}

现在,在测试中,您只需

Now, in your test, you can simply

$this->assertFalse(get_user_type(FALSE, 'Ensure not found data is handled properly as FALSE is returned');
$this->assertEqual('User', get_user_type(1), 'Test UserType=1');
$this->assertEqual('Admin', get_user_type(1), 'Test UserType=2');
...

这些作为代码的工作不会调用必须模拟从OS读取的函数,而是通过调用处理设置返回值的函数来处理所有预期的返回.在这里,您仅假设函数'get_setting_values_from_file()'的返回而无需文件或任何模拟.

These work as the code does not call the function that had to mock the read from the OS, but does handle all the expected returns by calling the function processing the setting return value. Here, you have simply assumed the return from the function 'get_setting_values_from_file()' without needing the file or any mocks.

但是,这不会测试从文件中读取数据,在另一项测试中,我将使用setUp和tearDown来实际创建具有所需值(fopen/fwrite)的文件,然后调用函数并确保其返回会发生什么.

This does NOT however test reading from the file, which I would do in another test by using the setUp and tearDown to actual create a file with the values you want (fopen/fwrite) and then call your function and ensure it returns what is expected.

我希望这有助于解释我的想法.

I hope this helps to explain what I was thinking.

这篇关于您如何模拟虚拟二进制文件,以便可以测试exec()/system()/passthru()函数的输出?的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆