Сервер, который перенаправляет (через /login) пользователя к поставщику удостоверений, может отличаться от того, который запускает маршрут /auth.
Я могу создать URL-адрес перенаправления, используя IP-адрес сервера, выполняющего запрос /login, но мне это кажется неподходящим, особенно для keycloak разрешены URL-адреса перенаправления, которые будут статическими IP-адресами.
Вот фрагмент кода, который я написал:
Код: Выделить всё
oauth = OAuth()
oauth.register(
name="keycloak",
client_id=settings.keycloak.client_id,
client_secret=settings.keycloak.client_secret.get_secret_value(),
server_metadata_url=settings.keycloak.server_metadata_url,
# The group scope does not exist by default. This must be added.
client_kwargs={"scope": "openid email profile group"},
# The state is a value which is used as a kind of CSRF check.
# When the /login redirects to keycloak, it includes this value.
# Later, when keycloak redirects to /auth, it also includes the state value.
# If the values mismatche, a CSRF error is raised.
# Configuring it is required to perform replication.
state="toto",
)
oauth_client: StarletteOAuth2App = oauth.keycloak
def get_user_name(userinfo: dict):
"""Get the user name from user information dict."""
return userinfo.get("name", None) or userinfo.get("preferred_username")
@router.get("/login", tags=["user"])
async def login(request: Request):
"""Redirect the user to keycloak login page."""
redirect_uri = request.url_for("auth")
return await oauth_client.authorize_redirect(request, redirect_uri, state="toto")
@router.get("/auth", tags=["user"])
async def auth(request: Request):
"""Authenticate the user by creating a session cookie."""
token = await oauth_client.authorize_access_token(request)
userinfo = token["userinfo"]
# Needs json.dumps otherwise this is not correctly saved in session
request.session["user"] = json.dumps(userinfo)
_LOGGER.info("User %s got connected", get_user_name(userinfo))
# Get the URL the user requested before login, if any.
target_url = request.session.pop("target-url", "/")
return RedirectResponse(target_url)
Ключевым вопросом может быть значение параметра состояния, которое должно быть одинаковым на всех серверах. Тем не менее, в документации неясно, как его использовать. Кроме того, этот ответ указывает, что значение должно быть случайным, чтобы предотвратить атаки. Итак, как я мог это сделать?
Подробнее здесь: https://stackoverflow.com/questions/796 ... eb-servers
Мобильная версия