2008-09-16 12 views
24

Una cosa que he empezado a hacer más a menudo recientemente es recuperar algunos datos al comienzo de una tarea y almacenándola en a $ _SESSION ['myDataForTheTask'].

Ahora parece muy conveniente hacerlo, pero no sé nada sobre el rendimiento, los riesgos de seguridad o similares, utilizando este enfoque. ¿Es algo que regularmente hacen los programadores con más experiencia o es más una cosa de aficionados que hacer?

Por ejemplo:

if (!isset($_SESSION['dataentry'])) 
{ 
    $query_taskinfo = "SELECT participationcode, modulearray, wavenum FROM mng_wave WHERE wave_id=" . mysql_real_escape_string($_GET['wave_id']); 
    $result_taskinfo = $db->query($query_taskinfo); 
    $row_taskinfo = $result_taskinfo->fetch_row(); 

     $dataentry = array("pcode" => $row_taskinfo[0], "modules" => $row_taskinfo[1], "data_id" => 0, "wavenum" => $row_taskinfo[2], "prequest" => FALSE, "highlight" => array()); 

     $_SESSION['dataentry'] = $dataentry; 
} 
+3

Su consulta SQL es vulnerable a ataques de inyección SQL. Por ejemplo, alguien podría poner '? Wave_id = wave_id' y la consulta seleccionaría todas las filas. (Es peor con las solicitudes DELETE, INSERTAR y ACTUALIZAR). En este caso, debe escribir el código para asegurarse de que sea un número, y la forma más fácil de hacerlo es intval() –

Respuesta

16

Las variables de sesión de pozo son realmente una de las únicas formas (y probablemente las más eficientes) de tener estas variables disponibles durante todo el tiempo que el visitante está en el sitio web, no hay manera real de que el usuario las edite (que no sea un exploit en tu código, o en el intérprete de PHP) por lo que son bastante seguros.

Es una buena manera de almacenar configuraciones que pueden ser modificadas por el usuario, ya que puede leer la configuración de la base de datos una vez al comienzo de una sesión y está disponible para esa sesión completa, solo necesita hacer más base de datos Llama si se cambian las configuraciones y, por supuesto, como se muestra en el código, es trivial averiguar si las configuraciones ya existen o si se deben extraer de la base de datos.

No puedo pensar en ninguna otra forma de almacenar de forma segura variables temporales (ya que las cookies pueden ser modificados fácilmente y esto va a ser indeseable en la mayoría de los casos) por lo que $ _SESSION sería el camino a seguir

+3

"son bastante seguros" solo es cierto si es un servidor dedicado. en alojamiento compartido, otros usuarios en la misma máquina pueden acceder a los datos de la sesión php. – Jacco

+0

No si elige almacenar sus datos de sesión en algún lugar que no sea el predeterminado. O cuando usa un mecanismo de almacenamiento de sesión diferente, como DB o (su propia) memcache privada. –

1

$ _SESSION artículos se almacenan en la sesión, que es, por defecto, se mantuvo en el disco. No es necesario hacer su propia matriz y rellenarla en una entrada de matriz de 'entrada de datos' como lo hizo. Solo puede usar $ _SESSION ['pcode'], $ _SESSION ['modules'], etc.

Como dije, la sesión se almacena en el disco y un puntero a la sesión se almacena en una cookie. Por lo tanto, el usuario no puede obtener fácilmente los datos de la sesión.

+1

Solo use una matriz multidimensional $ _SESSION [' mystuff '] [' mydata '] =' blah '; – conmulligan

+0

@conmulligan: Claro, pero nada va a estar en la sesión excepto lo que pongas allí. Puede confundir $ _SESSION con $ _SERVER. – nsayer

0

Utilizo este enfoque un poco, no veo ningún problema con él. A diferencia de las cookies, los datos no se almacenan en el lado del cliente, lo que a menudo es un gran error.

Sin embargo, como todo, tenga cuidado de que siempre esté desinfectando la entrada del usuario, especialmente si está ingresando datos del usuario en la variable $ _SESSION y luego usando esa variable en una consulta SQL.

3

Hay algunos factores que debe tener en cuenta al decidir dónde almacenar los datos temporales. El almacenamiento de la sesión es ideal para datos específicos de un solo usuario. Si encuentra que el controlador predeterminado de almacenamiento de sesión basado en archivos es ineficiente, puede implementar algo más, posiblemente utilizando una base de datos o un tipo de servidor de Memcache. Ver session_set_save_handler para más información.

Encuentro que es una mala práctica almacenar datos comunes en la sesión de un usuario. Hay mejores lugares para almacenar datos a los que muchos usuarios accederán con frecuencia y, al almacenar estos datos en la sesión, se duplicarán los datos para cada usuario que necesite estos datos. En su ejemplo, puede configurar un tipo diferente de motor de almacenamiento para esta información de onda (basada en wave_id) que NO está vinculada específicamente a la sesión de un usuario. De esta forma, extraerá los datos una vez y los almacenará en algún lugar para que varios usuarios puedan acceder a los datos sin necesidad de otra extracción.

1

IMO, es perfectamente aceptable para almacenar cosas en la sesión. Es una excelente forma de hacer que los datos sean persistentes. También es, en muchos casos, más seguro que almacenar todo en las cookies. Aquí hay algunas inquietudes:

  • Es posible que alguien pueda secuestrar una sesión, por lo que si va a utilizarla para realizar un seguimiento de la autorización del usuario, tenga cuidado. Lea this para obtener más información.
  • Puede ser una forma muy perezosa de guardar datos. No solo arroje todo en la sesión para que no tenga que consultarla más tarde.
  • Si va a almacenar objetos en la sesión, sus archivos de clase deberán incluirse antes de que la sesión se inicie en la próxima solicitud o tendrá que haber configurado un cargador automático.
2

Si está ejecutando en su propio servidor, o en un entorno donde nadie puede husmear en sus archivos/memoria en el servidor, los datos de la sesión son seguros. Se almacenan en el servidor y solo se envía una cookie de identificación al cliente. El problema es si otras personas pueden arrebatar la cookie y hacerse pasar por otra persona, por supuesto. Usar HTTPS y asegurarse de no colocar la ID de la sesión en las URL debe mantener a los usuarios a salvo de la mayoría de esos problemas. (XSS aún puede ser utilizado para robar cookies si no tiene cuidado, vea también Jeef Atwoods post on this)

En cuanto a qué almacenar en una variable de sesión, coloque sus datos allí si desea consultarlos nuevamente en otra página , como una cesta de la compra, pero no lo coloque allí si se trata de datos temporales utilizados para producir el resultado de esta página, como una lista de etiquetas para la publicación que se visualiza actualmente. Las sesiones son para datos persistentes por usuario.

0

Esto es algo bastante común de hacer, y la sesión generalmente será más rápida que las visitas continuas a la base de datos. También son razonablemente seguros, ya que los desarrolladores de PHP han trabajado arduamente para evitar el secuestro de sesiones.

El único problema es que debe recordar reconstruir la entrada de sesión cuando algo cambia. Y, si un usuario que no sea el dueño de la sesión cambia algo y resulta en la necesidad de actualizar esta clave, no hay una forma fácil de notificar al sistema para actualizar esta clave de sesión. Posiblemente no sea gran cosa, pero algo de lo que debes estar consciente.

4

Utilizo la variable de sesión todo el tiempo para almacenar información para los usuarios. No he visto ningún problema con el rendimiento. Los datos de la sesión se basan en la cookie (o PHPSESSID si tiene las cookies desactivadas). No veo que sea más un riesgo de seguridad que cualquier otra autenticación basada en cookies, y probablemente sea más seguro que almacenar los datos reales en la cookie de los usuarios.

Sólo para hacerle saber, sin embargo, usted tiene un problema de seguridad con la instrucción SQL:

SELECT participationcode, modulearray, wavenum FROM mng_wave WHERE wave_id=".$_GET['wave_id']; 

Debe NUNCA, repito NUNCA, tomar datos de usuario proporcionadas y lo utilizan para ejecutar un SQL declaración sin primero desinfectarla. Me gustaría envolverlo entre comillas y agregar la función mysql_real_escape_string(). Eso lo protegerá de la mayoría de los ataques. Por lo que su línea se vería así:

$query_taskinfo = "SELECT participationcode, modulearray, wavenum FROM mng_wave WHERE wave_id='".mysql_real_escape_string($_GET['wave_id'])."'"; 
+0

gracias! este desbordamiento de stak me hace aprender a un ritmo increíble, estoy sorprendido. – markus

1

Zend Framework tiene una biblioteca útil para la gestión de datos de sesión que ayuda con la caducidad y la seguridad (para cosas como captchas). También tienen una explicación útil de las sesiones. Consulte http://framework.zend.com/manual/en/zend.session.html

2

Otra forma de mejorar la validación de entrada es a emitir el _GET [ 'wave_id'] Variable:

wave_id
$query_taskinfo = "SELECT participationcode, modulearray, wavenum FROM mng_wave WHERE wave_id=".(int)$_GET['wave_id']." LIMIT 1"; 

estoy suponiendo es un entero, y que no hay una sola respuesta.

Will

+0

sí, exactamente. ¡gracias por la pista! – markus

1

he encontrado sesiones a ser muy útil, pero algunas cosas a tener en cuenta:

1) que PHP puede almacenar sus sesiones en una carpeta tmp u otro directorio que puede ser accesible a otra usuarios en tu servidor. Puede cambiar el directorio donde se almacenan las sesiones yendo al archivo php.ini.

2) Si está configurando un sistema de alto valor que necesita una seguridad muy estrecha, es posible que desee encriptar los datos antes de enviarlos a la sesión y descifrarlos para usarlos. Nota: esto podría generar demasiada sobrecarga dependiendo de la capacidad de tráfico/servidor.

3) He encontrado que session_destroy(); no elimina la sesión de inmediato, aún tiene que esperar que el recolector de elementos no utilizados de PHP limpie las sesiones. Puede cambiar la frecuencia con la que se ejecuta el recolector de elementos no utilizados en el archivo php.ini. Pero todavía no parece muy confiable, más información http://www.captain.at/howto-php-sessions.php

5

$ _SESSION mecanismo está utilizando cookies.

En caso de Firefox (y tal vez nuevo IE, no comprobé yo mismo) que significa que sesión se comparte entre las pestañas abiertas. Eso no es algo que esperas por defecto. Y significa que la sesión ya no es "algo específico para una sola ventana/usuario".

Por ejemplo, si ha abierto dos pestañas para acceder a su sitio, luego de haber iniciado sesión como raíz usando la primera pestaña, obtendrá privilegios de administrador en la otra.

Eso es realmente inconveniente, especialmente si codifica el cliente de correo electrónico u otra cosa (como e-shop). En este caso, deberá administrar las sesiones manualmente o introducir una clave regenerada constantemente en la URL o hacer otra cosa.

1

¿Le gustaría considerar qué tan REST-ful es esto?

es decir, consulte "Comunicación statelessly" en el apartado "A Brief Introduction to REST" ...

"mandatos descanso que el estado sea bien se convirtió en el estado del recurso, o mantenerse en el cliente. En otras palabras, un servidor no debería tener que retener algún tipo de estado de comunicación para ninguno de los clientes con los que se comunica más allá de una solicitud única ".

(o cualquiera de los otros enlaces en Wikipedia para REST)

Así, en su caso, la 'wave_id' es un recurso sensata de conseguir, pero es lo que realmente desea almacenar en la sesión?Seguramente memcached es su solución para almacenar en caché el objeto Recurso?

1

Algunas otras desventajas del uso de sesiones:

  1. $_SESSION datos expirará después de session.gc_maxlifetime segundos de inactividad.
  2. Deberá recordar llamar al session_start() para cada secuencia de comandos que utilizará los datos de la sesión.
  3. Escalar el sitio web mediante el equilibrio de carga en varios servidores podría ser un problema porque el usuario deberá dirigirse al mismo servidor cada vez. Resuelve esto con "Sesiones adhesivas".
0

$ _SESSION es muy útil en la seguridad, ya que es una forma del lado del servidor para almacenar información mientras el usuario está activamente en sus páginas, por lo tanto, difícil de piratear a menos que su archivo php real o servidor tiene debilidades que son explotados. Una muy buena implementación es almacenar una variable para confirmar que el usuario ha iniciado sesión, y solo permite tomar acciones si se confirma que inició sesión.

Cuestiones relacionadas