18

I don't want the user to go back to secured pages by clicking back button after logging out. In my logout code, I am unsetting the sessions and redirecting to login page.But, I think the browser is caching the page so it becomes visible despite the session being destroyed from logout.

I am able to avoid this by not allowing the browser to cache

header("Cache-Control", "no-cache, no-store, must-revalidate")

But this way I am loosing the advantage of Browser Caching.

Please suggest a better way of achieving this. I feel, there must be a way of handling this by javascript client side

3
  • 7
    You don't have to disable anything. If they go back, they're served the cached version of the restricted page. If they try to click around it, nothing will work because the appropriate session won't be set. Commented May 9, 2012 at 7:50
  • 1
    @N.B. A possible solution which might not necessarily be always usable as the user might have sensitive data on his display and then logs out. Another comes by (although the workstation should be locked ;) ) and presses back and sees (although cached) the data of the previous user. We usually add an info message alerting the user to close the browser (just to be sure all sessions have been cleared). It's not necessarily the best way, but at least you gave the user the info about the potential problem. Commented May 9, 2012 at 8:11
  • 3
    A cheap fix if all else fails would be a "Please close this window for security reasons" message on the logged out page. Commented May 9, 2012 at 8:36

9 Answers 9

12

Implement this in PHP and not javascript.

At the top of each page, check to see if the user is logged in. If not, they should be redirected to a login page:

<?php if(!isset($_SESSION['logged_in'])) : header("Location: login.php"); ?> 

As you mentioned, on logout, simply unset the logged_in session variable, and destroy the session:

<?php unset($_SESSION['logged_in']); session_destroy(); ?> 

If the user clicks back now, no logged_in session variable will be available, and the page will not load.

Sign up to request clarification or add additional context in comments.

3 Comments

I have already implemented this technique. But hitting back button don't actually requests to server. Instead the back page is rendered from browser cache. Hence it is not redirecting to login page.
So what is the problem? The user can't interact with server after logout and with back button he only retrieve data which he has already seen. If those data can be misused by someone else, just notice the user to close the window or use annonymous tab, if he doesn't, it's his fault.
A user is logged in and views some sensitive data. He then logs out and leaves the computer. Someone else comes along, presses the back button and has access to the sensitive data. That's the problem.
4

I was facing this same problem and spent whole day in figuring out it, Finally rectified it as follows:

In login validation script if user is authenticated set one session value for instance as follows:

$_SESSION['status']="Active"; 

And then in User Profile script put following code snippet:

<?php session_start(); if($_SESSION['status']!="Active") { header("location:login.php"); } ?> 

What above code does is, only and only if $_SESSION['status'] is set to "Active" then only it will go to user profile , and this session key will be set to "Active" only if user is authenticated... [Mind the negation [' ! '] in above code snippet]

Probably logout code should be as follows:

{ session_start(); session_destroy(); $_SESSION = array(); header("location:login.php"); } 

Hope this helps...!!!

Comments

3

Here's an easy solution which I have used in my application.

Add the below code inside script tag in the login HTML page (or whichever page it redirects to after logout)

<script> history.pushState(null, null, null); window.addEventListener('popstate', function () { history.pushState(null, null, null); }); </script> 

It will disable the back button. You will not be able to go back by clicking on the back button.

Note: Not tested on Safari.

6 Comments

here what is document.title
Hi Vijju, Javascript will fetch the title of the page whatever you have given in the head tag. You can give that as null and it will work as required in the question above.
I have editted the answer and tested in my application. works fine.
HII @Mashmoom . I have another doubt that is when I opened the log in page and click the back button button it doesn't go back to main page. when user log out from the website then only the back button is disabled.Remaining times it works
Don't break people's browser!!
|
1

I think your only server side option is to disallow caching. This is actually not that bad if you are using a Javascript heavy application as your main HTML might only be a series of JS calls and the Views are then generated on the fly. That way the bulk of the data (JS MVC and core code) is cached but the actual page request isn't.

To add to the comments pasted below I would suggest adding a small AJAX call during load time that fires even for cached pages that goes to your backend and checks the session. If not session is not found it would redirect the user away. This is clientside code and not a secure fix, sure, but looks nicer.

You could get this off your conscience with

A cheap fix if all else fails would be a "Please close this window for security reasons" message on the logged out page. – izb May 9 '12 at 8:36

But like N.B. said

You don't have to disable anything. If they go back, they're served the cached version of the restricted page. If they try to click around it, nothing will work because the appropriate session won't be set. – N.B. May 9 '12 at 7:50

Comments

1

the pages on which you required loged in, use setInterval for every 1000 ms and check wheather user is logged in or not using ajax. if user session is invalid, redirect him to log in page.

1 Comment

This answer is the only one with the right approach. Contact the server to see if they are logged in, if not, erase the page or redirect. But there's no need for an interval, that would keep contacting the server forever. It only needs to be done once on page load. This would run after the page initially loads, and each time the user clicks back onto a cached page. Your solution is for the case of wanting all open browser windows to simultaneously logout and redirect to another page, but the question was only looking to prevent viewing private pages via the back button when logged out.
0

You could insert a condition/function on each restricted page, checking if the appropriate session variable is set or not. This way, you can print 2 versions of the page (one for the valid users, and one redirecting to the login page)

1 Comment

I have already implemented this. But it won't stop the user to render the page when clicked on Back button since it is rendered from browser's cache. Although, if user refreshes the page or does any action on the page he will be redirected back to login page. Since there may be few personal information in the inner pages I want to restrict user to be able to view the previous pages by hitting back button after logout.
0

Avoiding the user to go back is not a good reason and most of all not secure at all.

If you test the user's session before every "admin" action made on the website, you should be fine, even if the user hit the back button, sees the cached page and tries something.

The "ties something" will return an error since the session is no longer valid.

Instead, you should focus on having a really secured back office.

Comments

0

Here's an easy and quick solution.

To the login form tag add target="_blank" which displays content in a different window. Then after logout simply close that window and the back button problem (Safari browser) is solved.

Even trying to use the history will not display the page and instead redirect to login page. This is fine for Safari browsers but for others such as Firefox the session_destroy(); takes care of it.

Comments

0

Note that although users can't change anything after resetting session data and/or cookie, they still may see usual information accessible to a logged in user as they appeared on the last visit. That is caused by browser caching the page.

You have to be sure to add the header on every page accessible by a logged in user, telling the browser that the data is sensitive and they should not cache the script result for the back button. It is important to add

header("Cache-Control: no-cache, must-revalidate"); 

Note that those other elements other than the immediate result of the script under this header, will still be cached and you can benefit from it. See that you gradually load parts of your page and tag sensitive data and the main HTML with this header.

As the answer suggests, unsetting the logged_in portion of $_SESSION global variable can achieve logging out, but be aware that first, you don't need to destroy session as mentioned in the PHP's session_destroy() documentation

Note: You do not have to call session_destroy() from usual code. Cleanup $_SESSION array rather than destroying session data.

And second, you better not to destroy the session at all as the next warning on the documentation explains.

Also, unset() is a lazy function; meaning that it won't apply the effect, until next use of the (part of the) variable in question. It is good practice to use assignment for immediate effect in sensitive cases, mostly global variables that may be used in concurrent requests. I suggest you use this instead:

$_SESSION['logged_in'] = null; 

and let the garbage collector collects it, at the same time it is not valid as a logged in user.

Finally, to complete the solution, Here are some functions:

<?php /* * Check the authenticity of the user */ function check_auth() { if (empty($_SESSION['logged_in'])) { header('Location: login.php'); // Immediately exit and send response to the client and do not go furthur in whatever script it is part of. exit(); } } /* * Logging the user out */ function logout() { $_SESSION['logged_in'] = null; // empty($null_variable) is true but isset($null_variable) is also true so using unset too as a safeguard for further codes unset($_SESSION['logged_in']); // Note that the script continues running since it may be a part of an ajax request and the rest handled in the client side. } 

Comments

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.