Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

How to inject an env variable just for certain testsuite using phpunit?

In the phpunit.xml one can define envirionment variables:

<php>
    <env name="ENVIRONMENT" value="test"/>
    <env name="FOO" value="BAR"/>
</php>

Now, I want to have multiple testsuites instead of just one. And I like to have different values for FOO for each, so I thought I could do this:

<testsuites>
    <testsuite name="First">
        <directory>unit</directory>
        <directory>Functional</directory>
        <php>
            <env name="FOO" value="NARF"/>
        </php>
    </testsuite>
    <testsuite name="Second">
        <directory>unit</directory>
        <directory>Functional</directory>
        <php>
            <env name="FOO" value="NARF"/>
        </php>
    </testsuite>
</testsuites>

It doesn't seem possible to nest php inside testsuite block. So I am currently stuck injecting a specific variable for a certain testsuite.

The only other clear option I see is defining multiple phpunit.xml files for each case, yet this would lead to a lot of code duplication I like to avoid.

Is there another way to inject an env variable to a phpunit testsuite?

like image 407
k0pernikus Avatar asked Feb 12 '16 10:02

k0pernikus


3 Answers

You can use the package phpunit-globals that allows you to modify the $_ENV (and $_SERVER) variables for a specific test class or method.

Install it as a development dependency with:

composer require --dev zalas/phpunit-globals

Afterwards, you can do:

/**
 * @env FOO=bar
 */
class ExampleTest extends TestCase
{
    /**
     * @env APP_ENV=foo
     */
    public function test_global_variables()
    {
        $this->assertSame('bar', $_ENV['FOO']);
        $this->assertSame('foo', $_ENV['APP_ENV']);
    }
}
like image 181
magnetik Avatar answered Oct 24 '22 05:10

magnetik


Environment variables defined in phpunit.xml are defaults. You can also pass them from shell:

FOO=bar phpunit

This is not going to help you much, as you'll need to run your test suites separately, passing env variables to each run.

I think a good alternative is to call these variables differently for each test suite (FOO_FIRST, FOO_SECOND etc).

like image 2
Jakub Zalas Avatar answered Oct 24 '22 05:10

Jakub Zalas


This is an old question, but with current versions of PHPUnit (8+), you can set environment variable inside tests without problems. So instead of having multiple testsuites with same tests and different envs, you can have one test suite with same tests and data provider for different envs - e.g. like this.

class ExampleTest extends TestCase
    public function envValueProvider(): array
    {
        return [
            [
                'foo',
            ],
            [
                'bar',
            ],
        ];
    }

    /**
     * @dataProvider envValueProvider
     */
    public function testSomeCode(string $value): void
    {
        putenv('FOO=' . $value);
        somecode();
        self::assertSomething();
    }
like image 2
Odin Avatar answered Oct 24 '22 04:10

Odin