Slim 2.x 到 3.x 升级 - configureMode 和 getInstance 替换

Slim 2.x to 3.x upgrade - configureMode and getInstance replacement

我正在努力将 Slim 2.x 升级到 3.x 以修复安全问题。目前在 Slim 2 中,我们使用 configureMode 来存储环境特定的数据库连接。 3.0 升级指南只说 configureMode 已被删除,但没有告诉您应该使用什么。我从未在 PHP 以及我团队中的其他任何人(遗留产品)工作过。

在我的 .htaccess 文件中,我们正在设置环境

SetEnv SLIM_MODE development

在我的 index.php 中,目前我们使用 configureMode 来设置数据库属性

$app->configureMode('development', function () use ($app) {
    $app->config(array(
        'masterDB' => array(
            'dbhost' => 'DEVDB',
            'dbuser' => 'USER',
            'dbpass' => 'PASS',
            'dbname' => 'MASTER'
        ),
        'userDB' => array(
            'dbuser' => 'USER',
            'dbpass' => 'PASS'
        ),
        'debug' => false
    ));
});

/**
 * QA configuration
 */ 
$app->configureMode('qa', function () use ($app) {
    $app->config(array(
        'masterDB' => array(
            'dbhost' => 'DEVDB',
            'dbuser' => 'USER',
            'dbpass' => 'PASS',
            'dbname' => 'MASTER'
        ),
        'userDB' => array(
            'dbuser' => 'USER',
            'dbpass' => 'PASS'
        ),
        'debug' => false
    ));
});

为了访问这些值,我们正在使用也已删除的 getInstance。

$app = \Slim\Slim::getInstance();

教程只是说这些已被删除,我不确定如何替换。 Slim 3.x 能否像我们目前使用的那样支持环境配置,或者现在是否需要在安装到该环境中时进行设置?

现在设置和访问这些值的正确方法是什么?

我使用 Slim 3 已经有几年了,我确信没有 "official" 如何配置环境特定设置的方法。但是我想告诉你我是怎么做到的。

首先在您的项目根目录中创建目录config/

然后将所有配置文件放入此 config/ 目录。

  1. 创建文件:config/defaults.php

该文件包含所有环境的所有默认设置。

<?php
//
// Configure defaults for the whole application.
//
// Error reporting
error_reporting(0);
ini_set('display_errors', '0');

// Timezone
date_default_timezone_set('Europe/Berlin');

// Slim settings
$settings = [
    'httpVersion' => '1.1',
    'responseChunkSize' => 4096,
    'outputBuffering' => 'append',
    'determineRouteBeforeAppMiddleware' => true,
    'displayErrorDetails' => false,
    'addContentLengthHeader' => true,
    'routerCacheFile' => false,
];

Full example

  1. 然后创建开发环境的配置文件:config/development.php
<?php

//
// Development environment
//
$settings['env'] = 'development';

// Error reporting
error_reporting(E_ALL);
ini_set('display_errors', '1');

// Display all errors
$settings['displayErrorDetails'] = true;

$settings['db']['host'] = '{{db_host}}';
$settings['db']['database'] = '{{db_database}}';

integration.phpstaging.phpproduction.php 重复此步骤。

  1. 然后创建一个文件env.php来定义有效环境。

注意:请不要将此文件提交给 git。

<?php
/**
 * Environment specific application configuration.
 *
 * You should store all secret information (username, password, token) here.
 *
 * Make sure the env.php file is added to your .gitignore
 * so it is not checked-in the code
 *
 * Place the env.php _outside_ the project root directory, to protect against
 * overwriting at deployment.
 *
 * This usage ensures that no sensitive passwords or API keys will
 * ever be in the version control history so there is less risk of
 * a security breach, and production values will never have to be
 * shared with all project collaborators.
 */
require __DIR__ . '/development.php';

// Database
$settings['db']['username'] = '{{db_username}}';
$settings['db']['password'] = '{{db_password}}';

// SMTP
$settings['smtp']['username'] = 'user@example.com';
$settings['smtp']['password'] = '';
  1. 然后创建一个合并所有其他配置文件的文件config/settings.php
<?php

// Defaults
require __DIR__ . '/defaults.php';

// Load environment configuration
if (file_exists(__DIR__ . '/../../env.php')) {
    require __DIR__ . '/../../env.php';
} elseif (file_exists(__DIR__ . '/env.php')) {
    require __DIR__ . '/env.php';
}

if (defined('APP_ENV')) {
    require __DIR__ . '/' . APP_ENV . '.php';
}

return $settings;

用法

在您的 config/bootstrap.php 中,您可以加载所有设置并将该配置传递给 Slim App 实例:

// Instantiate the app
$app = new \Slim\App(['settings' => require __DIR__ . '/../config/settings.php']);

// Set up dependencies

// Register middleware

// Register routes

$app->run();

你问的实际上是一个与框架无关的问题。有像 vlucas/phpdotenv 这样的库可以帮助您进行特定于环境的设置。如果您不想使用这样的库,您可以使用一种简单的机制来覆盖配置设置,就像@odan 建议的解决方案一样,但在我看来它可能更简单一些。这是我之前实际使用的解决方案:

  1. 将您的默认常用设置放在一个数组中。您可以选择将其放入文件
  2. 在每个环境中,创建一个文件(同名),仅包含该环境的设置
  3. 合并这两个数组,以特定于环境的键覆盖默认设置中的相同键的方式。这些文件应该有

默认设置(settings.default.php):

<?php
return array(
    'cache-driver' => 'redis',
    'debug' => false,
);

环境设置(env.php):

<?php
return array(
    'debug' => true,
    'userDB' => array(
         'dbuser' => 'env-db-user',
         'dbpass' => 'env-db-pass'
     ), 
);

如果 env.php 存在,合并来自两个文件的数组,可能在 index.phpapp.php:

<?php
$defaultSettings = require 'settings.default.php';
$environmentSettings = file_exists('env.php') ? require 'env.php' : array();

$settings = array_merge($defaultSettings, $environmentSettings);
$app = new App($settings);

现在print_r($settings)将输出:

Array
(
    [cache-driver] => redis
    [debug] => 1
    [userDB] => Array
        (
            [dbuser] => env-db-user
            [dbpass] => env-db-pass
        )

)

如您所见,cache-driver值来自默认设置,debug被覆盖,userDB仅在此环境下可用。这意味着您可以为不同的环境设置不同的设置数组,这使您可以控制依赖于这些值的对象的行为。