Comment faire une authentification sans état (sans session) et sans cookie?

Bob utilise une application Web pour réaliser quelque chose. Et:

  • Son navigateur est au régime, donc il ne supporte pas les cookies .
  • L’application Web est très répandue, elle s’adresse à un grand nombre d’utilisateurs à un moment donné – elle doit bien évoluer . Tant que garder la session imposerait une limite au nombre de connexions simultanées et, bien sûr, apporterait une pénalité de performance non négligeable, nous aimerions peut-être avoir un système sans session 🙂

Quelques notes importantes:

  • nous avons la sécurité du transport ( HTTPS et ses meilleurs amis);
  • derrière les rideaux, l’application Web délègue beaucoup d’opérations à des services externes , pour le compte de l’utilisateur actuel (ces systèmes reconnaissent Bob comme l’un de leurs utilisateurs) – cela signifie que nous devons leur transmettre les informations d’identification de Bob .

Maintenant, comment authentifier Bob (sur chaque requête)? Quelle serait une manière raisonnable de mettre en œuvre une telle chose?

  • jouer au tennis avec les identifiants via HTML sous forme de champs cachés … la balle contient les identifiants ( nom d’utilisateur et mot de passe ) et les deux raquettes sont respectivement le navigateur et l’application Web. En d’autres termes, nous pouvons transférer des données dans les champs de formulaire plutôt que via les cookies. A chaque demande Web, le navigateur affiche les informations d’identification. Toutefois, dans le cas d’une application à une page , cela peut sembler être un jeu de squash contre un mur en caoutchouc, au lieu de jouer au tennis , car le formulaire Web contenant les informations d’identité peut sera configuré pour ne pas offrir les informations d’identification de retour).
  • stocker le nom d’utilisateur et le mot de passe dans le contexte de la page – variables JavaScript, etc. Une seule page est requirejse ici, à mon humble avis.
  • authentification par jeton crypté. Dans ce cas, l’action de connexion entraînerait la génération d’un jeton de sécurité chiffré (nom d’utilisateur + mot de passe + autre chose). Ce jeton sera renvoyé au client et les demandes à venir seront accompagnées du jeton. Est-ce que ça a du sens? Nous avons déjà HTTPS …
  • autres…
  • dernier recours: ne faites pas cela, stockez les identifiants dans la session! La session est bonne. Avec ou sans cookies.

Est-ce que des préoccupations en matière de sécurité / Web vous viennent à l’esprit en ce qui concerne les idées décrites précédemment? Par exemple,

  • time-out – nous pouvons conserver un horodatage , avec les informations d’identification (horodatage = l’heure à laquelle Bob a entré ses informations d’identification). Par exemple, lorsque NOW – timestamp> threshold , nous pouvons refuser la demande.
  • Protection de script intersite – ne devrait en aucun cas être différente, non?

Merci beaucoup d’avoir pris le temps de lire ceci 🙂

Ah, j’adore ces questions – maintenir une session sans session.

J’ai vu de nombreuses façons de faire cela pendant mes relais lors des évaluations d’applications. L’un des moyens les plus répandus est la manière de jouer au tennis que vous avez mentionnée – l’envoi du nom d’utilisateur et du mot de passe dans chaque demande d’authentification de l’utilisateur. Ceci, à mon avis, est dangereux, surtout si l’application n’est pas une seule page. Il n’est pas non plus évolutif, surtout si vous souhaitez append des permissions à votre application en plus de l’authentification future (bien que je suppose que vous pouvez également créer quelque chose en fonction des connexions)

Un mécanisme populaire, mais pas complètement sans état (en supposant que vous exécutiez JavaScript) consiste à incorporer le cookie de session dans JavaScript. Le responsable de la sécurité en moi crie à cela, mais cela pourrait fonctionner – chaque requête a un en X-Authentication-Token tête X-Authentication-Token ou quelque chose comme ça, et vous le mappez sur une firebase database, un stockage en mémoire, etc. pour valider l’utilisateur. Ce jeton peut avoir un délai d’expiration, quelle que soit l’heure spécifiée, et s’il expire, l’utilisateur doit se reconnecter. Il est assez évolutif: si vous le stockez dans une firebase database, que son instruction SQL est exécutée et que les index sont corrects, son exécution prend très peu de temps, même avec plusieurs utilisateurs simultanés. Test de charge ici serait certainement utile si. Si je lis la question correctement, ce serait votre mécanisme de jeton crypté – bien que je suggère fortement que vous utilisiez un jeton cryptographique aléatoire de 32 caractères par opposition à une combinaison de nom d’utilisateur + mot de passe + autre chose – de cette façon, il rest imprévisible, mais vous pouvez toujours l’associer à l’ID utilisateur ou à une telle chose.

Quel que soit le mode d’utilisation, assurez-vous qu’il vous est envoyé en toute sécurité. HTTPS vous protège à travers le réseau, mais ne vous protège pas si vous jetez le jeton de session via l’URL (ou pire, les informations d’identification via l’URL). Je recommanderais d’utiliser un en-tête, ou si ce n’est pas faisable, d’envoyer le jeton via une requête POST à ​​chaque fois (cela signifierait un champ de formulaire masqué sur le navigateur de l’utilisateur). Cette dernière approche devrait utiliser des défenses CSRF. au cas où je pense que l’utilisation du jeton lui-même pourrait être une sorte de défense CSRF.

Enfin, assurez-vous d’avoir un mécanisme dans le backend pour purger les jetons expirés. Cela a été le fléau de nombreuses applications dans le passé – une firebase database de jetons d’authentification en croissance rapide qui ne semble jamais disparaître. Si vous devez prendre en charge plusieurs connexions utilisateur, assurez-vous de limiter le nombre ou de limiter la durée de chaque jeton. Comme je l’ai déjà dit, le test de charge peut être la réponse à cette question.

Il y a d’autres problèmes de sécurité auxquels je peux penser, mais ils sont trop vastes pour être traités à ce stade – si vous gardez à l’esprit tous les cas d’utilisation (et d’abus), vous devriez probablement être en mesure de ce système.

À propos de l’option de connexion – Je pense que vous souhaitez généralement prendre en charge des sessions pour les invités.

Donc, si vous voulez appliquer la connexion, l’option de jeton chiffré peut être bonne. Cela pourrait aussi être utile pour une session d’invité. Dans un autre sens, je combinerais l’ajout du jeton à l’URL et l’option de tennis.

Notez que l’envoi d’informations d’identification uniquement dans l’URL peut être dangereux. Par exemple, vous pourriez divulguer le jeton via l’en-tête de référence HTTP ou même par une personne qui inspecte simplement votre trafic ou surveille votre ordinateur.

Autre chose, même si vous pouviez utiliser des cookies, je vous recommande d’append un jeton aléatoire ou un verifer aléatoire pour vous protéger contre les attaques de type Cross Site Request Forgery (CSRF).