Skip to content

Commit ce773ec

Browse files
committed
add user authorization using jwt groups claim
1 parent 67a70bf commit ce773ec

5 files changed

Lines changed: 122 additions & 1 deletion

File tree

VSCODE.md

Lines changed: 101 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,101 @@
1+
## VS Code development
2+
3+
To run and debug the Clowder frontend and backend apps in VS Code IDE from the
4+
WSL Ubuntu 24.04 LTS distribution
5+
6+
1. Start VS Code, install the WSL (Windows Subsystem for Linux) extension,
7+
then exit
8+
9+
2. Open Ubuntu 24.04 WSL terminal and clone the clowder2 repo
10+
11+
```
12+
git clone https://github.com/clowder-framework/clowder2.git
13+
cd clowder2
14+
```
15+
16+
3. Install NPM needed for building frontend
17+
18+
```
19+
sudo apt install npm
20+
```
21+
22+
4. Install frontend dependencies
23+
24+
```
25+
cd frontend
26+
npm install
27+
cd ..
28+
```
29+
30+
5. Install Python version needed for backend, eg.
31+
32+
```
33+
wget http://www.python.org/ftp/python/3.10.19/Python-3.10.19.tgz
34+
tar xzf Python-3.10.19.tgz
35+
mkdir $HOME/.local/python
36+
cd Python-3.10.19/
37+
./configure --prefix=$HOME/.local/python
38+
make
39+
make install
40+
```
41+
42+
6. Create a Python virtualenv and install backend dependencies
43+
44+
```
45+
cd clowder2
46+
$HOME/.local/python/bin/python3 -m venv venv
47+
. venv/bin/activate
48+
pip install .
49+
deactivate
50+
```
51+
52+
7. Start local docker dependencies
53+
54+
```
55+
cd clowder2
56+
docker compose -f docker-compose.dev.yml -p clowder2-dev up -d
57+
# to stop use
58+
docker compose -p clowder2-dev down
59+
```
60+
61+
8. Add TCP proxy ports for forwarding Windows browser connections for the
62+
frontend, backend and Keycloak to WSL
63+
64+
Get WSL IP address for `eth0` in WSL terminal
65+
66+
```
67+
ip -br a show dev eth0
68+
```
69+
70+
Add TCP proxy ports in PowerShell admin terminal
71+
72+
```
73+
netsh interface portproxy show v4tov4
74+
netsh interface portproxy add v4tov4 listenport=3000 listenaddress=0.0.0.0 connectport=3000 connectaddress=<eth0_ip>
75+
netsh interface portproxy add v4tov4 listenport=8000 listenaddress=0.0.0.0 connectport=8000 connectaddress=<eth0_ip>
76+
netsh interface portproxy add v4tov4 listenport=8080 listenaddress=0.0.0.0 connectport=8080 connectaddress=<eth0_ip>
77+
```
78+
79+
9. Start VS Code from your WSL terminal
80+
81+
```
82+
cd clowder2
83+
code .
84+
```
85+
86+
10. Set the VS Code Python interpreter
87+
88+
1. Open Command Palette (Ctrl+Shift+P)
89+
2. Click **Python: Select Interpreter** from list, set it to `./venv/bin/python`
90+
91+
11. Start Clowder backend in VS Code Run and Debug view
92+
93+
1. Select **Python Debugger: FastAPI**
94+
2. Click **Start Debugging**
95+
96+
12. Start Clowder frontend in VS Code Run and Debug view
97+
98+
1. Select **Launch via npm**
99+
2. Click **Start Debugging**
100+
101+
13. Open [Clowder](http://localhost:3000/) in your Windows Edge or Chrome browser

backend/app/config.py

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -59,6 +59,7 @@ class Settings(BaseSettings):
5959
)
6060
auth_server_url = f"{auth_base}/keycloak/"
6161
auth_client_secret = ""
62+
auth_role = "clowder2"
6263

6364
# keycloak local config
6465
keycloak_username = "admin"

backend/app/keycloak_auth.py

Lines changed: 10 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -62,7 +62,7 @@ async def get_token(
6262
if token:
6363
try:
6464
# See https://github.com/marcospereirampj/python-keycloak/issues/89
65-
return keycloak_openid.decode_token(
65+
payload = keycloak_openid.decode_token(
6666
token,
6767
key=await get_idp_public_key(),
6868
options={"verify_aud": False},
@@ -85,6 +85,15 @@ async def get_token(
8585
detail=str(e),
8686
headers={"WWW-Authenticate": "Bearer"},
8787
)
88+
if settings.auth_role:
89+
groups: list = payload.get("groups", {})
90+
if settings.auth_role not in groups:
91+
raise HTTPException(
92+
status_code=403,
93+
detail="Not authorized.",
94+
headers={"WWW-Authenticate": "Bearer"},
95+
)
96+
return payload
8897

8998
if api_key:
9099
serializer = URLSafeSerializer(settings.local_auth_secret, salt="api_key")

frontend/src/types/action.ts

Lines changed: 7 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -293,6 +293,12 @@ interface NOT_FOUND_INLINE {
293293
reason: string;
294294
}
295295

296+
interface NOT_AUTHORIZED {
297+
stack: string;
298+
type: "NOT_AUTHORIZED";
299+
reason: string;
300+
}
301+
296302
interface RESET_FAILED {
297303
type: "RESET_FAILED";
298304
reason: string;
@@ -777,6 +783,7 @@ export type DataAction =
777783
| FAILED_INLINE
778784
| NOT_FOUND
779785
| NOT_FOUND_INLINE
786+
| NOT_AUTHORIZED
780787
| RESET_FAILED
781788
| RESET_FAILED_INLINE
782789
| RESET_LOGOUT

pyproject.toml

Lines changed: 3 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -7,6 +7,7 @@ description = """Clowder is a cloud native data management framework to support
77
readme = "README.md"
88
requires-python = ">=3.10"
99
dependencies = [
10+
"charset_normalizer==3.4.0",
1011
"fastapi==0.95.1",
1112
"pydantic==1.10.13",
1213
"uvicorn==0.21.1",
@@ -45,3 +46,5 @@ dev = [
4546
docs = [
4647
"mkdocs-material"
4748
]
49+
[tool.setuptools]
50+
py-modules = []

0 commit comments

Comments
 (0)