Pregunta ¿Es posible activar un error cuando se accede $ _POST u otro superglobal?


Tengo este tipo de proyecto marco en el backburner donde quiero aplicar el uso de un Input clase para acceder a todos los superglobales como $_POST, $_GET y $_SERVER. UN pregunta reciente Aquí me lo recordó.

La clase hará un poco. limpieza de las llaves para asegurarse de que no hay nada malicioso o inesperado, y proporcionar una forma de acceder a los elementos sin la molestia de usar isset() cada vez. Puede hacer otras cosas dependiendo de la configuración, y posiblemente también eliminará las superglobales. Tampoco me gusta el hecho de que Los superglobales no son de solo lectura, Quiero forzar la integridad en los valores. Quiero que esta clase se use exclusivamente y quiero advertir a los desarrolladores cuando no se usa.

Mi pregunta es esta, y me temo que la respuesta es "No":

Es posible desencadenar un error ¿Cuando se accede a una de las superglobales? Por ejemplo:

$myvar = $_POST['key'];
// Prints "Error: POST cannot be accessed directly, use the Input class instead"

¿O al escribir a superglobales ?:

$_POST['key'] = 'myvalue';
// Prints "Error: POST data cannot be modified"

5
2017-10-18 12:27


origen


Respuestas:


Puedes usar ArrayAccess

Ejemplo 1 :

$_POST = new SUPER($_POST);
$_POST['hello'] = "Hello World"; // This would trigger error ;

Ejemplo 2: a.php?var=1&var2=2

$_GET = new SUPER($_GET);
echo $_GET['var'] ; // returns 1
echo $_GET['var2'] ; // returns 2

$_GET['var3'] = 2 ; //return error

Clase utilizada

class SUPER implements \ArrayAccess {
    private $request = array();

    public function __construct(array $array) {
        $this->request = $array;
    }

    public function setRequest(array $array) {
        $this->request = $array;
    }

    public function offsetSet($offset, $value) {
        trigger_error("Error: SUPER GLOBAL data cannot be modified");
    }

    public function offsetExists($offset) {
        return isset($this->request[$offset]);
    }

    public function offsetUnset($offset) {
        unset($this->request[$offset]);
    }

    public function offsetGet($offset) {
        return isset($this->request[$offset]) ? $this->request[$offset] : null;
    }
}

6
2017-10-18 13:03



¿Qué hay de asignar un objeto a la variable $ _POST y usar métodos mágicos?

$ _POST = new% your-class% ();


6
2017-10-18 12:41



No activa nada más que un aviso, pero si primero copia todas las claves / valores de superglobales dentro de un objeto y luego hace:

unset($_GET,$_POST,$_SERVER);

después de eso, cualquier acceso de lectura a esos superglobales simplemente fallará. Para prohibir la escritura, puede instanciar un objeto de su elección sobre estas variables (es decir, con el nombre $ _GET, $ _POST, $ _SERVER). Para mantenerlos accesibles a través del operador de matriz [$ key], deben ser instancias de objetos que implementan el ArrayAccess interfaz.


2
2017-10-18 12:45



Esto es básicamente lo que @Baba ya mostró, pero he estado usando un envoltorio de entrada similar para algunos proyectos. Es muy adecuado para pequeños proyectos, pero debo admitir que todavía tengo que superar la resistencia al uso. Sin embargo, simplifica la desinfección y la auditoría.

http://sourceforge.net/p/php7framework/svn/66/tree/trunk/php7/input.php?force=True
http://sourceforge.net/p/php7framework/wiki/input/

los ArrayAccess enfoque es todo lo que necesitas. Para evitar la inyección de entrada en tiempo de ejecución o sobrescribir offsetSet es suficiente. Aunque solo estoy imprimiendo avisos, pero aún así lo permito.

Básicamente es para desinfectar sin embargo. Cualquier acceso en bruto, por ejemplo, $_REQUEST["key"] pasará por un filtro predeterminado, por ejemplo, pero también puede simplemente invocar varias cadenas de filtros en tiempo de ejecución:

 print $_POST->html->text["comment"];

Últimamente he estado permitiendo un trabajo restringido de register_globals, localizando múltiples variables a la vez. Con la sintaxis PHP 5.4 se ve bastante divertido:

 extract( $_REQUEST->list->text[[ title, id, email ]] );
 // implicit undef-constant notices here ^^ of course

Si acaba de envolver $ _GET, $ _POST, $ _REQUEST al inicio, ya ha logrado su objetivo. El único inconveniente sintáctico es que ya no se puede usar empty($_POST), todos los otros accesos de matriz sin procesar todavía están permitidos por tales envoltorios.


1
2017-10-18 20:54



Preguntas populares