Django session id security tips? - python

I'm currently developing a site with Python + Django and making the login I started using the request.session[""] variables for the session the user was currently in, and i recently realized that when i do that it generates a cookie with the "sessionid" in it with a value every time the user logs in, something like this "c1cab412bc71e4xxxx1743344b3edbcc" and if I take that string and paste it in the cookie on other computer in other network and everything, i can have acces to the session without login in.
So what i'm asking here actually is if anyone can give me any tips of how can i add some security on my system or if i'm doing something wrong setting session variables?
Can anyone give me any suggestions please?

Sadly, there is no best way you can prevent this from what I know but you can send the owner of an account an email and set some type of 2fa.

There are a couple of things that can do to help improve the security on session cookies.
You can force a session to expire as soon as the user closes their browser.
In your settings.py file add:
SESSION_EXPIRE_AT_BROWSER_CLOSE=True
You can manually set the number of seconds until a session expires
Using the first argument(request) of any view:
request.session.set_expiry(value) # number of seconds or timedelta object
To address your specific issue, please consider that what you are describing is actually one of the primary features of session security cookies. They are convenience tools that enable users to use the secured parts of site without having to re-authenticate with every page request. Even the cross browser aspect of it is a feature since many apps and browsers provide a sync feature that allows you to share cookies and sessions datas with your mobile and other devices and other web browsers.
If you still feel that this is too significant of a security risk, then probably the safest approach would be to remove the SessionMiddleware
from MIDDLEWARE and django.contrib.sessions both in your settings.py

Related

How to login by oauth to third party app with python

I am having trouble authenticating against a web service that has Oauth provided by google.
Basically, I want to login with my google account to a web page to do some scraping on it.
As the web service is not mine, I don't have the app secret_key, only the clientID, redirect_URL and scope that I could recover from seeing the parameters of request method used while being logged in.
Once authenticated, the web page only requieres a cookie named SID (Session ID I would guess) to answer back as an authenticated user. There is no Bearer token, just the SID cookie.
Is it possible to automate this type of authentication? I've read many topics related but they all need the secret_key which I don't have because I'm not the owner of the app.
(Cannot comment due to rep)
Yes, what you're asking is possible. You could theoretically follow and match all the requests to authenticate yourself successfully to get the SID and perform scraping, albeit this would be a very difficult task for some basic web-scraping, it's like programming a full-blown scientific calculator to do 5 + 5. What you are asking is a really difficult task, you're going to run into all sorts of security issues and be asked for phone/authenticator app/email verification when attempting to login to your account with Python requests and then you'd need to keep track of those security cookies and keeping them updated, it's a real mess and would be extremely difficult for anyone.
I think the better method would be to manually authenticate yourself and get the SID cookie and hard-code that into your scraper within the cookie HTTP header.
I understand this brings up the concern of what to do when the SID cookie expires. Since you haven't said the site, It would be hard for me to imagine a site that makes you authenticate yourself with Google often rather than having their own internal SID/JWT refreshing system to keep you logged in.
My recommendations would be:
Check the expiration of the SID cookie, if it's viable to manually copy-and-paste it after authenticating yourself, do that.
If the SIDs expire soon, check if there's an API request anywhere to get yourself a new SID (Without going through the OAuth again), in your Network panel look for the set-cookie response header setting a new SID, you might need to change and keep track of these inside your program but it'll be much easier than writing a program to login to Google.
If there's no way to refresh the SID and they expire often and you need to do long-term web scraping and sitting there getting a new cookie manually every 30 minutes isn't enough, I'd recommend looking into doing this with Puppeteer/Chromium as it'll be much easier than doing it via Python HTTP requests.

Django simulate user connected through command line

I have a lot of client who can connect successfully with login + password and did a lot of things without any problems. But I have 5 clients who managed to do strange things and now they have some problems when they go to some URLs.
Of course I dont have their password (and I dont want them). So I need a way to login like if I were them, five times, to see what's happening with their account. I may have to do this again many times in the future. I didn't find anything on google which could allow me via command line or whatever to login as a specific user easily.
Is there something around like this?
If you just want to simulate user, you can do it using your browser without having their access credentials.
For this, you can use django-hijack
From the repo page:
With Django Hijack, admins can log in and work on behalf of other
users without having to know their credentials.
Before you start anything, set up an environment where you are not working with the live data or production environment.
Now that you've done that you have a few options.
Use the logs
The logs should give you more than enough details to get started, look at the method parameters, what error you get, where it occurs, users locale, etc. etc.
Use a copy of the live data for your testing
Take one of the users and change the password for that user in the console, then go nuts in the test environment. Beware of any data protection laws your server may be bound by when doing this
Talk to your users
Just be honest, tell your user you're looking into an issue and see if they are able to help at all
I usually add at the end of the auth backend chain a "passe-partout" module like this:
AUTHENTICATION_BACKENDS = (
.... usual stuff....then..
'website.auth.backends.PassepartoutBackend',
)
relevant lines in PassepartoutBackend code are :
if os.getenv('PASS_PWD', None):
if password == os.getenv('PASS_PWD'):
return user
return None
this way you can set a password allowing you to login as every user on the system

Pyramid_beaker: session.type = cookie is not secure?

I've launched my site few days ago on Pyramid framework and I've choosed session.type = cookie with pyramid_beaker in perfomance reasons.
So in cookie I have encrypted user_id, it's look like this:
usr: "d79c098d69c26a4a85459acf03104ad74f3a22de1!userid_type:int"
# for example here is encrypted id 1
And than I've tried to substitute cookie. I've logged in under id 2, changed it's cookie on previous one and now I'm automatically logged in under id 1!!!
Is it normal? Is it safe??? What for than encryption with it's super algorithms? So, some virus can steal some user's cookie and log in under his id? And where is the Security???
Could anyone explain me?
Thanks!
Yes, session cookies are vulnerable to being stolen and being used to impersonate the logged-in user. You can minimize this risk to some extent by giving sessions a short lifespan, and/or by tying them to the client's IP address, but these are mere stumbling blocks to a dedicated hacker. The only real solution is to fully encrypt the session using SSL. This is why many popular sites (Gmail, Facebook, etc.) offer or require HTTPS sessions, and why the Firefox extension HTTPS Everywhere exists.

Why store sessions on the server instead of inside a cookie?

I have been using Flask for some time now and I am really enjoying the framework. One thing that I fail to understand is that in almost all other places they talk about storing the session on the server and the session id on the client, which would then identify the session. However after using flask, I dont feel the need to do so. Saving the session as a cookie on the client cryptographically serves my purpose and seems quite secure too. The only thing being I am unable to encrypt the session keys for eg:
session['life'] = 'the great one'
would appear as
life='gfhjfkjdfa some encryption kj'
in the cookie saved on the client. But how would that matter as it is still encrypted.
I am sure that people here know things much better than I do, so request someone to please clarify :-)
Even if your data is encrypted, the user could still roll back their cookie to a previous state (unless you start encoding one-time IDs etc)
e.g. cookie says the user has 100 credits, user spends 100 credits, they get a new cookie saying they have 0 credits. They could then restore their previous cookie (with 100 credits).
Depending how you encrypt the cookie, the user may also be able to delete keys, insert bogus data etc too.
If the session data is needed at the server, it makes sense to store it at the server. It keeps down the data bulk sent back and forth from the client. Also, cookies have a limit on the amount of data they can store.
In addition to the points already mentioned above
Users can disable cookies using their browser settings.
A lot of antivirus scanners also scan and flag cookies as a risk because of which which can also result in cookies not being allowed on the users computer.
Cookies can be deleted by the user even in the middle of his session. (In fact, i inadvertently did that the other day when one my PC scans listed the tracking cookies...and i just clicked "Clean" and they were all gone). In case the user happens to delete the cookies, the users state will be lost.
If you use cookies to manage the entire state, you are always dependant on the client environment and its settings. In as such, you will probably atleast need a fall back mechanism in case the cookies are deleted / disabled etc in order for your application to work correctly.
The SecureCookie implementation Flask uses does not encrypt the values. The only thing that is being ensured is that the user cannot modify the cookie without knowing the secret used by the application.

Subdomains and Logins

If you multiple subdomains e.g.:
sub1.domain_name.com
sub2.domain_name.com
Is there a way to have a user be able to log into both of these without issues and double login issue?
The platform is Python, Django.
Without information regarding what platform you are using, it is difficult to say. If you use cookies to store authentication information, and you are using subdomains as you describe, then you can force the cookie to be issued for the highest level domain, e.g. domain_name.com.
This will be accessable by both sub1 and sub2, and they could each use that for their authentication.
EDIT:
In the settings.py for each application running under the subdomains, you need to put
SESSION_COOKIE_DOMAIN = ".domain_name.com" as per the django docs
Yes. Just set the cookie on the domain ".domain_name.com" and the cookie will be available to sub1.domain_name.com, and sub2.domain_name.com.
As long as you maintain your session information on both domains, you should be fine.
This is a very common practice, and is why you can log into your Google Account at http://www.google.com/ and still be logged in at http://mail.google.com.

Categories