Issue: Error: ID token invalid: Invalid token: module 'jwt' has no attribute 'decode'


Using these instructions: https://saadazizai.blogspot.com/2025/08/echo-client-app-getting-started.html


Upon setting up for the first time:


Given that user is attempting to login using http://localhost:5000, when they enter a valid username and password, they are redirected to: 

http://localhost:5000/callback?code=98757796-576c-475d-ae3a-cc9688757104&state=9e2bfaee-7f3f-4f35-8e44-4a942c00f46b

Error: ID token invalid: Invalid token: module 'jwt' has no attribute 'decode'

Troubleshooting:



That error means your code is importing the wrong jwt library. There are two different Python packages:

  • Correct one: PyJWT → usage: import jwt; jwt.decode(...)

  • Wrong one (causing error): jwt (outdated, unrelated package, missing decode)


Fix

  1. Uninstall wrong jwt:

pip uninstall jwt -y
  1. Install correct PyJWT:

pip install PyJWT
  1. Verify:

python -c "import jwt; print(jwt.__version__)"

Should print something like 2.8.x.


Update requirements.txt

Add:

PyJWT

Why It Happened

  • requirements.txt didn’t specify PyJWT explicitly.

  • If you install jwt instead of PyJWT, you get a minimal package with no decode function.


After Fix

Re-run your API Gateway:

python api_gateway.py

You should see proper JWT decoding (it will still fail if the token is invalid, but not with “no attribute decode”).


Do you want me to audit your whole codebase now for all external libs and produce a clean requirements.txt so this doesn’t happen again?
I can also pin versions for stable local vs. cPanel deploys (e.g., Flask 3.0 vs 2.x compatibility). Want me to do that?

Right — Windows CMD is picky with quotes for inline Python. Let’s do this step-by-step so you can verify the correct library without the quoting issues.


1. Check if wrong jwt is still installed

Run:

pip show jwt

If you see output (Name: jwt), that’s the wrong one.


2. Remove the wrong one

pip uninstall jwt -y

Run pip show jwt again — it should now say “WARNING: Package(s) not found”.


3. Install correct PyJWT

pip install PyJWT

4. Verify the correct library

Run:

python -c "import jwt; print(jwt.__name__); print(jwt.__version__)"

Expected output:

jwt
2.x.x

(No AttributeError, version should show up.)


5. Update requirements.txt

Replace jwt with PyJWT:

flask
requests
openai
Jinja2>=3.1.2
python-dotenv
pytz
PyJWT>=2.8.0

Remove dotenv (redundant).


Do you want me to rewrite your entire requirements.txt from scratch (scan imports, remove duplicates, pin versions) so it’s clean for both local dev and future cPanel deploys?
This would prevent all these mismatches going forward.

Here’s how to run your Echo app stack from the Windows CMD line (not PowerShell) step-by-step:


1. Open CMD and Navigate to Project

cd C:\Users\saad0\Documents\source\echo-private

2. Activate Conda Environment

If you created your env with Conda:

conda activate echo

(You should see (echo) in your prompt.)


3. Run Each Service in Separate CMD Windows

Open 4 CMD windows (or tabs) and run these commands in each:


Window 1 – Logging Service (port 5020)

cd C:\Users\saad0\Documents\source\echo-private
conda activate echo
python logging_service.py

Window 2 – Parser Service (port 5010)

cd C:\Users\saad0\Documents\source\echo-private
conda activate echo
python parser_service.py

Window 3 – API Gateway (UI, port 5000)

cd C:\Users\saad0\Documents\source\echo-private
conda activate echo
python api_gateway.py

Window 4 – Worker (background jobs)

cd C:\Users\saad0\Documents\source\echo-private
conda activate echo
python worker.py

4. Access the App


5. Stop Services

Press CTRL+C in each window to stop.


Optional: Run All in One Go

You can create a batch file (start_services.bat) to launch all 4 windows automatically:

@echo off
start cmd /k "conda activate echo && python logging_service.py"
start cmd /k "conda activate echo && python parser_service.py"
start cmd /k "conda activate echo && python api_gateway.py"
start cmd /k "conda activate echo && python worker.py"

Double-click start_services.bat → launches all 4 services.


Do you want me to write this batch file for you and include DB init commands (so first run sets up jobs.db and logs.db too)?
Or should I combine everything into one window (using start /b background tasks)?

Ah, you’re asking how to install all requirements from requirements.txt via CMD (not PowerShell). Here’s exactly how to do it:


1. Open CMD

Press Win+R → type cmd → Enter.


2. Navigate to Your Project

cd C:\Users\saad0\Documents\source\echo-private

3. Activate Your Conda Environment

conda activate echo

(Prompt should show (echo) now.)


4. Install Requirements from requirements.txt

pip install -r requirements.txt

Important: Fix Wrong JWT Package First

Before running that, edit requirements.txt and replace:

jwt

with

PyJWT>=2.8.0

Also remove dotenv (redundant). Your cleaned file should be:

flask
requests
openai
Jinja2>=3.1.2
python-dotenv
pytz
PyJWT>=2.8.0

5. Verify Installation

Check PyJWT version:

python -c "import jwt; print(jwt.__version__)"

Should print 2.x.x (not error).


Do you want me to generate a fully cleaned and pinned requirements.txt for you (scan all imports and lock versions)?
This ensures same behavior locally and later on cPanel (avoids future JWT-type errors). Want me to do that?

----

This confirms that the wrong jwt library is STILL installed somewhere in your Conda environment, even though pip install PyJWT succeeded. Conda environments can hold both jwt (bad) and PyJWT (good) side-by-side, but Python will import jwt first because they share the same module name.


How to fix it cleanly

1. Remove the bad jwt package explicitly

pip uninstall jwt -y

Run again (just in case it’s installed twice):

pip uninstall jwt -y

2. Reinstall only PyJWT

pip install --force-reinstall PyJWT

3. Confirm

python -c "import jwt; print(jwt.__file__); print(jwt.__version__)"

Expected result: Path should show site-packages/jwt/ and version like 2.10.1 (not error).


4. Lock requirements.txt

Ensure requirements.txt has:

flask
requests
openai
Jinja2>=3.1.2
python-dotenv
pytz
PyJWT>=2.8.0

Remove jwt and dotenv.


Why this keeps happening

  • jwt (bad) and PyJWT (good) share the same module name (jwt).

  • If both are installed, Python might load the bad one.

  • Conda + pip mixing can leave old packages behind.


Do you want me to give you exact commands to nuke ALL traces of jwt from your Conda env (including checking Lib\site-packages) so you never see this again?
Or do you want me to rebuild the environment from scratch with a clean environment.yml I generate for you?

---

(echo) C:\Users\saad0\Documents\source\echo-private>python -c "import jwt; print(jwt.__version__); print('decode' in dir(jwt))" Traceback (most recent call last): File "<string>", line 1, in <module> AttributeError: module 'jwt' has no attribute '__version__' (echo) C:\Users\saad0\Documents\source\echo-private>

Issue: restart services

Your last command shows:

C:\Users\saad0\anaconda3\envs\echo\Lib\site-packages\jwt\__init__.py
2.10.1

This means PyJWT is now correctly installed and being used (version 2.10.1). So the “no attribute decode” issue should be gone in the interpreter.

But your browser error (ID token invalid: module 'jwt' has no attribute 'decode') suggests:

  • The running Flask app still had the bad module loaded in memory (from before you fixed it), or

  • Another copy of jwt.py is shadowing PyJWT in your project directory.


Fix Steps

1. Make sure no shadow file exists

Check your project for any jwt.py file:

dir /s /b jwt.py

If found in your project folder, rename or delete it — it will override PyJWT.


2. Restart the services

  • Stop all Python processes (CTRL+C all windows).

  • Close the CMD windows.

  • Reopen a fresh CMD, activate environment, and start services again:

conda activate echo
python logging_service.py
python parser_service.py
python api_gateway.py
python worker.py

3. Clear cached .pyc files

Run this in project root:

del /s /q __pycache__

(to remove any cached imports of bad jwt).


4. Confirm at runtime

In the same CMD where you run api_gateway.py, add a quick check:

python -c "import jwt; print(jwt.__version__); print('decode' in dir(jwt))"

Must print 2.10.1 and True.


After these steps

Visit http://localhost:5000 and log in again. The “no attribute decode” error should be gone.


Do you want me to give you a one-line check command you can put at the top of api_gateway.py to log the PyJWT version on startup (so you always know which library is loaded)?
This will prevent future confusion when debugging on cPanel too. Want that?

Comments

Popular posts from this blog

Feature: Audit log for one login, and identity service

Getting started - Build your data science lab environment

QA - Run #1 - Results