mirror of https://github.com/tiangolo/fastapi.git
📝 Bring the `scope` claim in line with the standard in `docs_src/security/tutorial005.py` (#11189)
Co-authored-by: pre-commit-ci[bot] <66853113+pre-commit-ci[bot]@users.noreply.github.com> Co-authored-by: Yurii Motov <yurii.motov.monte@gmail.com>
This commit is contained in:
parent
cef1f166df
commit
e902ed5fc6
|
|
@ -62,7 +62,7 @@ Oauth2️⃣ 👫 🎻.
|
||||||
|
|
||||||
🥇, ➡️ 🔜 👀 🍕 👈 🔀 ⚪️➡️ 🖼 👑 **🔰 - 👩💻 🦮** [Oauth2️⃣ ⏮️ 🔐 (& 🔁), 📨 ⏮️ 🥙 🤝](../../tutorial/security/oauth2-jwt.md){.internal-link target=_blank}. 🔜 ⚙️ Oauth2️⃣ ↔:
|
🥇, ➡️ 🔜 👀 🍕 👈 🔀 ⚪️➡️ 🖼 👑 **🔰 - 👩💻 🦮** [Oauth2️⃣ ⏮️ 🔐 (& 🔁), 📨 ⏮️ 🥙 🤝](../../tutorial/security/oauth2-jwt.md){.internal-link target=_blank}. 🔜 ⚙️ Oauth2️⃣ ↔:
|
||||||
|
|
||||||
{* ../../docs_src/security/tutorial005.py hl[2,4,8,12,46,64,105,107:115,121:124,128:134,139,155] *}
|
{* ../../docs_src/security/tutorial005.py hl[2,4,8,12,46,64,105,107:115,121:125,129:135,140,156] *}
|
||||||
|
|
||||||
🔜 ➡️ 📄 👈 🔀 🔁 🔁.
|
🔜 ➡️ 📄 👈 🔀 🔁 🔁.
|
||||||
|
|
||||||
|
|
@ -98,7 +98,7 @@ Oauth2️⃣ 👫 🎻.
|
||||||
|
|
||||||
///
|
///
|
||||||
|
|
||||||
{* ../../docs_src/security/tutorial005.py hl[155] *}
|
{* ../../docs_src/security/tutorial005.py hl[156] *}
|
||||||
|
|
||||||
## 📣 ↔ *➡ 🛠️* & 🔗
|
## 📣 ↔ *➡ 🛠️* & 🔗
|
||||||
|
|
||||||
|
|
@ -124,7 +124,7 @@ Oauth2️⃣ 👫 🎻.
|
||||||
|
|
||||||
///
|
///
|
||||||
|
|
||||||
{* ../../docs_src/security/tutorial005.py hl[4,139,168] *}
|
{* ../../docs_src/security/tutorial005.py hl[4,140,169] *}
|
||||||
|
|
||||||
/// info | 📡 ℹ
|
/// info | 📡 ℹ
|
||||||
|
|
||||||
|
|
@ -180,7 +180,7 @@ Oauth2️⃣ 👫 🎻.
|
||||||
|
|
||||||
👥 ✔ 👈 👥 ✔️ 👩💻 ⏮️ 👈 🆔, & 🚥 🚫, 👥 🤚 👈 🎏 ⚠ 👥 ✍ ⏭.
|
👥 ✔ 👈 👥 ✔️ 👩💻 ⏮️ 👈 🆔, & 🚥 🚫, 👥 🤚 👈 🎏 ⚠ 👥 ✍ ⏭.
|
||||||
|
|
||||||
{* ../../docs_src/security/tutorial005.py hl[46,116:127] *}
|
{* ../../docs_src/security/tutorial005.py hl[46,116:128] *}
|
||||||
|
|
||||||
## ✔ `scopes`
|
## ✔ `scopes`
|
||||||
|
|
||||||
|
|
@ -188,7 +188,7 @@ Oauth2️⃣ 👫 🎻.
|
||||||
|
|
||||||
👉, 👥 ⚙️ `security_scopes.scopes`, 👈 🔌 `list` ⏮️ 🌐 👫 ↔ `str`.
|
👉, 👥 ⚙️ `security_scopes.scopes`, 👈 🔌 `list` ⏮️ 🌐 👫 ↔ `str`.
|
||||||
|
|
||||||
{* ../../docs_src/security/tutorial005.py hl[128:134] *}
|
{* ../../docs_src/security/tutorial005.py hl[129:135] *}
|
||||||
|
|
||||||
## 🔗 🌲 & ↔
|
## 🔗 🌲 & ↔
|
||||||
|
|
||||||
|
|
|
||||||
|
|
@ -62,7 +62,7 @@ For OAuth2 they are just strings.
|
||||||
|
|
||||||
First, let's quickly see the parts that change from the examples in the main **Tutorial - User Guide** for [OAuth2 with Password (and hashing), Bearer with JWT tokens](../../tutorial/security/oauth2-jwt.md){.internal-link target=_blank}. Now using OAuth2 scopes:
|
First, let's quickly see the parts that change from the examples in the main **Tutorial - User Guide** for [OAuth2 with Password (and hashing), Bearer with JWT tokens](../../tutorial/security/oauth2-jwt.md){.internal-link target=_blank}. Now using OAuth2 scopes:
|
||||||
|
|
||||||
{* ../../docs_src/security/tutorial005_an_py310.py hl[5,9,13,47,65,106,108:116,122:125,129:135,140,156] *}
|
{* ../../docs_src/security/tutorial005_an_py310.py hl[5,9,13,47,65,106,108:116,122:126,130:136,141,157] *}
|
||||||
|
|
||||||
Now let's review those changes step by step.
|
Now let's review those changes step by step.
|
||||||
|
|
||||||
|
|
@ -98,7 +98,7 @@ But in your application, for security, you should make sure you only add the sco
|
||||||
|
|
||||||
///
|
///
|
||||||
|
|
||||||
{* ../../docs_src/security/tutorial005_an_py310.py hl[156] *}
|
{* ../../docs_src/security/tutorial005_an_py310.py hl[157] *}
|
||||||
|
|
||||||
## Declare scopes in *path operations* and dependencies { #declare-scopes-in-path-operations-and-dependencies }
|
## Declare scopes in *path operations* and dependencies { #declare-scopes-in-path-operations-and-dependencies }
|
||||||
|
|
||||||
|
|
@ -124,7 +124,7 @@ We are doing it here to demonstrate how **FastAPI** handles scopes declared at d
|
||||||
|
|
||||||
///
|
///
|
||||||
|
|
||||||
{* ../../docs_src/security/tutorial005_an_py310.py hl[5,140,171] *}
|
{* ../../docs_src/security/tutorial005_an_py310.py hl[5,141,172] *}
|
||||||
|
|
||||||
/// info | Technical Details
|
/// info | Technical Details
|
||||||
|
|
||||||
|
|
@ -180,7 +180,7 @@ Instead of, for example, a `dict`, or something else, as it could break the appl
|
||||||
|
|
||||||
We also verify that we have a user with that username, and if not, we raise that same exception we created before.
|
We also verify that we have a user with that username, and if not, we raise that same exception we created before.
|
||||||
|
|
||||||
{* ../../docs_src/security/tutorial005_an_py310.py hl[47,117:128] *}
|
{* ../../docs_src/security/tutorial005_an_py310.py hl[47,117:129] *}
|
||||||
|
|
||||||
## Verify the `scopes` { #verify-the-scopes }
|
## Verify the `scopes` { #verify-the-scopes }
|
||||||
|
|
||||||
|
|
@ -188,7 +188,7 @@ We now verify that all the scopes required, by this dependency and all the depen
|
||||||
|
|
||||||
For this, we use `security_scopes.scopes`, that contains a `list` with all these scopes as `str`.
|
For this, we use `security_scopes.scopes`, that contains a `list` with all these scopes as `str`.
|
||||||
|
|
||||||
{* ../../docs_src/security/tutorial005_an_py310.py hl[129:135] *}
|
{* ../../docs_src/security/tutorial005_an_py310.py hl[130:136] *}
|
||||||
|
|
||||||
## Dependency tree and scopes { #dependency-tree-and-scopes }
|
## Dependency tree and scopes { #dependency-tree-and-scopes }
|
||||||
|
|
||||||
|
|
|
||||||
|
|
@ -119,7 +119,8 @@ async def get_current_user(
|
||||||
username: str = payload.get("sub")
|
username: str = payload.get("sub")
|
||||||
if username is None:
|
if username is None:
|
||||||
raise credentials_exception
|
raise credentials_exception
|
||||||
token_scopes = payload.get("scopes", [])
|
scope: str = payload.get("scope", "")
|
||||||
|
token_scopes = scope.split(" ")
|
||||||
token_data = TokenData(scopes=token_scopes, username=username)
|
token_data = TokenData(scopes=token_scopes, username=username)
|
||||||
except (InvalidTokenError, ValidationError):
|
except (InvalidTokenError, ValidationError):
|
||||||
raise credentials_exception
|
raise credentials_exception
|
||||||
|
|
@ -153,7 +154,7 @@ async def login_for_access_token(
|
||||||
raise HTTPException(status_code=400, detail="Incorrect username or password")
|
raise HTTPException(status_code=400, detail="Incorrect username or password")
|
||||||
access_token_expires = timedelta(minutes=ACCESS_TOKEN_EXPIRE_MINUTES)
|
access_token_expires = timedelta(minutes=ACCESS_TOKEN_EXPIRE_MINUTES)
|
||||||
access_token = create_access_token(
|
access_token = create_access_token(
|
||||||
data={"sub": user.username, "scopes": form_data.scopes},
|
data={"sub": user.username, "scope": " ".join(form_data.scopes)},
|
||||||
expires_delta=access_token_expires,
|
expires_delta=access_token_expires,
|
||||||
)
|
)
|
||||||
return Token(access_token=access_token, token_type="bearer")
|
return Token(access_token=access_token, token_type="bearer")
|
||||||
|
|
|
||||||
|
|
@ -120,7 +120,8 @@ async def get_current_user(
|
||||||
username = payload.get("sub")
|
username = payload.get("sub")
|
||||||
if username is None:
|
if username is None:
|
||||||
raise credentials_exception
|
raise credentials_exception
|
||||||
token_scopes = payload.get("scopes", [])
|
scope: str = payload.get("scope", "")
|
||||||
|
token_scopes = scope.split(" ")
|
||||||
token_data = TokenData(scopes=token_scopes, username=username)
|
token_data = TokenData(scopes=token_scopes, username=username)
|
||||||
except (InvalidTokenError, ValidationError):
|
except (InvalidTokenError, ValidationError):
|
||||||
raise credentials_exception
|
raise credentials_exception
|
||||||
|
|
@ -154,7 +155,7 @@ async def login_for_access_token(
|
||||||
raise HTTPException(status_code=400, detail="Incorrect username or password")
|
raise HTTPException(status_code=400, detail="Incorrect username or password")
|
||||||
access_token_expires = timedelta(minutes=ACCESS_TOKEN_EXPIRE_MINUTES)
|
access_token_expires = timedelta(minutes=ACCESS_TOKEN_EXPIRE_MINUTES)
|
||||||
access_token = create_access_token(
|
access_token = create_access_token(
|
||||||
data={"sub": user.username, "scopes": form_data.scopes},
|
data={"sub": user.username, "scope": " ".join(form_data.scopes)},
|
||||||
expires_delta=access_token_expires,
|
expires_delta=access_token_expires,
|
||||||
)
|
)
|
||||||
return Token(access_token=access_token, token_type="bearer")
|
return Token(access_token=access_token, token_type="bearer")
|
||||||
|
|
|
||||||
|
|
@ -119,7 +119,8 @@ async def get_current_user(
|
||||||
username = payload.get("sub")
|
username = payload.get("sub")
|
||||||
if username is None:
|
if username is None:
|
||||||
raise credentials_exception
|
raise credentials_exception
|
||||||
token_scopes = payload.get("scopes", [])
|
scope: str = payload.get("scope", "")
|
||||||
|
token_scopes = scope.split(" ")
|
||||||
token_data = TokenData(scopes=token_scopes, username=username)
|
token_data = TokenData(scopes=token_scopes, username=username)
|
||||||
except (InvalidTokenError, ValidationError):
|
except (InvalidTokenError, ValidationError):
|
||||||
raise credentials_exception
|
raise credentials_exception
|
||||||
|
|
@ -153,7 +154,7 @@ async def login_for_access_token(
|
||||||
raise HTTPException(status_code=400, detail="Incorrect username or password")
|
raise HTTPException(status_code=400, detail="Incorrect username or password")
|
||||||
access_token_expires = timedelta(minutes=ACCESS_TOKEN_EXPIRE_MINUTES)
|
access_token_expires = timedelta(minutes=ACCESS_TOKEN_EXPIRE_MINUTES)
|
||||||
access_token = create_access_token(
|
access_token = create_access_token(
|
||||||
data={"sub": user.username, "scopes": form_data.scopes},
|
data={"sub": user.username, "scope": " ".join(form_data.scopes)},
|
||||||
expires_delta=access_token_expires,
|
expires_delta=access_token_expires,
|
||||||
)
|
)
|
||||||
return Token(access_token=access_token, token_type="bearer")
|
return Token(access_token=access_token, token_type="bearer")
|
||||||
|
|
|
||||||
|
|
@ -119,7 +119,8 @@ async def get_current_user(
|
||||||
username = payload.get("sub")
|
username = payload.get("sub")
|
||||||
if username is None:
|
if username is None:
|
||||||
raise credentials_exception
|
raise credentials_exception
|
||||||
token_scopes = payload.get("scopes", [])
|
scope: str = payload.get("scope", "")
|
||||||
|
token_scopes = scope.split(" ")
|
||||||
token_data = TokenData(scopes=token_scopes, username=username)
|
token_data = TokenData(scopes=token_scopes, username=username)
|
||||||
except (InvalidTokenError, ValidationError):
|
except (InvalidTokenError, ValidationError):
|
||||||
raise credentials_exception
|
raise credentials_exception
|
||||||
|
|
@ -153,7 +154,7 @@ async def login_for_access_token(
|
||||||
raise HTTPException(status_code=400, detail="Incorrect username or password")
|
raise HTTPException(status_code=400, detail="Incorrect username or password")
|
||||||
access_token_expires = timedelta(minutes=ACCESS_TOKEN_EXPIRE_MINUTES)
|
access_token_expires = timedelta(minutes=ACCESS_TOKEN_EXPIRE_MINUTES)
|
||||||
access_token = create_access_token(
|
access_token = create_access_token(
|
||||||
data={"sub": user.username, "scopes": form_data.scopes},
|
data={"sub": user.username, "scope": " ".join(form_data.scopes)},
|
||||||
expires_delta=access_token_expires,
|
expires_delta=access_token_expires,
|
||||||
)
|
)
|
||||||
return Token(access_token=access_token, token_type="bearer")
|
return Token(access_token=access_token, token_type="bearer")
|
||||||
|
|
|
||||||
|
|
@ -118,7 +118,8 @@ async def get_current_user(
|
||||||
username: str = payload.get("sub")
|
username: str = payload.get("sub")
|
||||||
if username is None:
|
if username is None:
|
||||||
raise credentials_exception
|
raise credentials_exception
|
||||||
token_scopes = payload.get("scopes", [])
|
scope: str = payload.get("scope", "")
|
||||||
|
token_scopes = scope.split(" ")
|
||||||
token_data = TokenData(scopes=token_scopes, username=username)
|
token_data = TokenData(scopes=token_scopes, username=username)
|
||||||
except (InvalidTokenError, ValidationError):
|
except (InvalidTokenError, ValidationError):
|
||||||
raise credentials_exception
|
raise credentials_exception
|
||||||
|
|
@ -152,7 +153,7 @@ async def login_for_access_token(
|
||||||
raise HTTPException(status_code=400, detail="Incorrect username or password")
|
raise HTTPException(status_code=400, detail="Incorrect username or password")
|
||||||
access_token_expires = timedelta(minutes=ACCESS_TOKEN_EXPIRE_MINUTES)
|
access_token_expires = timedelta(minutes=ACCESS_TOKEN_EXPIRE_MINUTES)
|
||||||
access_token = create_access_token(
|
access_token = create_access_token(
|
||||||
data={"sub": user.username, "scopes": form_data.scopes},
|
data={"sub": user.username, "scope": " ".join(form_data.scopes)},
|
||||||
expires_delta=access_token_expires,
|
expires_delta=access_token_expires,
|
||||||
)
|
)
|
||||||
return Token(access_token=access_token, token_type="bearer")
|
return Token(access_token=access_token, token_type="bearer")
|
||||||
|
|
|
||||||
|
|
@ -119,7 +119,8 @@ async def get_current_user(
|
||||||
username: str = payload.get("sub")
|
username: str = payload.get("sub")
|
||||||
if username is None:
|
if username is None:
|
||||||
raise credentials_exception
|
raise credentials_exception
|
||||||
token_scopes = payload.get("scopes", [])
|
scope: str = payload.get("scope", "")
|
||||||
|
token_scopes = scope.split(" ")
|
||||||
token_data = TokenData(scopes=token_scopes, username=username)
|
token_data = TokenData(scopes=token_scopes, username=username)
|
||||||
except (InvalidTokenError, ValidationError):
|
except (InvalidTokenError, ValidationError):
|
||||||
raise credentials_exception
|
raise credentials_exception
|
||||||
|
|
@ -153,7 +154,7 @@ async def login_for_access_token(
|
||||||
raise HTTPException(status_code=400, detail="Incorrect username or password")
|
raise HTTPException(status_code=400, detail="Incorrect username or password")
|
||||||
access_token_expires = timedelta(minutes=ACCESS_TOKEN_EXPIRE_MINUTES)
|
access_token_expires = timedelta(minutes=ACCESS_TOKEN_EXPIRE_MINUTES)
|
||||||
access_token = create_access_token(
|
access_token = create_access_token(
|
||||||
data={"sub": user.username, "scopes": form_data.scopes},
|
data={"sub": user.username, "scope": " ".join(form_data.scopes)},
|
||||||
expires_delta=access_token_expires,
|
expires_delta=access_token_expires,
|
||||||
)
|
)
|
||||||
return Token(access_token=access_token, token_type="bearer")
|
return Token(access_token=access_token, token_type="bearer")
|
||||||
|
|
|
||||||
Loading…
Reference in New Issue