2010-10-29 16 views
60

Digamos por ejemplo que tenía una aplicación que envía las siguientes cabeceras HTTP para establecer a cookie llamada "a":¿Cómo manejar múltiples cookies con el mismo nombre?

Set-Cookie: a=1;Path=/;Version=1 
Set-Cookie: a=2;Path=/example;Version=1 

Si accedo /example en el servidor de ambos caminos son válidos, así que tengo dos galletas llamadas "una "¡! Como el navegador no envía información de ruta, las dos cookies no se pueden distinguir.

Cookie: a=2; a=1 

¿Cómo se debe manejar este caso? Elija el primero? Crear una lista con todos los valores de cookies? ¿O debería considerarse un caso como un error del desarrollador?

+0

Haré todo lo posible (léase: todo lo que pueda) para evitar nombres duplicados de cookies. La mayoría de la gente nunca se ha encontrado con este problema, por una buena razón. –

Respuesta

31

De this article on SitePoint:

Si varias cookies del mismo nombre que coincida con una petición URI dado, uno es elegido por el navegador.

Cuanto más específica sea la ruta, mayor será la precedencia. Sin embargo, la precedencia basada en otros atributos, incluido el dominio, no está especificada, y puede variar entre los navegadores. Esto significa que si ha configurado las cookies del mismo nombre contra ".example.org" y "www.example.org", no puede estar seguro de cuál será devuelto.

Editar: esta información a partir de 2010 está superada, parece navegadores ahora pueden enviar varias cookies a cambio, véase la respuesta por @Nate abajo para más detalles

+6

Entonces, ¿cómo se pueden eliminar las múltiples cookies idénticas? He trabajado duro durante dos días y las cookies duplicadas parecen indestructibles. –

+9

@Brant Ese artículo puede ser ligeramente incorrecto: acabo de ver que Chrome envía dos cookies del mismo nombre (pero con diferentes rutas), por lo que "uno es elegido por el navegador" no es necesariamente cierto. La cookie de ruta más profunda se envió primero, por cierto, lo cual parece razonable. Y otra galleta lo hizo en el medio, también. –

+0

Oops, quise decir @Jan, supongo. –

-1

Si necesita distinguirlos, debe asignarles valores de clave diferentes.

0

Estoy seguro de que conozco las aplicaciones que hacen esto de forma extensiva utilizando múltiples identificadores de sesión, y parecen funcionar de manera consistente. Sin embargo, no sé, y no tengo intención de averiguarlo, si lo hacen porque el navegador devuelve las cookies en un orden coherente, dependiendo de cuándo se establecieron, de qué ruta se establecieron o si la aplicación intenta hacer coincidir cada una. uno a una sesión existente.

Recomiendo encarecidamente que se evite esta práctica.

Sin embargo, si realmente desea saber cómo los navegadores (y las aplicaciones) manejan este escenario, ¿por qué no construir un equipo de prueba y probarlo?

+2

Un servidor no tiene control sobre lo que le envía el navegador. Aún necesita ser manejado. –

0

No hay nada malo en tener múltiples valores para el el mismo nombre ... si los quieres. Incluso podría incluir un contexto adicional en el valor.

Si no lo hace, por supuesto, diferentes nombres son una solución si desea ambos contextos.

La alternativa es enviar el mismo nombre de cookie con la misma ruta (y dominio) incluso desde las rutas más específicas. Esas instrucciones de cookies configuradas sobrescribirán el valor de esa cookie.

Ahora que conoce la parte más importante (cómo funcionan) y que puede lograr lo que necesita de diferentes maneras, mi respuesta a su pregunta es: este es un problema del desarrollador.

59

La respuesta referente a un artículo sobre SitePoint no está del todo completa. Consulte RFC 6265 (para ser justos, este RFC se publicó en 2011 después de que se publicó esta pregunta, que sustituye a los anteriores RFC 2965 de 2000 y RFC 2109 de 1997).

Sección 5.4, inciso 2 tiene esto que decir:

El agente de usuario debería ordenar la galleta-lista en el siguiente orden:

  • Galletas con trayectorias más largas se enumeran antes de galletas con caminos más cortos.

NOTA: No todos los agentes de usuario ordenar la cookie de lista en este orden, pero este orden refleja la práctica común cuando este documento fue escrito, y, servidores históricamente, ha habido que (erróneamente) dependían de este orden.

También existe esta pequeña joya en la sección 4.2.2:

... Los servidores no debe confiar en el orden de serialización. En en particular, si el encabezado Cookie contiene dos cookies con el mismo nombre (por ejemplo, que se establecieron con diferentes atributos de ruta o de dominio), los servidores NO DEBEN depender del orden en que aparecen estas cookies en el encabezado.

En su ejemplo solicitud cookie (Cookie: a = 2; a = 1) tenga en cuenta que la cookie establece con el camino /ejemplo (a = 2) tiene una trayectoria más larga que la con la ruta / (a = 1), por lo que se le enviará primero en línea, lo que coincide con la recomendación de la especificación. Por lo tanto, usted es más o menos correcto al suponer que podría seleccionar el primer valor.

Por desgracia, el lenguaje utilizado en los RFC es muy específica - el uso de las palabras DEBE y NO DEBE generar una ambigüedad en el RFC. Estos indican convenciones que deben seguir, pero no son requeridas para cumplir con la especificación. Si bien entiendo bastante bien el RFC para esto, no he hecho la investigación para ver qué hacen los clientes del mundo real; es posible que uno o más navegadores u otros softwares que actúen como clientes HTTP no puedan enviar la cookie de ruta más larga (p. ej .: /ejemplo) primero en el encabezado Cookie:.

Si está en condiciones de controlar el valor de la cookie y usted desea hacer su infalible solución, que es el mejor de ambos:

  1. utilizando un nombre de cookie distinta para anular en ciertos caminos, tales como:

    • Set-cookie: a-mundial = 1; Path = /; versión = 1
    • Set-cookie: a-ejemplo = 2; Path =/ejemplo; versión = 1
  2. almacenar la ruta de acceso que necesita en el valor de la cookie en sí:

    • Set-Cookie: a = 1 & path = /; Path = /; versión = 1
    • Set-Cookie: a = 2 & path =/ejemplo; Path =/ejemplo, versión = 1

dos de estas soluciones requieren una lógica adicional en el servidor para escoger el valor de la cookie deseada, mediante la comparación de la URL solicitada con la lista de cookies disponibles . No es muy bonito. Es desafortunado que el RFC no tuvo la previsión de exigir que una ruta más larga anule por completo una cookie con una ruta más corta (por ejemplo: en su ejemplo, recibiría Cookie: a = 2solamente).

+1

¡Gracias por sacar esto de estos malditos RFC! // ¿por qué molestarse en leerlos si nadie sigue estas recomendaciones? ... – Rast

+3

Parece que Wildfly 8.0 está prestando atención al orden de las cookies y usa la primera. Esto nos permite ejecutar otra aplicación en un contexto 'anidado'. Sin embargo, fallaría si algunos navegadores no siguen la recomendación de RFC. La forma correcta de hacerlo es establecer un nombre diferente para la cookie de sesión, como JSESSIONID2. – honzajde

+0

Probé los navegadores más importantes después de leer su respuesta: Chrome 63/Opera 55/IE11/Edge 16/Safari 11/Firefox 58 Y parece que todos manejan correctamente que las cookies con una ruta más larga se encuentran antes que la ruta más corta. Y en PHP (probado en la versión 7) solo lee la primera cookie que está configurada en la variable $ _COOKIE. –

Cuestiones relacionadas