merged branch naitsirch/process-inherit-env-fix (PR #8718)

This PR was submitted for the 2.3 branch but it was merged into the master branch instead (closes #8718).

Discussion
----------

[Process] always manually inherit $_SERVER by kriswallsmith #8067

| Q             | A
| ------------- | ---
| Bug fix?      | yes
| New feature?  | no
| BC breaks?    | no
| Deprecations? | no
| Tests pass?   | yes
| Fixed tickets | ~
| License       | MIT
| Doc PR        | ~

The `$_ENV` superglobal is not populated if `E` is not present in the `variables_order` directive. Since populating this variable is not recommended (for performance reasons), we should not rely on it.

This change updates the builder so `$env=null` is never passed to `proc_open()`. Instead we always merge the `$_SERVER` superglobal into any environment variables that were manually set on the builder (unless inherit has been disabled).

This is a copy of PR https://github.com/symfony/symfony/pull/8067 by @kriswallsmith. I have created a new PR because there were some failing tests and kriswallsmith seems to have no time to rebase.

Commits
-------

75be4d9 [Process] always manually inherit $_SERVER
This commit is contained in:
Fabien Potencier 2013-08-13 09:53:25 +02:00
commit e617ddb746
2 changed files with 18 additions and 59 deletions

View File

@ -164,7 +164,8 @@ class ProcessBuilder
$script = implode(' ', array_map(array(__NAMESPACE__.'\\ProcessUtils', 'escapeArgument'), $arguments));
if ($this->inheritEnv) {
$env = $this->env ? $this->env + $_ENV : null;
// include $_ENV for BC purposes
$env = array_replace($_ENV, $_SERVER, $this->env);
} else {
$env = $this->env;
}

View File

@ -17,75 +17,33 @@ class ProcessBuilderTest extends \PHPUnit_Framework_TestCase
{
public function testInheritEnvironmentVars()
{
$snapshot = $_ENV;
$_ENV = $expected = array('foo' => 'bar');
$_ENV['MY_VAR_1'] = 'foo';
$pb = new ProcessBuilder();
$pb->add('foo')->inheritEnvironmentVariables();
$proc = $pb->getProcess();
$proc = ProcessBuilder::create()
->add('foo')
->getProcess();
$this->assertNull($proc->getEnv(), '->inheritEnvironmentVariables() copies $_ENV');
unset($_ENV['MY_VAR_1']);
$_ENV = $snapshot;
$env = $proc->getEnv();
$this->assertArrayHasKey('MY_VAR_1', $env);
$this->assertEquals('foo', $env['MY_VAR_1']);
}
public function testProcessShouldInheritAndOverrideEnvironmentVars()
{
$snapshot = $_ENV;
$_ENV = array('foo' => 'bar', 'bar' => 'baz');
$expected = array('foo' => 'foo', 'bar' => 'baz');
$_ENV['MY_VAR_1'] = 'foo';
$pb = new ProcessBuilder();
$pb->add('foo')->inheritEnvironmentVariables()
->setEnv('foo', 'foo');
$proc = $pb->getProcess();
$this->assertEquals($expected, $proc->getEnv(), '->inheritEnvironmentVariables() copies $_ENV');
$_ENV = $snapshot;
}
public function testProcessBuilderShouldNotPassEnvArrays()
{
$snapshot = $_ENV;
$_ENV = array('a' => array('b', 'c'), 'd' => 'e', 'f' => 'g');
$expected = array('d' => 'e', 'f' => 'g');
$pb = new ProcessBuilder();
$pb->add('a')->inheritEnvironmentVariables()
->setEnv('d', 'e');
$proc = $pb->getProcess();
$this->assertEquals($expected, $proc->getEnv(), '->inheritEnvironmentVariables() removes array values from $_ENV');
$_ENV = $snapshot;
}
public function testInheritEnvironmentVarsByDefault()
{
$pb = new ProcessBuilder();
$proc = $pb->add('foo')->getProcess();
$this->assertNull($proc->getEnv());
}
public function testNotReplaceExplicitlySetVars()
{
$snapshot = $_ENV;
$_ENV = array('foo' => 'bar');
$expected = array('foo' => 'baz');
$pb = new ProcessBuilder();
$pb
->setEnv('foo', 'baz')
->inheritEnvironmentVariables()
$proc = ProcessBuilder::create()
->setEnv('MY_VAR_1', 'bar')
->add('foo')
;
$proc = $pb->getProcess();
->getProcess();
$this->assertEquals($expected, $proc->getEnv(), '->inheritEnvironmentVariables() copies $_ENV');
unset($_ENV['MY_VAR_1']);
$_ENV = $snapshot;
$env = $proc->getEnv();
$this->assertArrayHasKey('MY_VAR_1', $env);
$this->assertEquals('bar', $env['MY_VAR_1']);
}
/**