practicas - pasar variables por url php post
¿Cuál es la mejor manera de guardar variables de configuración en una aplicación web PHP? (11)
A menudo cambio entre el desarrollo de .NET y PHP. Con los sitios ASP.NET, guardo información de configuración (por ejemplo, cadenas de conexión, directorios, configuración de la aplicación) en el archivo web.config , que está adecuadamente protegido y es fácil de acceder a los valores, etc.
En PHP , resuelvo esto con una clase que tiene métodos estáticos para cada variable:
class webconfig {
public static function defaultPageIdCode() {
return ''welcome'';
}
}
El archivo está incluido por las variables de la aplicación se accede con una línea:
$dp = webconfig::defaultPageIdCode();
Y dado que PHP no está compilado, es fácil hacer telnet y cambiar el valor de un sitio web de todos modos, por lo que esta solución funciona bastante bien y me ofrece estas dos ventajas :
- Puedo agregar lógica a una variable de configuración sin romper su interfaz con la aplicación
- estas variables de configuración aparecen como intellisense en mi ejemplo, Eclipse, NetBeans, etc.
Pero me puedo imaginar que hay otras maneras en que las personas resuelven guardar configuraciones de configuración web en PHP que pueden tener otras ventajas.
Especialmente aquellos que tienen experiencia con varios frameworks de PHP, ¿qué otras formas de guardar variables de configuración y sus ventajas y desventajas?
Como PHP puede usar OO, me gusta ir con una "clase de configuración":
class Config
{
/**
* ---------------------------------
* Database - Access
* ---------------------------------
*/
/**
* @var String
*/
const DB_DRIVER = ''pgsql'';
const DB_USER = ''postgres'';
const DB_PASSWORD = ''postgres'';
const DB_NAME = ''postgres'';
}
Es de fácil acceso con Config :: DB_DRIVER. No es necesario incluir el archivo, ya que el autocargador de la aplicación lo hará por usted. Por supuesto, aún se necesita proteger el archivo.
Creo que hay muchas posibilidades, pero los métodos más comunes son almacenar como texto sin formato en archivos como .csv, .ini, .xml. Con pequeños trucos puede proteger estos archivos, de modo que nadie pueda cargar los archivos directamente.
un ejemplo de INI-File:
;<?php die(); ?>
[config1]
var1 = ''value1'';
var2 = ''value2'';
...
[config2]
...
El ;
se considera un comentario en archivos ini. Entonces, cuando lea el archivo con un analizador interno, esta línea será ignorada. Si alguien accede al archivo directamente a través de url, se ejecutará la función de die()
. Esto solo funciona si el archivo INI usa una extensión de archivo como .php para que el servidor sepa que esto debe ejecutarse y no mostrarse como texto sin formato.
La posible desventaja de la mayoría de los almacenamientos de configuración de base de archivos son los problemas con algunos caracteres utf8.
Zend_Config es un componente de Zend-Framework, que ofrece posibilidades para varios adaptadores de almacenamiento con una API fácil de usar.
En PHP siempre uso un ".htaccess" para proteger mi archivo de configuración (doble protección)
Hay pocas posibilidades:
Puede usar el archivo de configuración (ini, json, xml o yaml). Para ini tienes
parse_ini_file
, para JSON hayjson_decode
(+ file_get_contents), para YAML tienes que usar la biblioteca externa (buscar sfYaml)Puede tener un archivo de configuración con variables o constantes (mejor para configuración inmutable y accesible en todos los ámbitos), que incluye en su secuencia de comandos:
define (''ROOT_DIR'', ''/ home / www'');
$ sRootDir = ''/ home / www'';
Si está orientado a OO, puede envolverlo en clase, como propiedades; no tiene el método getter para cada propiedad, solo puede tener:
class Config
{
public $var1 = ''xxx'';
public $var2 = ''yyy'';
}
($ c = nueva Config (); print $ c-> var1)
o
static class Config
{
public static $var1 = ''xxx'';
public static $var2 = ''yyy'';
}
(imprimir c :: $ var1)
Lo mejor es tener una clase de tipo registro, implementar un patrón singleton y poder leer la configuración desde el archivo dado.
He decidido enumerar todos los métodos conocidos junto con sus ventajas y desventajas.
He marcado esta respuesta como una wiki comunitaria para que la colaboración sea más fácil.
Constantes globales
Asignando:
-
define(''CONFIG_DIRECTIVE'', ''value'');
Accediendo a:
-
$object = new MyObject(CONFIG_DIRECTIVE);
Ventajas:
- Tiene alcance global.
- Autocompletado por la mayoría de los IDEs.
- Tiene una convención de nombres acordada (UPPERCASE_UNDERSCORE_SEPARATED) .
Desventajas:
- Las directivas no pueden contener matrices (anteriores a v7.0.0).
Notas especiales:
- No se puede reasignar
Archivos de sintaxis alternativos
Por ejemplo: XML, INI, YAML, etc.
Asignando:
- Simplemente edite el archivo en su idioma específico. (Por ejemplo, para archivos INI:
config_directive = value
.)
Accediendo a:
- El archivo de configuración necesita ser analizado. (Por ejemplo, para INI:
parse_ini_file()
)
Ventajas:
- Lo más probable es que tenga una sintaxis más adecuada para un archivo de configuración.
Desventajas:
- Posible sobrecarga de acceso y análisis del archivo.
Formación
Asignando:
-
$config[''directive''] = ''value'';
Accediendo a:
- El método más limpio para acceder a los valores de configuración con este método es pasar los valores requeridos al objeto que los necesita en la creación, o pasarlos a su objeto contenedor y dejar que se encargue de distribuirlos internamente.
-
$object = new MyObject($config[''directive'']);
-
$container = new MyContainer($config);
-
Ventajas:
- Las directivas pueden ser matrices.
Desventajas:
- Sin autocompletar
Notas especiales:
- Colisiones variables pueden ocurrir Si esto es una preocupación, nombre su matriz de manera apropiada para evitarlos.
Clase
Asignando:
- Hay muchas implementaciones basadas en clases diferentes.
- Clase estática
-
myCfgObj::setDirective(''DIRECTIVE'', ''value'');
-
- Clase instanciada.
-
myCfgObj->setDirective(''DIRECTIVE'', ''value'');
-
- Clase estática
Accediendo a:
- De nuevo, hay varias implementaciones basadas en clases.
- Clase estática
-
$object = new MyObject(myCfgObj::getDirective(''DIRECTIVE''));
-
- Clase instanciada.
-
$object = new MyObject(myCfgObj->getDirective(''DIRECTIVE''));
-
- Clase estática
Ventajas:
- Se puede cargar automáticamente.
Desventajas:
- Tiende a ser un poco detallado.
- Puede ser difícil de mantener si no se usa una clase de contenedor.
La forma en que lo hago es almacenarlos directamente en una array
y guardar el archivo como config.php
<?php
$config[''dbname''] = "mydatabase";
$config[''WebsiteName''] = "Fundoo Site";
$config[''credits''] = true;
$config[''version''] = "4.0.4";
?>
Thi es la forma en que la mayoría de los frameworks PHP como Wordpress, etc. lo hacen.
La ruta habitual es usar define
:
define(''MYSQL_USER'', ''ROOT'');
y acceder a ella a través de la aplicación a través de MYSQL_USER
:
$user = MYSQL_USER;
Sin embargo, las matrices no son compatibles de esta manera.
Para poder probarlo, utilizo una clase Config
que contiene los datos de configuración reales y una clase estática de AppConfig
que contiene una referencia a un objeto de Config
cargado en el arranque de archivos de configuración de toda la aplicación (dependencia inyectada en el arranque). En el entorno de pruebas, solo cambio el objeto Config
. Ver https://github.com/xprt64/Config
Telnet? ¡OMG, he caído en un timewarp y llegué en 1992!
Pero en serio, IIRC hay herramientas que permiten que asp.net (y otros lenguajes) analicen los datos de la sesión, que es solo una matriz php serializada. Me gustaría implementar la configuración global como una especie de sesión paralela dentro de PHP. Incluso si no almacena sus configuraciones de configuración como una matriz PHP serializada, podría mapearlas en la sesión en tiempo de ejecución utilizando su propio manejador de sesión.
En términos de dónde almacena los datos, es más complicado cuando presumiblemente se ejecuta en una plataforma de Microsoft. Obviamente, no desea el gasto de acceso al disco para cada solicitud. Aunque NT hace algo de caché de disco, no es (IME) tan efectivo como otros sistemas operativos. Memcached parece ser una solución para esto. Parece ser utilizable desde asp.net.
HTH
Tiendo a usar una clase estática de Configuración en PHP, esto es porque
- Tiene un alcance global.
- Puede habilitar / deshabilitar los cambios a las configuraciones protegidas.
- Puede agregar cualquier configuración durante cualquier parte dentro del tiempo de ejecución.
- Puede automatizar la clase para buscar configuraciones públicas desde un archivo / base de datos.
Ejemplo:
abstract class Settings
{
static private $protected = array(); // For DB / passwords etc
static private $public = array(); // For all public strings such as meta stuff for site
public static function getProtected($key)
{
return isset(self::$protected[$key]) ? self::$protected[$key] : false;
}
public static function getPublic($key)
{
return isset(self::$public[$key]) ? self::$public[$key] : false;
}
public static function setProtected($key,$value)
{
self::$protected[$key] = $value;
}
public static function setPublic($key,$value)
{
self::$public[$key] = $value;
}
public function __get($key)
{//$this->key // returns public->key
return isset(self::$public[$key]) ? self::$public[$key] : false;
}
public function __isset($key)
{
return isset(self::$public[$key]);
}
}
Luego, dentro de su tiempo de ejecución, si cargó este archivo primero, seguido de su archivo de configuración de base de datos, su archivo de configuración de base de datos se vería así:
<?php
Settings::setProtected(''db_hostname'', ''localhost'');
Settings::setProtected(''db_username'', ''root'');
Settings::setProtected(''db_password'', '''');
Settings::setProtected(''db_database'', ''root'');
Settings::setProtected(''db_charset'', ''UTF-8'');
//...
echo Settings::getProtected(''db_hostname''); // localhost
//...
Settings::setPublic(''config_site_title'', ''MySiteTitle'');
Settings::setPublic(''config_site_charset'', ''UTF-8'');
Settings::setPublic(''config_site_root'', ''http://localhost/dev/'');
Como puede ver, tenemos un método __get
que solo debería permitir tomar variables públicas. Un ejemplo de por qué tenemos esto es el siguiente:
$template = new Template();
$template->assign(''settings'', new Settings());
Independientemente del hecho de que hayamos utilizado este objeto como un objeto estático, los valores deberían permanecer así dentro de la plantilla que ahora puede hacer, digamos.
<html>
<head>
<?php echo isset($settings->config_site_title) ? $settings->config_site_title : ''Fallback Title''; ?>
</head>
</html>
Y esto solo le permitirá tener acceso a los datos públicos durante el período inicializado.
Esto puede ser mucho más complejo pero más amigable con el sistema, algunos ejemplos:
- Un método
loadConfig
para analizar automáticamente un archivo de configuración, xml, php, yaml. - Si registra una función
shutdown_function
, puede actualizar automáticamente la base de datos con una nueva configuración. - Puede completar automáticamente la clase con config desde esa base de datos.
- Puede implementar iteradores para hacerlo compatible con el bucle.
- Mucho más.
Esto también es, de lejos, los mejores métodos para completar este trabajo.
Nota: "La mejor manera" nunca existe. Cada aplicación y marco lo hacen a su propio estilo. Mientras que su ejemplo está haciendo el truco, creo que es un poco pesado en recursos para un archivo de configuración simple.
- Puedes hacerlo con variables individuales como Amber señaló
- Puedes hacerlo con arreglos este es el enfoque más común y siempre puedes editar fácilmente tu archivo de configuración.
- Puedes hacerlo con archivos .ini que PHP analiza fácilmente
Editar:
Edward, por favor eche un vistazo a los ejemplos de parse_ini_file. Puede cargar el archivo .ini con un comando simple y luego puede usar las variables en una clase como en su ejemplo.