Хранение конфигурации PHP - PullRequest
10 голосов
/ 08 мая 2011

Способы хранения конфигурации для веб-приложения, написанного на PHP?
Я видел, как люди используют .ini, basic .php и т. Д.
Также define() или простые глобальные переменные?
Большая часть информации, которую вы можете найти.
Кроме того, являются ли базы данных хорошими методами хранения конфигурации?

Ответы [ 7 ]

16 голосов
/ 08 мая 2011

Нет & ldquo; Best Way (tm) & rdquo; хранить настройки вашего приложения. На самом деле все зависит от вашего приложения, типа конфигураций, как часто они могут / должны меняться, и как легко вы хотите сделать так, чтобы они менялись.

Некоторые люди используют полный одноэлементный (или статический) класс Config для своего приложения. Который выглядит примерно так (с разным уровнем сложности):

<?php

class Config
{

    protected static $config = array();

    private function __construct() {} // make this private so we can't instanciate

    public static function set($key, $val)
    {
        self::$config[$key] = $val;
    }

    public static function get($key)
    {
        return self::$config[$key];
    }

}

Это удобно, потому что вы можете вызывать его в любом месте приложения с помощью Config::set() или Config::get(). Тогда у вас будет центральное место, в котором сконфигурировано все ваше приложение, и вы можете сделать его настолько сложным или простым, насколько вам нравится. Вы можете создавать резервные копии в базе данных, memcached и т. Д., Что угодно.

Что подводит меня к следующему. Использование базы данных хорошо для вещей, которые нужно менять на лету, и не обязательно иметь & ldquo; начальную настройку & rdquo ;. Примером могут быть функции настройки приложения сайта (например, валюта, цвет фона, изображение заголовка и т. Д.). Проблема здесь в том, что вы должны загружать ее каждый раз, когда в ваше приложение загружается страница. Чтобы решить эту проблему, вы можете использовать технологию кэширования среднего уровня (например, memcached, если хотите). Это было бы быстро, намного быстрее, чем база данных, но все равно добавляет накладные расходы, потому что вам нужно загружать его при каждой загрузке страницы.

Самый быстрый способ, а следовательно, & ldquo; самый сложный & rdquo; изменить, это использовать файл config.php или тому подобное. Этот файл будет иметь $_GLOBALS определения ключей массива или define() для значений, к которым вам нужен доступ во всем приложении. Это быстро, потому что он включен в запрос и жестко запрограммирован в PHP, поэтому все, что PHP должен сделать, это интерпретировать файл - никаких сетевых операций ввода-вывода или каких-либо дополнительных затрат, кроме минимальных затрат на включение файла в ваш скрипт. Вещи, которые вы храните в этих файлах PHP, такие как учетные данные подключения MySQL, учетные данные подключения к веб-службам и т. Д.

Для приложения, в котором много пользователей и много настроек, вам, вероятно, потребуется развернуть «гибрид». методов или придумать свой. Для чего-то, что является просто стандартным развертыванием приложения, вы можете обойтись без очень простого подхода типа config.php.

5 голосов
/ 08 мая 2011

Я не думаю, что есть лучший способ, каждый метод имеет свои преимущества и недостатки. Просто убедитесь, что файл конфигурации (особенно если он содержит пароли) недоступен в общедоступном каталоге, но где-то в частном порядке.

Сохранение конфигурации в базе данных может работать, но вам все равно нужно где-то хранить информацию о соединении с базой данных, чтобы получить соединение. Лично я никогда не был поклонником этого метода. Единственным преимуществом будет простое изменение значений элементов конфигурации в режиме онлайн или, например, конфигурация на уровне пользователя.

Использование define(); создаст константы, из которых вы не можете изменить значение во время выполнения. В некоторых случаях это работает, в других - нет. Если вы хотите, чтобы ваша конфигурация была доступна везде - во всех областях - вы можете рассмотреть возможность считывания конфигурации в класс (может быть, шаблон Singleton?), Чтобы вы могли получить доступ к значениям конфигурации везде.

Я использовал включенный php-файл, .ini-файлы, XML-файлы и JSON-файлы для конфигурации, лично я предпочитаю избегать .php-файлов конфигурации, так как я делюсь своими файлами конфигурации на нескольких языках для разных приложений в моих веб-приложениях. и придерживайтесь других «стандартов».

3 голосов
/ 08 января 2014

Как на самом деле @Roger Ng указал, принятый ответ на самом деле не работает. Проблема в том, что вы не можете использовать $this в статическом методе.
PHP: статическое ключевое слово - руководство

Я думал об этом следующим образом:

class Config {
    protected static $config=array();
    private function __construct(){}
    public static function set($k,$v){
            self::$config[$k]=$v;
    }
    public static function get($k){
            return self::$config[$k];
    }
    public static function init($a){
            self::$config=$a;
    }
    public static function merge($a){
            self::$config=array_merge(self::$config,$a);
    }
}

Я использую функцию Config::init(), чтобы создать конфигурацию по умолчанию для возврата, и функцию Config::merge(), чтобы объединить конфигурации по умолчанию, например, с производственными значениями.

Так что здесь мой default_config.php может выглядеть следующим образом:

Config::init(array(
    'key' => 'value',
    'key2' => 'value2',
));

И мой config.php примерно такой:

Config::merge(array(
    'key' => 'newvalue',
    'key3' => 'value3',
));

В реальном коде я получу свои значения конфигурации точно так, как это сделано в принятом ответе, написав Config::get('key').

3 голосов
/ 08 мая 2011

.ini - плохой способ хранения конфигов, так как веб-сервер будет отображать их для всех.Не делайте этого.

Храните конфиги в .php файле.Вы можете использовать глобальные переменные, define () или обычные переменные.Определить, как правило, лучше всего.Для большей безопасности разместите его вне общедоступного каталога.

Обычно я размещаю настройки базы данных в config.php, а все динамические настройки - в базе данных.Все настройки, которые не сильно меняются, обычно хорошо помещать в конфигурационный файл.Как дорожки и т. Д.

1 голос
/ 18 января 2016

IMO, сегодня наиболее целесообразно хранить данные конфигурации в файле JSON.

Некоторые преимущества JSON:

  • встроенная поддержка во многих языках программирования
  • легко читается для людей
  • легко читается для машин
  • маленький файл

Пример кода:

Файл JSON:

{
    "version" : "0.0.1",
    "title" : "My first web app",
    "database" : {
        "host" : "localhost",
        "name" : "DB",
        "user" : "JJ",
        "password" : "Passw0rd"
    }
}

Класс PHP:

namespace App;

class Config {

    protected static $config = array();

    public static function load($filename) {
        static::$config = json_decode(file_get_contents($filename), true);
    }

    [...]
}

Загрузка файла Json:

\App\Config::load('myConfigFile.json');
0 голосов
/ 08 ноября 2017

Я подправил код Джеймса и Заху.Вот моя реализация.Когда значение ищется и если существует, оно возвращается, в противном случае возвращается пустая строкаТаким образом, никакие уведомления не будут показаны.Есть метод удаления.комментарии и форматирование кода.

<?php
/*
 * This file can be used to store config values. It is based on discussion below.
 * @see /5115207/hranenie-konfiguratsii-php
 * @author https://stackoverflow.com/users/2632129/james
 * @author https://stackoverflow.com/users/3173125/zachu
 * @author Slavi Marinov | http://orbisius.com
 */
class App_Config {
    protected static $config = array();

    /**
     * Do not instantiate this class
     */
    private function __construct() {}

    /**
     * Initializes or resets the config if nothing is supplied
     * App_Config::init();
     * @param array $a
     */
    public static function init($a = array()) {
        self::$config = $a;
    }

    /**
     * App_Config::get();
     * @param str $k
     * @return mixed
     */
    public static function get($k) {
        return empty(self::$config[$k]) ? '' : self::$config[$k];
    }

    /**
     * Sets a value
     * App_Config::set();
     * @param str $k
     * @param mixed $v
     */
    public static function set($k, $v) {
        self::$config[$k] = $v;
    }

    /**
     * Removes a key
     * App_Config::remove();
     * @param str $k
     * @param mixed $v
     */
    public static function remove($k) {
        unset(self::$config[$k]);
    }

    /**
     * Removes a key
     * App_Config::delete();
     * @param str $k
     * @param mixed $v
     */
    public static function delete($k) {
        self::remove($k);
    }

    /**
     * App_Config::exists();
     * @param str $k
     * @return bool
     */
    public static function exists($k) {
        return isset(self::$config[$k]) ? true : false;
    }

    /**
     * App_Config::merge();
     * @param str $k
     * @return array
     */
    public static function merge($a) {
        self::$config = array_merge(self::$config, $a);
        return self::$config;
    }
}
0 голосов
/ 11 марта 2014

Это то, что я делаю.

Сначала я определяю общий класс Dataset, который я могу использовать для глобального хранения данных:

<?php

namespace MyNamespace\Core;

class Dataset {

    protected static $_data = array();

    public static function set($key, $value) {
        static::$_data[$key] = $value;
    }

    public static function get($key) {
        return static::$_data[$key];
    }

    public static function remove($key) {
        unset(static::$_data[$key]);
    }
}
?>

Затем я определяю Config Класс, который расширяет это, где я могу добавить методы, специфичные для этого класса.

<?php

namespace MyNamespace\Core;

class Config extends Factory {

    protected static $_data = array();

}
?>

Обратите внимание, что важно добавить правило protected static $_data = array(); в класс Config или любые другие дочерние классы, если вы не используетене хочу, чтобы они использовали один и тот же массив.

...