OK, I'm stumped, and have been staring at this for hours.
I'm setting a cookie at /access/login.php with the following code:
setcookie('username', $username, time() + 604800, '/');
When I try to logout, which is located at /access/logout.php (and rewritten to /access/logout), the cookie won't seem to unset. I've tried the following:
setcookie('username', false, time()-3600, '/');
setcookie('username', '', time()-3600, '/');
setcookie('username', '', 1, '/');
I've also tried to directly hit /access/logout.php, but it's not working.
Nothing shows up in the php logs.
Any suggestions? I'm not sure if I'm missing something, or what's going on, but it's been hours of staring at this code and trying to debug.
How are you determining if it unset? Keep in mind that setcookie() won't remove it from the $_COOKIE superglobal of the current script, so if you call setcookie() to unset it and then immediatly print_r($_COOKIE);, it will still show up until you refresh the page.
Try pasting javascript:alert(document.cookie); in your browser to verify you don't have multiple cookies saved. Clear all cookies for the domain you're working on to make to sure you're starting fresh. Also ini_set(E_ALL); to make sure you're not missing any notices.
Seems to be a server issue. My last domain was pretty relaxed on PHP error handling while the new domain shows every error. I'm using both sites side by side and the old one removes the cookie as it should.
Is there perhaps a timezone issue here? Have you tried setting using something farther in the past, like time() - (3600*24)? PHP's documentation says that the internal implementation for deleting cookies uses a timestamp of one year in the past.
Also, you should be able to use just setcookie('username', false); without passing an expiration timestamp, since that argument is optional. Maybe including it is confusing PHP somehow?
How you use cookies data in your application?
If you read the cookies and check if username is not false or not '', then setting it to false or '' will be sufficient, since your application will ignore the cookies value.
You better put some security in cookies value, to prevent user change it's value. You can take a look of CodeIgniter session library, see how CI protect the cookies value using hash. Unauthorized value change will detected and the cookies will be deleted.
Also, CI do this to kill the cookies:
// Kill the cookie
setcookie(
$this->cookie_name,
addslashes(serialize(array())),
(time() - 31500000),
$this->cookie_path,
$this->cookie_domain,
0
);
You can delete cookies from javascript as well. Check here http://www.php.net/manual/en/function.setcookie.php#96599
A simple and convenient way, is to use this additional functions:
function getCookie($name) {
if (!isset($_COOKIE[$name])) return false;
if ($_COOKIE[$name]=='null') $_COOKIE[$name]=false;
return $_COOKIE[$name];
}
function removeCookie($name) {
unset($_COOKIE[$name]);
setcookie($name, "null");
}
removing a cookie is simple:
removeCookie('MyCookie');
....
echo getCookie('MyCookie');
I had a similar issue.
I found that, for whatever reason, echoing something out of logout.php made it actually delete the cookie:
echo '{}';
setcookie('username', '', time()-3600, '/');
I had the same issue; I log out (and I'm logged out), manually reload the index.php and then I'm logged in again. Then when I log out, I'm properly logged out.
The log out is a simple link (index.php?task=logout). The task removes the user from the session, and "deletes" (set value '' and set expiry in the past) the cookie, but index.php will read the user's auth token from the cookie just after this (or all) task (as with normal operations). Which will reload the user. After the page is loaded the browser will show no cookie for the auth token. So I suspect the cookie gets written after page finish loading.
My simple solution was to not read the cookie if the task was set to logout.
use sessions for authentication, don't use raw cookies
http://www.php.net/manual/en/book.session.php
Related
I have created a logout.php page to let the user sign out from the website and redirects them to the sign in page.
however what ever i do, the cookies are not getting deleted, so when the user gets redirected to the singin page the latter examines the cookies and then find it, therefore logs the user in.
Below is the code of logout.php:
<?php
unset($login);
if (isset($_COOKIE['xxx'])){
setcookie('xxx', false, time() - 3600,"/");
}
if (isset($_COOKIE['yyy'])){
setcookie('yyy', false, time() - 3600,"/");
}
header("Location: singin.php");
die();
?>
Please note that this php page is in subfolder protected by password and the html link redirects to a php file that require() the logout.php file.
use php unset() to delete your cookie as, you can get the complete details here delete the cookie
if (isset($_COOKIE['xxx'])){
unset($_COOKIE['xxx']);
}
if (isset($_COOKIE['yyy'])){
unset($_COOKIE['yyy']);
}
or, set value as null and a negative time for your cookie as
setcookie('xxx', null, -1, '/');
setcookie('yyy', null, -1, '/');
or, set value as empty and a past time for your cookie as
setcookie("xxx", "", time()-3600);
setcookie("yyy", "", time()-3600);
I have found finally the reason behind the issue.
it's because I have put session_cache_limiter('public'); in my code, so which I presume prevents the client to set the cookie to an expiry date.
I have done that because I don't want the client to ask the user each time they hit back to resubmit the form.
It seems that it's not the correct practice, I'll post another question for that.
Thanks all for the help.
So i've tried multiple other "solutions" to my problem (both on this site and others) and cannot find a solution that works for me.
I'm trying to set a cookie to log in my user and then on log out delete that cookie. Here is my code.
list ($check, $data) = check_login($dbc, $_POST['Username'], $_POST['Password']);
if ($check) {
setcookie('Username', $data['Username'], time() + 60*60*24*90);
header('Location: RedirectPage.php');
Which, checks the username and password have been entered on the login form (and accepted), If so, the cookie "Username" is set with the username drawn from the database, and a time equalling 90 days, and the user is then redirected.
This part works fine, it logs the user in as would be expected.
However in the delete part,
header('Refresh: 0;');
setcookie('Username', '', time() - 60*60*24*90);
unset($_COOKIE['Username']);
require ('RedirectPage.php');
redirect_user();
I delete the cookie in the same way it was set, as expected, removing any data and setting the time to a negative value, and then for good measure i run the unset cookie to ensure that it has gone.
Except, this doesn't work. setcookie (to delete) does not do anything, and unset cookie only works on the page after it has been run (in this case, index.php) and as soon as i click to another page, or refresh the page it "forgets" that the cookie has been deleted.
Now going into the Chrome inspect element to check the cookie i get
Username, "Value" (the withdrawn username), r3gamers.com (domain), / (path), 2015-02-03T13:45:00 (Expires/MaxAge), 19 (Size) and HTTP and Secure are both set as empty.
Watching the process after hitting the logout button, this cookie is never deleted. The only thing which can actually delete the cookie is overwriting it with a new cookie (logging in again) or deleting it through inspect element.
Any ideas? As far as i'm aware, i'm doing everything that should be done.
EDIT:
I'd also like to mention that when testing this on localhost, offline through netbeans this functionality does work. However when i upload the pages to godaddy for my website they stop working properly.
I found the answer. It's a stupid answer too. Here is the full code file i was using for logout.
<?php
require_once ('Connection.php');
header('Refresh: 0;');
if (!isset($_COOKIE['Username'])){
header('Location: LoginFunctions.php');
} else {
setcookie('Username', '', time()-60*60*24*90, '/', '', 0, 0);
unset($_COOKIE['Username']);
header('Location: index.php');
}
?>
The problem, which i can't show here, was that the opening php tag had a single line break on it, meaning that it started on line 2. Why it was like this initially i don't know, but that small error meant that it worked on localhost and didn't work on godaddy. How frustrating. At least i've fixed the problem now.
For future use, for those stuck with the same issue, apparently godaddy (or most hosting sites) require that any cookie adding, editing or deleting occur from line 1 onwards, therefore the php tag which includes the cookie must be on line 1, no html code can preceed this php tag, or any line breaks, the php tag has to start on line 1.
You do not set the path of your cookie, I assume you want it to be site-wide, so you should set the path to '/':
setcookie('Username', $data['Username'], time() + 60*60*24*90, '/');
And then, when unsetting it, try using 1 instead of time() - 60*60*24*90 (also still specifying the path), otherwise the expiration time of the cookie might vary depending on the user's computer clock:
setcookie('Username', '', 1, '/');
I think your problem really is the path not being set: http://php.net/manual/en/function.setcookie.php
If set to '/', the cookie will be available within the entire domain. If set to '/foo/', the cookie will only be available within the /foo/ directory and all sub-directories such as /foo/bar/ of domain. The default value is the current directory that the cookie is being set in.
The thing is, if you are in /logout/doit.php, and you try to set the cookie expiration time to a negative value, it will create a new cookie with the path '/logout/' and set its expiration time. (Instead of setting the expiration time on your site-wide cookie)
1. setcookie('Username', 12, time()-3600);
2. if(isset($_COOKIE['Username']) doSomething();
1. doesn't work, but 2. works, this makes no sense to me, how can it read the cookie but not be able to delete it?
This is how I've set the cookie: setcookie('Username', $user['username'], time()+3600*24);
I should have probably defined the path, but still, why does one thing work and the other doesn't? I need to find a way to delete that cookie because I've changed my website folder and there's 1000's of users with active cookies on their browsers, and not being able to delete them is generating an infinite redirection loop.
EDIT
I was able to delete the cookie by changing the path to /: setcookie('Username', 12, time()-3600, '/');
It still doesn't explain why I was able to access the cookie on a different path...
EDIT
For some reason, that above worked that time, but now it doesn't working anymore... Starting to make me insane.
EDIT
I forgot to change the new cookies path... That's why it wasn't working again.
You need to empty that value. setcookie('Username', "", time()-3600);
I have an ASP.NET Login App on my site and once logged in, I can navigate to the WordPress(PHP) side (still on the same domain) whilst maintaining the session. See my pastie link below for how this works.
However, the problem arises if I close my browser, I then lose the PHP 'session' despite keeping the ASP.NET session. So I'm 'logged out' on the PHP side but still 'logged in' on the .NET side.
-- Is there a way, using my existing code, to set a lifetime to the session/cookie, to avoid the session/cookie disappearing when I close my browser? --
I have pastie'd my current PHP code from my template's here: http://pastie.org/private/ndcqgbog34uqld1etozda which checks and persists the session.
I did have a look at this example on PHP.net but got confused as to how to use it in my solution.
Many thanks for any pointers with this.
Think you should be using setcookie() with an expiry time (see here). You're only setting stuff in the session (copied from cookies, it looks like, but I'm not sure what their lifetime is).
Instead of this line:
$_SESSION[DOT_NET_SESSION][ $tuple['SessionName'] ] =
$tuple['SessionValue'];
Try this:
$cookie = array($tuple['SessionName'] => $tuple['SessionValue']);
setcookie(DOT_NET_SESSION, $cookie, time() + 60 * 60 * 24);
That should set a cookie for a day, I think.
I'm just trying to set and use a cookie but I can't seem to store anything.
On login, I use:
setcookie("username", $user);
But, when I use Firefox and the Web Developer plugin Cookies -> View Cookie Information There is no username cookie.
Also, when I try to access the value from a subsequent page using
$_COOKIE["username"]
It is returning null/empty
var_dump(setcookie("username", $user));
RESULT: bool(true)
and
var_dump($_COOKIE)
RESULT: specific cookie does not exist (others are there)
I have done some more testing...
The cookie exists after login (first page) but disappears when I go to another (2nd page) and is lost for good...
Are there any headers that must be present or not present?
http://php.net/manual/en/function.setcookie.php
Try setting the $expire parameter to some point in the future. I believe it defaults to 0, which is in the distant past.
Make sure that you are setting the domain parameter correctly in case the URL is changing after you go to another page after login. You can read more about the domain parameter on http://php.net/manual/en/function.setcookie.php
The cookie is probably expired because $expire defaults to 0 seconds since the Unix epoch. (docs)
Try
setcookie("username", $user, time() + 1200);
which expires 20 minutes after set (based on the client's time).
Use var_dump() on setcookie(..) to see what is returned. Also might do the same to $_COOKIE to see if the key is set.
Thanks everyone for the feedback... Aditya lead me to further analyse the cookie and I discovered that the path was the issue...
The login path was /admin/ and then I was redirecting back to the root...
Thanks all for your help and feedback!