¿Qué se requiere para almacenar para reconocer la máquina de forma segura?
Supongo que quiso decir razonablemente de manera única y confiable, en cuyo caso, este es un problema difícil. Más difícil aún porque cualquier aplicación web no tiene acceso al hardware subyacente, solo información transitoria como la versión del navegador y la dirección IP. Sí, puede obtener mucha información sobre un sistema, por ejemplo, como lo hace panopticlick, pero esa información es variable a pedido.
Además, cualquiera de estas métricas puede cambiar. ¿Usando CPUID? ¿Qué sucede si el usuario final actualiza su procesador? Su estado de "dispositivo de confianza" desaparece. Eso podría ser aceptable o podría no pensar en la activación de Windows.
En cualquier caso, para protegerte contra la intercepción de tokens, MITM, repetición y todos los demás desagradables de este tipo, debes usar SSL para este canal, que me lleva a:
Todavía tendrá que iniciar sesión con contraseña + nombre de usuario, sin embargo, SOLO puede iniciar sesión desde la máquina dada.
Esto suena como un caso de uso para certificados de cliente SSL, en mi opinión. La lógica habitual se ve así:
- Pida al navegador un certificado de cliente.
- Si obtiene uno, verifique ese certificado, busque la base de datos del usuario, etc. e inicie sesión en el usuario.
- De lo contrario, muestra la página de inicio de sesión del usuario.
Creo que lo que estás pidiendo es una variación, en la que si encuentras el certificado, presentas un formulario de inicio de sesión y, de lo contrario, muestras un 403.
Se trata del lado de autenticación de las cosas bastante bien. También alivia la necesidad de almacenar ID de máquinas únicas y todos los problemas para generarlas, aunque puede hacerlo si lo desea, y le permite al usuario designar dispositivos confiables con solo instalar el certificado.
¿Puedo almacenar de forma segura una clave de cifrado (privada) en la máquina, para que el usuario no tenga que ingresarla al cargar datos, etc.?
Bueno, nunca ha tenido ninguna garantía de seguridad del lado del cliente en la web. Simplemente tienes que confiar en que los usuarios están cuidando sus credenciales.
Lo mismo ocurre con las cookies. Recuerde, los usuarios pueden hacer todo tipo de cosas a las cookies, incluso limpiarlas inesperadamente. Si está creando una aplicación web y tiene la intención de hacer criptografía del lado del cliente en JS, y pierde esa clave, el usuario perderá sus datos.
Las alternativas son:
- Encripta los datos en el servidor. Como probablemente haya adivinado, esto significa que cualquier persona con acceso al servidor puede obtener esa información, y ninguna protección que usted proporcione ayudará.
- Cifre los datos en el cliente fuera del navegador, donde el almacenamiento es más confiable. Cuando digo "fuera del navegador", me refiero a través de un mecanismo con un almacenamiento persistente adecuado que no son cookies.
- Espere el cifrado homomórfico.
- Diseñe una forma de extraer la clave de la cookie y asegúrese de que sus usuarios puedan volver a ingresarla nuevamente según sea necesario.
En términos generales, el consejo estándar para las cookies (esto incluye las cookies de su sesión) sobre https es utilizar seguro y httponly marcas para que XSS no funcione y la cookie no se escape.