-
-
Notifications
You must be signed in to change notification settings - Fork 9.6k
[Dotenv] add a flag to allow env vars override #26859
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
Conversation
@@ -35,6 +35,12 @@ | |||
private $end; | |||
private $state; | |||
private $values; | |||
private $enableOverride; | |||
|
|||
public function __construct(bool $enableOverride = false) |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Maybe a docblock specifying what the parameter is for.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
docblock added.
@@ -73,7 +79,7 @@ public function populate(array $values): void | |||
foreach ($values as $name => $value) { | |||
$notHttpName = 0 !== strpos($name, 'HTTP_'); | |||
// don't check existence with getenv() because of thread safety issues | |||
if (!isset($loadedVars[$name]) && (isset($_ENV[$name]) || (isset($_SERVER[$name]) && $notHttpName))) { | |||
if (!isset($loadedVars[$name]) && ((!$this->enableOverride && isset($_ENV[$name])) || (isset($_SERVER[$name]) && $notHttpName))) { |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Shouldn't this be used for all isset
checks?
if (!isset($loadedVars[$name]) && (!$this->enableOverride && (isset($_ENV[$name]) || (isset($_SERVER[$name]) && $notHttpName)))) {
Additionally, I prefer an explicit === false
check for readability, but I'm not sure what the convention is.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
For security reasons I think it's better to not allow overriding $_SERVER['HTTP_*']
values, a previous discussion took place before the creation of this component. Maybe a core team member can confirm this later.
About CS style, there are plenty of examples in the codebase (and in this file too) where shortcut is used. Personaly I think it's very strange to explicitly test a false value against a boolean return type :)
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
The !$notHttpName
already fulfills the stop condition to not overwrite the http server vars. So I think it's safe to include your check on the $_SERVER
?
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Updated
Status: Needs Review |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Not sure that this will make it to 4.1, as it's a feature freeze, unless it can be made as an exception ?
@@ -73,7 +79,7 @@ public function populate(array $values): void | |||
foreach ($values as $name => $value) { | |||
$notHttpName = 0 !== strpos($name, 'HTTP_'); | |||
// don't check existence with getenv() because of thread safety issues | |||
if (!isset($loadedVars[$name]) && (isset($_ENV[$name]) || (isset($_SERVER[$name]) && $notHttpName))) { | |||
if (!isset($loadedVars[$name]) && ((!$this->enableOverride && isset($_ENV[$name])) || (isset($_SERVER[$name]) && $notHttpName))) { |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
The !$notHttpName
already fulfills the stop condition to not overwrite the http server vars. So I think it's safe to include your check on the $_SERVER
?
$dotenv = new DotEnv(true); | ||
$dotenv->populate(array('TEST_ENV_VAR_OVERRIDEN' => 'new_value')); | ||
|
||
$this->assertSame('new_value', getenv('TEST_ENV_VAR_OVERRIDEN')); |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Add some asserts for the _ENV
, _SERVER
vars too ?
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Asserts added.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Don't you want to test they're getting properly overridden from $_SERVER
and $_ENV
?
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
@@ -1,6 +1,11 @@ | |||
CHANGELOG | |||
========= | |||
|
|||
4.1.0 |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
should be 4.2.0 now
private $enableOverride; | ||
|
||
/** | ||
* @param bool $enableOverride true if you want to allow env vars overriding |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I'd propose to remove this comment and name the option $overrideExistingVars
(default false) instead.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
That would be a BC break Nevermind, I see the name change switches the functionality. That change would of course require a logic change as well, but I’m for it 👍
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Why so? That's adding an optional argument on the constructor, which doesn't break BC usually.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Already edited 😀
@nicolas-grekas rebased & comments addressed. |
I was looking for how did other similar libraries solved this:
The most popular option seems to be to define two methods called |
Lets' add |
I would also prefer to add another method. |
I added Tests failed are unrelated. |
*/ | ||
public function populate(array $values): void | ||
public function populate(array $values, bool $overrideExistingVars = false): void |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
This should be reverted IMHO: it makes no sense to provide two public interfaces to do the same thing.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I agree but I think the same thing of populate()
method, I don't know why it is public because the purpose of Dotenv
is to use a file, no directly an array of vars it's so low level IMHO. So I added here to be consistent but let me know if you have no doubt about this revert, I can do it :)
Thank you @fmata. |
This PR was merged into the 4.2-dev branch. Discussion ---------- [Dotenv] add a flag to allow env vars override | Q | A | ------------- | --- | Branch? | master | Bug fix? | no | New feature? | yes | BC breaks? | no | Deprecations? | no | Tests pass? | yes | Fixed tickets | #26846 | License | MIT | Doc PR | symfony/symfony-docs#9568 I choose to use a new parameter in the constructor instead of `populate()` to not add boilerplate code to them who want allow overriding in their current setup. It's just a parameter to add in `Dotenv` creation instead of change or customize the loading of different .env files. I targeted 4.1 despite the feature freeze because it's a small change but if you don't agree I can change to 4.2. ~~If you accept this PR I will do the doc PR then.~~ doc ready Commits ------- 228b220 [Dotenv] add Dotenv::overload() to allow env vars override
if (!is_readable($path) || is_dir($path)) { | ||
throw new PathException($path); | ||
} | ||
$this->doLoad(false, $path, ...$paths); |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
instead of creating a PHP array (with the variadic argument) to spread it again (here) to create another PHP array (variadic argument in the private method), it might make sense to pass an array to the private method instead of making it variadic.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Indeed, we don't need a variadic argument in the private method.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
…luz) This PR was merged into the master branch. Discussion ---------- Document the DotEnv::overload() method I'm not sure how to update the doc according my PR symfony/symfony#26859 which is pending review but feel free to comment if I did a mistake. Thank you. Commits ------- 38e4f08 Reword f8a3c0d Update dotenv.rst 6325759 Update dotenv.rst c8ad296 Update dotenv.rst
…() (fmata) This PR was merged into the 4.2-dev branch. Discussion ---------- [Dotenv] use array instead of variadic in Dotenv::doLoad() | Q | A | ------------- | --- | Branch? | master | Bug fix? | no | New feature? | no | BC breaks? | no | Deprecations? | no | Tests pass? | yes | Fixed tickets | n/a | License | MIT According to comments done after merge in #26859. Commits ------- f3af242 [Dotenv] use array instead of variadic in Dotenv::doLoad()
I choose to use a new parameter in the constructor instead of
populate()
to not add boilerplate code to them who want allow overriding in their current setup. It's just a parameter to add inDotenv
creation instead of change or customize the loading of different .env files.I targeted 4.1 despite the feature freeze because it's a small change but if you don't agree I can change to 4.2.
If you accept this PR I will do the doc PR then.doc ready