Initial commit: apps.supersam24.ru

This commit is contained in:
root committed 2026-10-22 00:04:27 +03:00
commit e955e1da36
6566 files changed
+1271095

No files matched your search

+12
View File
@@ -0,0 +1,12 @@
; This file is for unifying the coding style for different editors and IDEs.
; More information at http://editorconfig.org
root = false
[*]
indent_style = space
indent_size = 4
charset = "utf-8"
end_of_line = lf
insert_final_newline = true
trim_trailing_whitespace = true
+62
View File
@@ -0,0 +1,62 @@
# How to contribute
Dotenv loves to welcome your contributions. There are several ways to help out:
* Create a ticket in GitHub, if you have found a bug
* Write testcases for open bug tickets
* Write patches for open bug/feature tickets, preferably with testcases included
* Contribute to the [documentation](https://github.com/josegonzalez/php-dotenv/tree/gh-pages)
There are a few guidelines that we need contributors to follow so that we have a
chance of keeping on top of things.
## Getting Started
* Make sure you have a [GitHub account](https://github.com/signup/free)
* Submit a ticket for your issue, assuming one does not already exist.
* Clearly describe the issue including steps to reproduce when it is a bug.
* Make sure you fill in the earliest version that you know has the issue.
* Fork the repository on GitHub.
## Making Changes
* Create a topic branch from where you want to base your work.
* This is usually the develop branch
* To quickly create a topic branch based on master; `git branch
master/my_contribution master` then checkout the new branch with `git
checkout master/my_contribution`. Better avoid working directly on the
`master` branch, to avoid conflicts if you pull in updates from origin.
* Make commits of logical units.
* Check for unnecessary whitespace with `git diff --check` before committing.
* Use descriptive commit messages and reference the #ticket number
* Core testcases should continue to pass. You can run tests locally or enable
[travis-ci](https://travis-ci.org/) for your fork, so all tests and codesniffs
will be executed.
## Which branch to base the work
* Bugfix branches will be based on develop branch.
* New features that are backwards compatible will be based on develop branch
* New features or other non-BC changes will go in the next major release branch.
## Submitting Changes
* Push your changes to a topic branch in your fork of the repository.
* Submit a pull request to the repository with the correct target branch.
## Testcases and codesniffer
Dotenv tests requires [PHPUnit](http://www.phpunit.de/manual/current/en/installation.html)
3.5 or higher. To run the testcases locally use the following command:
phpunit --coverage-text
To run the sniffs for PSR2 coding standards
phpcs --standard=psr2 src/
# Additional Resources
* [Bug tracker](https://github.com/josegonzalez/php-dotenv/issues)
* [General GitHub documentation](https://help.github.com/)
* [GitHub pull request documentation](https://help.github.com/send-pull-requests/)
+21
View File
@@ -0,0 +1,21 @@
The MIT License (MIT)
Copyright (c) 2013 Jose Diaz-Gonzalez <email@josediazgonzalez.com>
Permission is hereby granted, free of charge, to any person obtaining a copy
of this software and associated documentation files (the "Software"), to deal
in the Software without restriction, including without limitation the rights
to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
copies of the Software, and to permit persons to whom the Software is
furnished to do so, subject to the following conditions:
The above copyright notice and this permission notice shall be included in
all copies or substantial portions of the Software.
THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
THE SOFTWARE.
+426
View File
@@ -0,0 +1,426 @@
[![Build Status](https://img.shields.io/travis/josegonzalez/php-dotenv/master.svg?branch=master&style=flat-square)](https://travis-ci.org/josegonzalez/php-dotenv)
[![Coverage Status](https://img.shields.io/coveralls/josegonzalez/php-dotenv.svg?branch=master&style=flat-square)](https://coveralls.io/r/josegonzalez/php-dotenv?branch=master)
[![Total Downloads](https://img.shields.io/packagist/dt/josegonzalez/dotenv.svg?style=flat-square)](https://packagist.org/packages/josegonzalez/dotenv)
[![Latest Stable Version](https://img.shields.io/packagist/v/josegonzalez/dotenv.svg?style=flat-square)](https://packagist.org/packages/josegonzalez/dotenv)
# PHP Dotenv
A `.env` file parsing and loading library for PHP.
- [What is it and why should I use it?](#what-is-it-and-why-should-i-use-it)
- [Rules to follow](#rules-to-follow)
- [General Security Information](#general-security-information)
## Requirements
* PHP 5.5+
## Installation
_[Using [Composer](http://getcomposer.org/)]_
Run `composer require josegonzalez/dotenv:dev-master`
Or add the plugin to your project's `composer.json` - something like this:
```javascript
{
"require": {
"josegonzalez/dotenv": "dev-master"
}
}
```
## Usage
Create a new loader:
```php
<?php
$Loader = new josegonzalez\Dotenv\Loader('path/to/.env');
// Parse the .env file
$Loader->parse();
// Send the parsed .env file to the $_ENV variable
$Loader->toEnv();
?>
```
Most methods return the loader directly, so the following is also possible:
```php
<?php
$Loader = (new josegonzalez\Dotenv\Loader('path/to/.env'))
->parse()
->toEnv(); // Throws LogicException if ->parse() is not called first
?>
```
You can use a `.env` file with any of the following features:
```shell
# comments are allowed
FOO=bar # you can also have comments on the end of a line
export BAR=baz # you can optionally begin with an `export` statement
# both single and double quotes are allowed
BAZ='qux'
QUX="quux"
# as are escaped quotes or similar:
QUUX="corge \" grault"
CORGE='garply" waldo'
# unquoted values containing [null, true, false] are turned into
# their PHP equivalents
PHP_NULL=null
PHP_TRUE=true
PHP_FALSE=false
# when quoted, they are simply string values
STRING_NULL="null"
STRING_TRUE="true"
STRING_FALSE="false"
# spaces are allowed as well
# in a slightly more relaxed form from bash
GRAULT =fred
GARPLY = plugh
SPACES=" quote values with spaces" # will contain preceding space
# When using newlines, you should use quoted values
QUOTED_NEWLINE="newline\\nchar"
# you can even have nested variables using `${VAR}` syntax
# remember to define the nested var *before* using it
WALDO=${xyzzy} # not yet defined, so will result in WALDO = `{}`
THUD=${GARPLY} # will be defined as `plugh`
# note that variables beginning with a character
# other than [a-zA-Z_] shall throw a ParseException
01SKIPPED=skipped
# However, numbers *are* allowed elsewhere in the key
NOT_SKIPPED1=not skipped # will have the value `not`
```
> Example `.env` files are available in the [fixtures](https://github.com/josegonzalez/php-dotenv/tree/master/tests/josegonzalez/fixtures) directory.
### Defining Constants
You can also define constants automatically from your env file:
```php
<?php
$Loader = (new josegonzalez\Dotenv\Loader('path/to/.env'))
->parse()
->define(); // Throws LogicException if ->parse() is not called first
?>
```
Already defined constants will result in an immediate `LogicException`.
### Adding to `$_ENV`
```php
<?php
$overwriteENV = true;
$Loader = (new josegonzalez\Dotenv\Loader('path/to/.env'))
->parse()
->toEnv($overwriteENV); // Throws LogicException if ->parse() is not called first
?>
```
Already defined `$_ENV` entries will result in an immediate `LogicException`, unless `$overwriteENV` is set to `true` (default `false`).
### Adding to `$_SERVER`
```php
<?php
$overwriteSERVER = true;
$Loader = (new josegonzalez\Dotenv\Loader('path/to/.env'))
->parse()
->toServer($overwriteSERVER); // Throws LogicException if ->parse() is not called first
?>
```
Already defined `$_SERVER` entries will result in an immediate `LogicException`, unless `$overwriteSERVER` is set to `true` (default `false`).
### Making available to `apache_getenv()`
> This should be preferred over `getenv` when using the Apache web server with `mod_php`.
```php
<?php
$overwrite = true;
$Loader = (new josegonzalez\Dotenv\Loader('path/to/.env'))
->parse()
->apacheSetenv($overwriteAPACHE); // Throws LogicException if ->parse() is not called first
// May throw a PHP Error if either apache_setenv() or apache_putenv() are not available
?>
```
Already defined `apache_getenv()` entries will result in an immediate `LogicException`, unless `$overwriteAPACHE` is set to `true` (default `false`).
### Making available to `getenv()`
```php
<?php
$overwrite = true;
$Loader = (new josegonzalez\Dotenv\Loader('path/to/.env'))
->parse()
->putenv($overwriteENV); // Throws LogicException if ->parse() is not called first
?>
```
Already defined `getenv()` entries will result in an immediate `LogicException`, unless `$overwriteENV` is set to `true` (default `false`).
### Setting key prefixes
```php
<?php
$environment = (new josegonzalez\Dotenv\Loader('path/to/.env'))
->parse()
->prefix('FOO')
->toServer(); // BAR=baz becomes FOOBAR=baz
?>
```
### Return as array
```php
<?php
$environment = (new josegonzalez\Dotenv\Loader('path/to/.env'))
->parse()
->toArray(); // Throws LogicException if ->parse() is not called first
?>
```
### Return as json
```php
<?php
$jsonEnvironment = (string)((new josegonzalez\Dotenv\Loader('path/to/.env'))->parse());
?>
```
### Require environment variables
```php
<?php
$Loader = (new josegonzalez\Dotenv\Loader('path/to/.env'))
->parse()
->expect('FOO', 'BAR', 'BAZ'); // Throws RuntimeException if variables are missing
?>
```
### Turning off exceptions
```php
<?php
$Loader = (new josegonzalez\Dotenv\Loader('path/to/.env'))
->raiseExceptions(false)
->parse()
->expect('FOO', 'BAR', 'BAZ'); // Returns false if variables are missing
?>
```
### Filtering environments
It is possible to optionally filter the environment data produced by php-dotenv through the use of filter classes. A filter class has an `__invoke` method like so:
```php
<?php
class LollipopFilter
{
/**
* Sets every key's value to the string `lollipop`
*
* @param array $environment Array of environment data
* @param array $config Array of configuration data that includes the callable
* @return array
*/
public function __invoke(array $environment, array $config)
{
$newEnvironment = [];
foreach ($environment as $key => $value) {
$newEnvironment[$key] = 'lollipop';
}
return $newEnvironment;
}
}
?>
```
You can attach filters using the `setFilters()` method, which will override all currently specified filters. If an invalid filter is specified, a LogicException will be thrown.
```php
<?php
$Loader = (new josegonzalez\Dotenv\Loader('path/to/.env'))
->setFilters(['LollipopFilter']); // Takes an array of namespaced class names
?>
```
Note that you can optionally set configuration for your filters. These are passed to the `__invoke` method as the second argument.:
```php
<?php
$Loader = (new josegonzalez\Dotenv\Loader('path/to/.env'))
->setFilters([
'LollipopFilter' => ['paintshop'],
]); // Takes an array of namespaced class names
?>
```
Filters can also be callables functions, which is useful in one-off situations. They are wrapped by the special `CallableFilter`.
```php
<?php
$Loader = (new josegonzalez\Dotenv\Loader('path/to/.env'))
->setFilters([function ($data) {
return $data;
}]);
?>
```
If you need special configuration for your callable filters, you can prefix your callable with `__callable__N`, where `N` is the integer index the callable is in your array. The callable itself should be contained in a `callable` config key, as follows:
```php
<?php
$Loader = (new josegonzalez\Dotenv\Loader('path/to/.env'))
->setFilters([
'__callable__0' => [
'callable' => function ($data, $config) {
return $data;
},
'someKey' => 'value',
]
]);
?>
```
Finally, to invoke a filter, you must call `filter()` after calling `parse()`.
```php
<?php
$Loader = (new josegonzalez\Dotenv\Loader('path/to/.env'))
->setFilters(['LollipopFilter'])
->parse()
->filter();
?>
```
#### Available Filters
The following filters are built into php-dotenv.
- `josegonzalez\Dotenv\Filter\CallableFilter`: Wraps a callable and invokes it upon the environment.
- `josegonzalez\Dotenv\Filter\LowercaseKeyFilter`: Lowercases all the keys for an environment to a single-depth.
- `josegonzalez\Dotenv\Filter\NullFilter`: Returns the environment data without any changes.
- `josegonzalez\Dotenv\Filter\RemapKeysFilter`: Remaps specific keys in a `$config` array to a set of values at a single-depth.
- `josegonzalez\Dotenv\Filter\UnderscoreArrayFilter`: Expands a flat array to a nested array. For example, `['0_Foo_Bar' => 'Far']` becomes `[['Foo' => ['Bar' => 'Far']]]`.
- `josegonzalez\Dotenv\Filter\UppercaseFirstKeyFilter`: Uppercases the first letter for all the keys for an environment to a single-depth..
- `josegonzalez\Dotenv\Filter\UrlParseFilter`: When there is a key with the suffix `_URL`, this filter uses `parse_url` to add extra data to the environment.
### Static Environment Definition
You can also call it via the static `load` method call, which takes an array of arguments. If a method name is specified, the method is called with the value in the `$options` array being sent into the method.
```php
<?php
josegonzalez\Dotenv\Loader::load(array(
'filepath' => 'path/to/.env',
'expect' => array('FOO', 'BAR', 'BAZ'),
'toEnv' => true,
'toServer' => true,
'define' => true,
));
?>
```
## Validating External Environments
In some cases it may be necessary to validate that a given array of environment data matches your requirements. You can use the `Loader->expect()` functionality via the standalone `Expect` class:
```php
<?php
use josegonzalez\Dotenv\Expect;
$expect = new Expect($env);
$expect('FOO'); // Raises a RuntimeException if `env` is missing FOO
// You can turn off exception raising using the second `raise` argument
$expect = new Expect($env, false);
$expect('FOO'); // Returns false if `env` is missing FOO
?>
```
## What is it and why should I use it?
When developing and deploying your applications you are typically interacting with various environments - production and development for instance. These environments both execute your code, but will do so using different credentials. You may also wish to distribute your application to developers without accidentally giving them access to important external services.
Simple examples include authentication keys to your email provider or database connection credentials. You would never want to accidentally send testing emails to all your users, or run a `DROP TABLE` statement against production because you ran your unit tests.
How do you tackle these differing credentials? The `php-dotenv` helps solve this issue by allowing you to configure your environments in a universal fashion, making it easy to safely switch between environments, as well as share those environments with multiple projects/languages.
Need more reasons? Check out the [twelve-factor app docs on configuration](http://12factor.net/config).
## Rules to follow
When using `php-dotenv`, you should strive to follow the following rules:
- Add your `.env` file to a gitignore and use a `.env.default` or `.env.example` to set defaults for your projects. This allows your development team to override defaults in a method that works for their local environment.
- Always set sane development defaults for any credential. If necessary, disable features when those credentials are "invalid".
- Where necessary, add comments to credentials with information as to what they are, how they are used, and how one might procure new ones.
- As `php-dotenv` uses more lax procedures for defining environment variables, ensure your `.env` files are compatible with your shell. A good way to test this is to run the following:
```shell
# source in your .env file
source .env
# check the environment
env
```
- Avoid running `php-dotenv` in production settings, and instead set environment variables in your webserver, process manager, or in bash before running your commands. A simple way to ensure this is to check for the existence of a sentinel environment variable that is *only* set in production:
```php
// APP_NAME isn't set in staging/dev
if (!env('APP_NAME')) {
$loader = new josegonzalez\Dotenv\Loader([
__DIR__ '/.env',
__DIR__ '/.env.default'
]);
$loader->parse()->toEnv();
}
```
## General Security Information
If you configure `php-dotenv` to output configuration in any of the ways listed above and then dump them, they may be available to undesired users. For instance, using a project like [filp/whoops](https://github.com/filp/whoops) in conjunction with `$Loader->toServer()` can result in outputting sensitive data to your users if you leave whoops enabled in production.
For this reason, `php-dotenv` never populates data to an environment variable by default and requires that the developer make a conscious decision about how they want to use loaded environment variables
Many error reporting tools have the option of whitelisting or blacklisting sensitive data, and you should familiarize yourself with said tooling.
## License
The MIT License (MIT)
Copyright (c) 2013 Jose Diaz-Gonzalez
Permission is hereby granted, free of charge, to any person obtaining a copy
of this software and associated documentation files (the "Software"), to deal
in the Software without restriction, including without limitation the rights
to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
copies of the Software, and to permit persons to whom the Software is
furnished to do so, subject to the following conditions:
The above copyright notice and this permission notice shall be included in
all copies or substantial portions of the Software.
THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
THE SOFTWARE.
+30
View File
@@ -0,0 +1,30 @@
{
"name": "josegonzalez/dotenv",
"type": "library",
"description": "dotenv file parsing for PHP",
"keywords": ["php", "dotenv", "configuration"],
"homepage": "https://github.com/josegonzalez/php-dotenv",
"license": "MIT",
"authors": [
{
"name": "Jose Diaz-Gonzalez",
"email": "dotenv@josegonzalez.com",
"homepage": "http://josediazgonzalez.com",
"role": "Maintainer"
}
],
"require": {
"php": ">=5.5.0",
"m1/env": "2.*"
},
"require-dev": {
"squizlabs/php_codesniffer": "2.*",
"satooshi/php-coveralls": "1.*",
"php-mock/php-mock-phpunit": "^1.1"
},
"autoload": {
"psr-0": {
"josegonzalez\\Dotenv": ["src", "tests"]
}
}
}
@@ -0,0 +1,56 @@
<?php
namespace josegonzalez\Dotenv;
use LogicException;
use RuntimeException;
class Expect
{
protected $raise = true;
public function __construct($environment, $raise = true)
{
$this->environment = $environment;
$this->raise = $raise;
}
public function __invoke()
{
$args = func_get_args();
if (count($args) == 0) {
return $this->raise('LogicException', 'No arguments were passed to expect()');
}
if (isset($args[0]) && is_array($args[0])) {
$args = $args[0];
}
$keys = (array) $args;
$missingEnvs = array();
foreach ($keys as $key) {
if (!isset($this->environment[$key])) {
$missingEnvs[] = $key;
}
}
if (!empty($missingEnvs)) {
return $this->raise(
'RuntimeException',
sprintf("Required ENV vars missing: ['%s']", implode("', '", $missingEnvs))
);
}
return true;
}
protected function raise($exception, $message)
{
if ($this->raise) {
throw new $exception($message);
}
return false;
}
}
@@ -0,0 +1,19 @@
<?php
namespace josegonzalez\Dotenv\Filter;
class CallableFilter
{
/**
* Wraps a callable and invokes it upon the environment.
*
* @param array $environment Array of environment data
* @param array $config Array of configuration data that includes the callable
* @return array
*/
public function __invoke(array $environment, array $config)
{
$callable = $config['callable'];
return $callable($environment, $config);
}
}
@@ -0,0 +1,21 @@
<?php
namespace josegonzalez\Dotenv\Filter;
class LowercaseKeyFilter
{
/**
* Lowercases all the keys for an environment to a single-depth.
*
* @param array $environment Array of environment data
* @return array
*/
public function __invoke(array $environment)
{
$newEnvironment = array();
foreach ($environment as $key => $value) {
$newEnvironment[strtolower($key)] = $value;
}
return $newEnvironment;
}
}
@@ -0,0 +1,17 @@
<?php
namespace josegonzalez\Dotenv\Filter;
class NullFilter
{
/**
* Returns the environment data without any changes.
*
* @param array $environment Array of environment data
* @return array
*/
public function __invoke(array $environment)
{
return $environment;
}
}
@@ -0,0 +1,24 @@
<?php
namespace josegonzalez\Dotenv\Filter;
class RemapKeysFilter
{
/**
* Remaps specific keys in a $config array to a set of values at a single-depth.
*
* @param array $environment Array of environment data
* @param array $config Array of keys to remap to specific values
* @return array
*/
public function __invoke(array $environment, array $config)
{
foreach ($config as $key => $value) {
if (array_key_exists($key, $environment)) {
$environment[$value] = $environment[$key];
unset($environment[$key]);
}
}
return $environment;
}
}
@@ -0,0 +1,50 @@
<?php
namespace josegonzalez\Dotenv\Filter;
class UnderscoreArrayFilter
{
/**
* Expands a flat array to a nested array.
*
* For example, `['0_Foo_Bar' => 'Far']` becomes
* `[['Foo' => ['Bar' => 'Far']]]`.
*
* @param array $environment Array of environment data
* @return array
*/
public function __invoke(array $environment)
{
$result = array();
foreach ($environment as $flat => $value) {
$keys = explode('_', $flat);
$keys = array_reverse($keys);
$child = array(
$keys[0] => $value
);
array_shift($keys);
foreach ($keys as $k) {
$child = array(
$k => $child
);
}
$stack = array(array($child, &$result));
while (!empty($stack)) {
foreach ($stack as $curKey => &$curMerge) {
foreach ($curMerge[0] as $key => &$val) {
$hasKey = !empty($curMerge[1][$key]);
if ($hasKey && (array)$curMerge[1][$key] === $curMerge[1][$key] && (array)$val === $val) {
$stack[] = array(&$val, &$curMerge[1][$key]);
} else {
$curMerge[1][$key] = $val;
}
}
unset($stack[$curKey]);
}
unset($curMerge);
}
}
return $result;
}
}
@@ -0,0 +1,21 @@
<?php
namespace josegonzalez\Dotenv\Filter;
class UppercaseFirstKeyFilter
{
/**
* Uppercases the first letter for all the keys for an environment to a single-depth.
*
* @param array $environment Array of environment data
* @return array
*/
public function __invoke(array $environment)
{
$newEnvironment = array();
foreach ($environment as $key => $value) {
$newEnvironment[ucfirst($key)] = $value;
}
return $newEnvironment;
}
}
@@ -0,0 +1,43 @@
<?php
namespace josegonzalez\Dotenv\Filter;
class UrlParseFilter
{
/**
* When there is a key with the suffix `_URL`, this filter uses `parse_url`
* to add extra data to the environment.
*
* @param array $environment Array of environment data
* @return array
*/
public function __invoke(array $environment)
{
$newEnvironment = array();
foreach ($environment as $key => $value) {
$newEnvironment[$key] = $value;
if (substr($key, -4) === '_URL') {
$prefix = substr($key, 0, -3);
$url = parse_url($value);
$newEnvironment[$prefix . 'SCHEME'] = $this->get($url, 'scheme', '');
$newEnvironment[$prefix . 'HOST'] = $this->get($url, 'host', '');
$newEnvironment[$prefix . 'PORT'] = $this->get($url, 'port', '');
$newEnvironment[$prefix . 'USER'] = $this->get($url, 'user', '');
$newEnvironment[$prefix . 'PASS'] = $this->get($url, 'pass', '');
$newEnvironment[$prefix . 'PATH'] = $this->get($url, 'path', '');
$newEnvironment[$prefix . 'QUERY'] = $this->get($url, 'query', '');
$newEnvironment[$prefix . 'FRAGMENT'] = $this->get($url, 'fragment', '');
}
}
return $newEnvironment;
}
public function get(array $data, $key, $default = null)
{
if (isset($data[$key])) {
return $data[$key];
}
return $default;
}
}
@@ -0,0 +1,441 @@
<?php
namespace josegonzalez\Dotenv;
use InvalidArgumentException;
use josegonzalez\Dotenv\Expect;
use josegonzalez\Dotenv\Filter\CallableFilter;
use LogicException;
use M1\Env\Parser;
class Loader
{
protected $environment = null;
protected $filepaths = null;
protected $filters = array();
protected $prefix = null;
protected $raise = true;
protected $skip = array(
'apacheSetenv' => false,
'define' => false,
'putenv' => false,
'toEnv' => false,
'toServer' => false,
);
public function __construct($filepaths = null)
{
$this->setFilepaths($filepaths);
return $this;
}
public static function load($options = null)
{
$filepaths = null;
if (is_string($options)) {
$filepaths = $options;
$options = array();
} elseif (isset($options['filepath'])) {
$filepaths = (array)$options['filepath'];
unset($options['filepath']);
} elseif (isset($options['filepaths'])) {
$filepaths = $options['filepaths'];
unset($options['filepaths']);
}
$dotenv = new \josegonzalez\Dotenv\Loader($filepaths);
if (array_key_exists('raiseExceptions', $options)) {
$dotenv->raiseExceptions($options['raiseExceptions']);
}
$dotenv->parse();
if (array_key_exists('filters', $options)) {
$dotenv->setFilters($options['filters']);
$dotenv->filter();
}
$methods = array(
'skipExisting',
'prefix',
'expect',
'apacheSetenv',
'define',
'putenv',
'toEnv',
'toServer',
);
foreach ($methods as $method) {
if (array_key_exists($method, $options)) {
$dotenv->$method($options[$method]);
}
}
return $dotenv;
}
public function filepath()
{
return current($this->filepaths);
}
public function filepaths()
{
return $this->filepaths;
}
public function setFilepath($filepath = null)
{
return $this->setFilepaths($filepath);
}
public function setFilepaths($filepaths = null)
{
if ($filepaths == null) {
$filepaths = array(__DIR__ . DIRECTORY_SEPARATOR . '.env');
}
if (is_string($filepaths)) {
$filepaths = array($filepaths);
}
$this->filepaths = $filepaths;
return $this;
}
public function filters()
{
return $this->filters;
}
public function setFilters(array $filters)
{
$newList = array();
$keys = array_keys($filters);
$count = count($keys);
for ($i = 0; $i < $count; $i++) {
if (is_int($keys[$i])) {
$filter = $filters[$keys[$i]];
if (is_string($filter)) {
$newList[$filter] = null;
} else {
$newList['__callable__' . $i] = array(
'callable' => $filter
);
}
} else {
$newList[$keys[$i]] = $filters[$keys[$i]];
}
}
$this->filters = $newList;
foreach ($this->filters as $filterClass => $config) {
if (substr($filterClass, 0, 12) === '__callable__') {
if (is_callable($config['callable'])) {
continue;
}
return $this->raise(
'LogicException',
sprintf('Invalid filter class')
);
}
if (is_callable($filterClass)) {
continue;
}
if (!class_exists($filterClass)) {
return $this->raise(
'LogicException',
sprintf('Invalid filter class %s', $filterClass)
);
}
continue;
}
return $this;
}
public function filter()
{
$this->requireParse('filter');
$environment = $this->environment;
foreach ($this->filters as $filterClass => $config) {
$filter = $filterClass;
if (is_string($filterClass)) {
if (substr($filterClass, 0, 12) === '__callable__') {
$filter = new CallableFilter;
}
if (class_exists($filterClass)) {
$filter = new $filterClass;
}
}
$environment = $filter($environment, $config);
}
$this->environment = $environment;
return $this;
}
public function parse()
{
$contents = false;
$filepaths = $this->filepaths();
foreach ($filepaths as $i => $filepath) {
$isLast = count($filepaths) - 1 === $i;
if (!file_exists($filepath) && $isLast) {
return $this->raise(
'InvalidArgumentException',
sprintf("Environment file '%s' is not found", $filepath)
);
}
if (is_dir($filepath) && $isLast) {
return $this->raise(
'InvalidArgumentException',
sprintf("Environment file '%s' is a directory. Should be a file", $filepath)
);
}
if ((!is_readable($filepath) || ($contents = file_get_contents($filepath)) === false) && $isLast) {
return $this->raise(
'InvalidArgumentException',
sprintf("Environment file '%s' is not readable", $filepath)
);
}
if ($contents !== false) {
break;
}
}
$parser = new Parser($contents);
$this->environment = $parser->getContent();
return $this;
}
public function expect()
{
$this->requireParse('expect');
$expect = new Expect($this->environment, $this->raise);
call_user_func_array($expect, func_get_args());
return $this;
}
public function apacheSetenv($overwrite = false)
{
$this->requireParse('apache_setenv');
foreach ($this->environment as $key => $value) {
$prefixedKey = $this->prefixed($key);
if (apache_getenv($prefixedKey) !== false && !$overwrite) {
if ($this->skip['apacheSetenv']) {
continue;
}
return $this->raise(
'LogicException',
sprintf('Key "%s" has already been defined in apache_getenv()', $prefixedKey)
);
}
apache_setenv($prefixedKey, $value);
}
return $this;
}
public function define()
{
$this->requireParse('define');
foreach ($this->environment as $key => $value) {
$prefixedKey = $this->prefixed($key);
if (defined($prefixedKey)) {
if ($this->skip['define']) {
continue;
}
return $this->raise(
'LogicException',
sprintf('Key "%s" has already been defined', $prefixedKey)
);
}
define($prefixedKey, $value);
}
return $this;
}
public function putenv($overwrite = false)
{
$this->requireParse('putenv');
foreach ($this->environment as $key => $value) {
$prefixedKey = $this->prefixed($key);
if (getenv($prefixedKey) !== false && !$overwrite) {
if ($this->skip['putenv']) {
continue;
}
return $this->raise(
'LogicException',
sprintf('Key "%s" has already been defined in getenv()', $prefixedKey)
);
}
putenv($prefixedKey . '=' . $value);
}
return $this;
}
public function toEnv($overwrite = false)
{
$this->requireParse('toEnv');
foreach ($this->environment as $key => $value) {
$prefixedKey = $this->prefixed($key);
if (array_key_exists($prefixedKey, $_ENV) && !$overwrite) {
if ($this->skip['toEnv']) {
continue;
}
return $this->raise(
'LogicException',
sprintf('Key "%s" has already been defined in $_ENV', $prefixedKey)
);
}
$_ENV[$prefixedKey] = $value;
}
return $this;
}
public function toServer($overwrite = false)
{
$this->requireParse('toServer');
foreach ($this->environment as $key => $value) {
$prefixedKey = $this->prefixed($key);
if (array_key_exists($prefixedKey, $_SERVER) && !$overwrite) {
if ($this->skip['toServer']) {
continue;
}
return $this->raise(
'LogicException',
sprintf('Key "%s" has already been defined in $_SERVER', $prefixedKey)
);
}
$_SERVER[$prefixedKey] = $value;
}
return $this;
}
public function skipExisting($types = null)
{
$args = func_get_args();
if (isset($args[0]) && is_array($args[0])) {
$args = $args[0];
}
$types = (array)$args;
if (empty($types)) {
$types = array_keys($this->skip);
}
foreach ((array)$types as $type) {
$this->skip[$type] = true;
}
return $this;
}
public function skipped()
{
$skipped = array();
foreach ($this->skip as $key => $value) {
if ($value == true) {
$skipped[] = $key;
}
}
return $skipped;
}
public function prefix($prefix = null)
{
$this->prefix = $prefix;
return $this;
}
public function prefixed($key)
{
if (!!$this->prefix) {
$key = $this->prefix . $key;
}
return $key;
}
public function raiseExceptions($raise = true)
{
$this->raise = $raise;
return $this;
}
public function toArray()
{
$this->requireParse('toArray');
if ($this->environment === null) {
return null;
}
$environment = array();
foreach ($this->environment as $key => $value) {
$environment[$this->prefixed($key)] = $value;
}
return $environment;
}
public function __toString()
{
try {
$data = $this->toArray();
} catch (LogicException $e) {
$data = array();
}
return json_encode($data);
}
protected function requireParse($method)
{
if (!is_array($this->environment)) {
return $this->raise(
'LogicException',
sprintf('Environment must be parsed before calling %s()', $method)
);
}
}
protected function raise($exception, $message)
{
if ($this->raise) {
throw new $exception($message);
}
$this->exceptions[] = new $exception($message);
return false;
}
}