web-dev-qa-db-fra.com

Empêcher l'utilisateur de voir la page sécurisée précédemment visitée après la déconnexion

J'ai l'obligation de ne pas pouvoir revenir à la page restreinte après la déconnexion/déconnexion de l'utilisateur final. Mais actuellement, l'utilisateur final peut le faire en cliquant sur le bouton Précédent du navigateur, en consultant l'historique du navigateur ou même en ressaisissant l'URL dans la barre d'adresse du navigateur.

En gros, je souhaite que l'utilisateur final ne puisse accéder à la page restreinte de quelque manière que ce soit après la déconnexion. Comment puis-je atteindre ce meilleur? Puis-je désactiver le bouton Retour avec JavaScript?

96
raaz

Vous pouvez et ne devez pas désactiver le bouton de retour du navigateur ou son historique. C'est mauvais pour l'expérience utilisateur. Il existe des hacks JavaScript, mais ils ne sont pas fiables et ne fonctionneront pas non plus lorsque le client a désactivé JS. 

Votre problème concret est que la page demandée est chargée à partir du cache du navigateur plutôt que directement du serveur. C’est essentiellement inoffensif, mais source de confusion pour l’utilisateur final, car il/elle pense à tort que cela vient vraiment du serveur.

Vous devez simplement indiquer au navigateur de pas mettre en cache toutes les pages JSP restreintes (et donc pas uniquement la page/action de déconnexion elle-même!). De cette façon, le navigateur est obligé de demander la page au serveur au lieu de la cache et donc toutes les vérifications de connexion sur le serveur seront exécutées. Vous pouvez le faire en utilisant un Filtre qui définit les en-têtes de réponses nécessaires dans la méthode doFilter():

@WebFilter
public class NoCacheFilter implements Filter {

    @Override
    public void doFilter(ServletRequest req, ServletResponse res, FilterChain chain) throws IOException, ServletException {
        HttpServletResponse response = (HttpServletResponse) res;

        response.setHeader("Cache-Control", "no-cache, no-store, must-revalidate"); // HTTP 1.1.
        response.setHeader("Pragma", "no-cache"); // HTTP 1.0.
        response.setDateHeader("Expires", 0); // Proxies.

        chain.doFilter(req, res);
    }

    // ...
}

Mappez cette Filter sur un url-pattern d'intérêt, par exemple *.jsp.

@WebFilter("*.jsp")

Ou si vous souhaitez appliquer cette restriction uniquement aux pages sécurisées, vous devez spécifier un modèle d'URL couvrant toutes les pages sécurisées. Par exemple, lorsqu'ils se trouvent tous dans le dossier /app, vous devez spécifier le modèle d'URL de /app/*

@WebFilter("/app/*")

Encore plus, vous pouvez effectuer ce travail dans la même Filter que celle où vous vérifiez la présence de l'utilisateur connecté.

N'oubliez pas de vider le cache du navigateur avant de tester! ;)

Voir également:

130
BalusC

* .jsp dans le modèle d'URL ne fonctionnera pas si vous transférez une page. Essayez également d’inclure votre servlet pour que votre application soit sécurisée contre ce problème de bouton arrière.

5
Sathyan

Le moyen le plus simple de le faire sans désactiver le navigateur, mais en ajoutant ce code à l'événement page_load de la page sur laquelle vous ne souhaitez pas que l'utilisateur revienne après sa déconnexion:

if (!IsPostBack)
    {
        if (Session["userId"] == null)
        {
            Response.Redirect("Login.aspx");
        }
        else
        {
            Response.ClearHeaders();
            Response.AddHeader("Cache-Control", "no-cache, no-store, max-age=0, must-revalidate");
            Response.AddHeader("Pragma", "no-cache");
        }
    }
2
Ashraf Abusada

La bonne façon de faire est d’ajouter le

Vary: Cookie

en-tête sur les pages sécurisées. Lorsque l'utilisateur se déconnecte, effacez son cookie de session. Ensuite, lorsqu'ils reviendront après la déconnexion, la mémoire cache du navigateur sera manquante. Cela a également l'avantage de ne pas vaincre complètement la mise en cache.

0
Dan

Vous pouvez essayer de dire au navigateur de ne pas mettre en cache la page d'accueil (en utilisant les en-têtes appropriés - Expires, Cache-Control, Pragma). Mais il n'est pas garanti que cela fonctionne. Ce que vous pouvez faire, c'est faire un appel ajax au serveur lors du chargement de la page pour vérifier si l'utilisateur est connecté, et si non - rediriger.

0
Bozho