delight-im / PHP-Auth

Authentication for PHP. Simple, lightweight and secure.
MIT License
1.08k stars 234 forks source link

check isLoggedIn() not working consistently #279

Open NopMap opened 2 years ago

NopMap commented 2 years ago

I have a very strange issue with isLoggedIn() not always reporting the correct state.

I am using some editing functions and AJAX to maintain lists of data. The whole thing is protected with Auth, you need to login first and all write operations are protected with checks whether you are logged in and have admin rights. The login page is designed to show a login form if you are not logged in and a logout button otherwise.

The whole setup works fine when testing locally with Xampp, so my code should be ok. But when I move my stuff to the real server, the logged-in detection on the login page fails, it always claims that I am not logged in, even right after login. All other editing functions that check for login work and allow access, so the login information is there, just on this one page it is somehow returning false.

The behaviour is 100% reproducible. Reducing the sync interval to 5 seconds did not change it.

Both local and remote server use PHP 7.3 with mySql DB.

This issue sounds like it may be related: #237

Do you have any idea what could cause this behaviour?

maietta commented 2 years ago

I can't see your application logic, but I have experienced unexpected cache behavior on xhr/ajax http requests. If you are checking this status on every ajax call to a protected request, perhaps it's simply cahed responses? IDK. If this is suspected, adding a cache busting timestamp query parameter to the end of your query string will rule this out.

I use PHP Auth a lot and have never run into inconsistent isLoggedIn() responses when directly called from the PHP app. It was only ever when dealing with ajax requests that I ran into this.

Unrelated to your question but I moved away from Xamp and other local webservers in favor of using Docker containers that replicate my exact hosting environment so that I can remove any discrepancies between development and production. If this is interesting at all to you, check out my local dev stack found here: https://github.com/PremoWeb/SDK-Foundation-Vue. Gives me a Vue 3 front-end and PHP backend using Fat Free Framework. The important bits are the Dockerfile and docker-compose.yml at the root of the project. Grab those and install Docker for Desktop on your machine and you're now able to develop websites using PHP 8.1.x and Nginx (provided docker image by me). In my scenario, I also deploy the exact same container to my Caprover PaaS servers so I know my production system is identical to the local development environment. No more discrepancies, ever.

NopMap commented 2 years ago

Thanks for your response. Unfortunately, it is exactly the opposite behaviour. When I use AJAX to retrieve data, everything works fine. The problem happens when I try to call isLoggedIn in the creation of a web page.

maietta commented 2 years ago

Okay, very interesting.

ocram commented 2 years ago

Thank you for your question, @NopMap , and thanks a lot for helping, @maietta !

  1. Do you have any idea how your login page may be different from all the other pages (which do not show the wrong behavior)?
  2. The check on the login page not only does not work right after login, but even when loading the page again or navigating to it without submitting any form, right?
  3. Any significant differences in PHP configurations (php.ini) between the two environments? Make sure to check which PHP configuration is actually loaded.
  4. Are the cookies set correctly when using the application on the server?
  5. Any major problems logged in the error logs of PHP or the server?
eypsilon commented 2 years ago

I am using some editing functions and AJAX to maintain lists of data.

I had a similar problem with Auth and AJAX, session_write_close() fixed it for me. You can call it right after Auth is done, or at the end of your script.

ponasromas commented 1 year ago

I too encountered this problem. Also using Fat Free framework. I also use ajax for login request. What's strange, is that if I login with "rememberDuration" isLoggedIn value is present. If not - it does not validate and therefore does not write anything to session. Trying to wrap my head around this...

Update: Seems problem is that 'auth_user_id' in session is not set if 'rememberDuration' not selected. How is that 'auth_user_id' is set in session after successful login?

TrackWorx commented 11 months ago

Is there a solution for this? When I call up the page via a link, isLogged() is not executed. Only when I fire the URL in the browser with an Enter. Is this possibly a cache setting of PHPAuth?

ponasromas commented 11 months ago

Is there a solution for this? When I call up the page via a link, isLogged() is not executed. Only when I fire the URL in the browser with an Enter. Is this possibly a cache setting of PHPAuth?

If you use F3 framework, than it is related with sessions in database. Particularly this bit of code:

// start session
        new \DB\SQL\Session($this->db, 'sessions', false, function ($session) {

            $logger = new \Log(date("Ymd") . '_sessions.log');

            // Suspect session
            if (($ip = $session->ip()) != $this->f3->IP) {
                $logger->write('User changed IP:' . $ip);
            } else {
                $logger->write('User changed browser/device: ' . $this->f3->AGENT);
            }

            // The default behaviour destroys the suspicious session.
            //return false;
        }, 'CSRF');

I just commented out return part of code. It is related to IP change within the session. In current times, when visitors use mobile internet with changing IPs this creates problem.