¿Alguna falla en este modelo de seguridad para un servicio web REST?

9

He diseñado un servicio web REST que requiere autenticación. Maneja la autenticación de manera similar a los servicios web de Amazon, a saber: el usuario tiene un ACCESS_KEY (por ejemplo, 'abcd') y un SECRET_KEY (por ejemplo, 'aabbcc'). El SECRET_KEY se usa para crear un TOKEN : un SHA-1 usando la información de solicitud, por ejemplo:

GET path HTTP/1.1
Date: Mon, 23 May 2005 22:38:34 GMT
ACCESS_KEY: abcd
TOKEN: SHA1(SECRET_KEY + ACCESS_KEY + Date + path)

Puedo verificar el TOKEN en el servidor y autenticar la solicitud. Hasta este punto, no creo que haya ningún problema con el modelo de seguridad.

Mi única pregunta es cómo proporcionar el SECRET_KEY al usar el servicio desde una página web. Pensé que podría enviarlo como una variable de JavaScript (la conexión es HTTPS) y simplemente usar esa variable en una función de JavaScript que agregue el encabezado apropiado a cada HTTPRequest . La autenticación inicial se puede realizar utilizando enfoques estándar basados en cookies (por ejemplo, confiar en Django para manejar una sesión).

Entonces, la arquitectura se ve como:

  • sesión del sitio web: manejada por Django usando seguridad basada en sesión estándar ( example.com )
  • La sesión del sitio web recibe a través de HTTPS el SECRET_KEY como una variable global de JavaScript, que se utiliza para agregar los encabezados adecuados a cada HTTPRequest .
  • Los HTTPRequests están hechos para api.example.com , lo cual es ajeno a la sesión de Django: solo le importa tener los encabezados apropiados.

Creo que este enfoque es seguro, al tiempo que mantiene una API REST completamente sin estado. No uso la autenticación HTTP estándar (básica o compacta) porque no quiero piratear el problema "no se puede cerrar sesión" y quiero mantener la API REST. Estrictamente.

¿Tiene algún comentario con respecto a este enfoque? Si es defectuoso, ¿cómo lograría mis objetivos?

¡Gracias!

    
pregunta Escualo 19.09.2011 - 19:50
fuente

3 respuestas

8

No veo ningún defecto, pero sí creo que te estás excediendo. Me parece que me falta algo, que usas un token porque crees que deberías, no porque haya una razón legítima.

El mejor enfoque sería identificar primero sus requisitos (de seguridad) y luego buscar las soluciones.

Una de las cosas en las que debería pensar con API sin estado es la repetición de ataques. De la forma en que lo describe, su protocolo parece vulnerable a un ataque de repetición. Además, se puede abusar de CSRF ya que no hay aleatoriedad en cada solicitud. No estoy seguro de si esto es algo que la API REST pueda solucionar, porque es un problema inherente de la aplicación web, pero vale la pena pensarlo.

En pocas palabras, nadie puede evaluar si su seguridad está bien si no tiene requisitos de seguridad (y un panorama de amenazas).

    
respondido por el Henri 19.09.2011 - 20:47
fuente
6

Creo que deberías quedarte con https. Si se generan partes importantes en el javascript del lado del cliente (por ejemplo, el sha1 del token), ¿qué tan difícil sería para un ataque MITM, donde un atacante lleva a las personas a una versión falsa de su sitio, donde el javascript está alterado para revelar ¿La clave secreta para el servidor? (Por ejemplo, alterar el DNS y falsificar el sitio en un punto de acceso wifi público).

¿También quién está generando la fecha (cliente o servidor)? ¿Por cuánto tiempo es válida una ficha? ¿Un token generado / validado hace dos minutos sigue siendo válido? ¿Podría un MITM interceptar un token válido para realizar una solicitud específica y reproducirla (y hacer algo malicioso mediante la reproducción)?

    
respondido por el dr jimbob 19.09.2011 - 21:59
fuente
1

¿Puede confirmar que hay un caso de uso siguiente para su servicio web RESTful

  1. Solicitud de envío de otros servicios / aplicaciones a su servicio. No es necesario mantener el estado de sesión
  2. Solicitud de los navegadores.

Para el primer caso de uso, creo que su enfoque es bueno. Puedes considerar los siguientes cambios para hacerlo aún mejor 1. Use SHA256 en lugar de SHA1 (dicen que SHA1 no se considera demasiado fuerte hoy en día) 2. Asegúrese de que todas las claves secretas emitidas sigan las reglas de complejidad apropiadas

Espero que solo estés hablando del modelo de autenticación aquí y no de otras cosas. Si también está hablando de otras cosas, SSL debería estar en su lista de prioridades (por varias razones).

Para el segundo caso de usuario, las recomendaciones diferirían dependiendo de si realmente desea mantener un estado de sesión (no realmente REST;)) o bien con una solicitud individual no relacionada desde el navegador

Puedo intentar dar algunas sugerencias basadas en el caso de uso (sesión o no sesión)

    
respondido por el Sachin Kumar 21.09.2011 - 13:11
fuente

Lea otras preguntas en las etiquetas