Skip to content

Commit 61504b1

Browse files
committed
Allow configure Magento with env
- add coverage by unit test
1 parent 09a6147 commit 61504b1

File tree

2 files changed

+67
-9
lines changed

2 files changed

+67
-9
lines changed

lib/internal/Magento/Framework/App/DeploymentConfig.php

Lines changed: 17 additions & 9 deletions
Original file line numberDiff line numberDiff line change
@@ -20,7 +20,8 @@
2020
class DeploymentConfig
2121
{
2222
private const MAGENTO_ENV_PREFIX = 'MAGENTO_DC_';
23-
private const ENV_NAME_PATTERN = '~^%env\(\s*(?<name>\w+)\s*(,\s*"(?<default>[^"]+)")?\)%$~';
23+
private const ENV_NAME_PATTERN = '~^#env\(\s*(?<name>\w+)\s*(,\s*"(?<default>[^"]+)")?\)$~';
24+
private const OVERRIDE_KEY = self::MAGENTO_ENV_PREFIX . '_OVERRIDE';
2425

2526
/**
2627
* Configuration reader
@@ -151,7 +152,7 @@ public function isDbAvailable()
151152
*/
152153
private function getEnvOverride() : array
153154
{
154-
$env = getenv(self::MAGENTO_ENV_PREFIX . '_OVERRIDE');
155+
$env = getenv(self::OVERRIDE_KEY);
155156
return !empty($env) ? (json_decode($env, true) ?? []) : [];
156157
}
157158

@@ -172,6 +173,19 @@ private function load()
172173
);
173174
// flatten data for config retrieval using get()
174175
$this->flatData = $this->flattenParams($this->data);
176+
177+
// allow reading values from env variables by convention
178+
// MAGENTO_DC_{path}, like db/connection/default/host =>
179+
// can be overwritten by MAGENTO_DC_DB__CONNECTION__DEFAULT__HOST
180+
foreach (getenv() as $key => $value) {
181+
if (false !== \strpos($key, self::MAGENTO_ENV_PREFIX)
182+
&& $key !== self::OVERRIDE_KEY
183+
) {
184+
// convert MAGENTO_DC_DB__CONNECTION__DEFAULT__HOST into db/connection/default/host
185+
$flatKey = strtolower(str_replace([self::MAGENTO_ENV_PREFIX, '__'], ['', '/'], $key));
186+
$this->flatData[$flatKey] = $value;
187+
}
188+
}
175189
}
176190
}
177191

@@ -210,17 +224,11 @@ private function flattenParams(array $params, $path = null, array &$flattenResul
210224
} else {
211225
// allow reading values from env variables
212226
// value need to be specified in %env(NAME, "default value")% format
213-
// like %env(DB_PASSWORD)%, %env(DB_NAME, "test")%
227+
// like #env(DB_PASSWORD), #env(DB_NAME, "test")
214228
if (preg_match(self::ENV_NAME_PATTERN, $param, $matches)) {
215229
$param = getenv($matches['name']) ?: ($matches['default'] ?? null);
216230
}
217231

218-
// allow reading values from env variables by convention
219-
// MAGENTO_DC_{path}, like db/connection/default/host =>
220-
// can be overwritten by MAGENTO_DC_DB__CONNECTION__DEFAULT__HOST
221-
$envName = self::MAGENTO_ENV_PREFIX . strtoupper(str_replace(['/'], ['__'], $newPath));
222-
$param = getenv($envName) ?: $param;
223-
224232
$flattenResult[$newPath] = $param;
225233
}
226234
}

lib/internal/Magento/Framework/App/Test/Unit/DeploymentConfigTest.php

Lines changed: 50 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -147,6 +147,16 @@ public function testKeyCollision(array $data): void
147147
$object->get();
148148
}
149149

150+
protected function tearDown(): void
151+
{
152+
foreach (array_keys(getenv()) as $key) {
153+
if (false !== \strpos($key, 'MAGENTO_DC')) {
154+
putenv($key);
155+
}
156+
}
157+
parent::tearDown();
158+
}
159+
150160
/**
151161
* @return array
152162
*/
@@ -178,4 +188,44 @@ public function testIsDbAvailable(): void
178188
$this->_deploymentConfig->resetData();
179189
$this->assertTrue($this->_deploymentConfig->isDbAvailable());
180190
}
191+
192+
public function testNoEnvVariables()
193+
{
194+
$this->reader->expects($this->once())->method('load')->willReturn(['a'=>'b']);
195+
$this->assertSame('b', $this->_deploymentConfig->get('a'));
196+
}
197+
198+
public function testEnvVariables()
199+
{
200+
$this->reader->expects($this->once())->method('load')->willReturn([]);
201+
putenv('MAGENTO_DC__OVERRIDE={"a": "c"}');
202+
$this->assertSame('c', $this->_deploymentConfig->get('a'));
203+
}
204+
205+
public function testEnvVariablesWithNoBaseConfig()
206+
{
207+
$this->reader->expects($this->once())->method('load')->willReturn(['a'=>'b']);
208+
putenv('MAGENTO_DC_A=c');
209+
putenv('MAGENTO_DC_B__B__B=D');
210+
$this->assertSame('c', $this->_deploymentConfig->get('a'));
211+
$this->assertSame('D', $this->_deploymentConfig->get('b/b/b'));
212+
}
213+
214+
public function testEnvVariablesSubstitution()
215+
{
216+
$this->reader->expects($this->once())
217+
->method('load')
218+
->willReturn(
219+
[
220+
'a'=>'#env(MAGENTO_DC____A)',
221+
'b'=>'#env(MAGENTO_DC____B, "test")',
222+
'c'=>'#env(MAGENTO_DC____D, "e$%^&")'
223+
]
224+
);
225+
putenv('MAGENTO_DC____A=c');
226+
putenv('MAGENTO_DC____B=D');
227+
$this->assertSame('c', $this->_deploymentConfig->get('a'));
228+
$this->assertSame('D', $this->_deploymentConfig->get('b'), 'return value from env');
229+
$this->assertSame('e$%^&', $this->_deploymentConfig->get('c'), 'return default value');
230+
}
181231
}

0 commit comments

Comments
 (0)