With Flask-Login, you want current_user == None
, not current_user is None
current_user
is a proxy object that happens to be wrapping None
, but isn’t actually None
.
I was writing some code that uses Flask-Login, and I wanted to test the scenario where a user wasn’t logged in.
I get the value of current_user
, and it’s None
:
>>> from flask_login import current_user
>>> current_user
None
Great! So now I can check if this value is None
, and react accordingly:
>>> if current_user is None:
... print("Nobody is logged in!")
...
>>>
Hmm.
If you look at how Flask-Login works, you see that current_user
is defined as a LocalProxy
that wraps the _get_user()
function:
from werkzeug.local import LocalProxy
...
#: A proxy for the current user. If no user is logged in, this will be an
#: anonymous user
current_user = LocalProxy(lambda: _get_user())
This LocalProxy
class is some sort of wrapper. The Werkzeug docstring describes it as “a proxy to the object bound to a context-local object” which doesn’t mean much to me, but I can see that it’s getting in the way of the identity checks.
In particular, the wrapper is equal to None
but not identical to it:
>>> p = LocalProxy(lambda: None)
>>> p
None
>>> p == None
True
>>> p is None
False
>>> id(p)
4349196416
>>> id(None)
4343995648
This means my code has to use current_user == None
, not current_user is None
. This looks odd – generally it’s better Python to use is None
as a comparison, but in this case it won’t work.