From 46e24b0a5aa507b433658014d2a644cca2463f7b Mon Sep 17 00:00:00 2001 From: Zach Sailer Date: Tue, 21 Feb 2023 08:25:17 -0800 Subject: [PATCH] ake JS 2.0 identity provider backwards compatible with classic server's auth model --- jupyter_server/auth/identity.py | 3 ++- jupyter_server/base/handlers.py | 23 +++++++++++++++++++++-- 2 files changed, 23 insertions(+), 3 deletions(-) diff --git a/jupyter_server/auth/identity.py b/jupyter_server/auth/identity.py index 42c4ce839a..e12858bc8b 100644 --- a/jupyter_server/auth/identity.py +++ b/jupyter_server/auth/identity.py @@ -236,7 +236,8 @@ async def _get_user(self, handler: JupyterHandler) -> User | None: _token_user: User | None | Awaitable[User | None] = self.get_user_token(handler) if isinstance(_token_user, Awaitable): _token_user = await _token_user - token_user: User | None = _token_user # need second variable name to collapse type + # need second variable name to collapse type + token_user: User | None = _token_user _cookie_user = self.get_user_cookie(handler) if isinstance(_cookie_user, Awaitable): _cookie_user = await _cookie_user diff --git a/jupyter_server/base/handlers.py b/jupyter_server/base/handlers.py index 061eea672a..57f0b15ef3 100644 --- a/jupyter_server/base/handlers.py +++ b/jupyter_server/base/handlers.py @@ -251,9 +251,28 @@ def identity_provider(self): ) from jupyter_server.auth import IdentityProvider - # no identity provider set, load default + non_alphanum = re.compile(r"[^A-Za-z0-9]") + default_cookie_name = non_alphanum.sub("-", f"username-{self.request.host}") + + # If there is no identity provider set, load the default. If using + # a classic notebook server, adding extensions that inherit + # from JupyterHandler will use a mix of new+old authentication log. + # Here, we construct an identity provider that works side-by-side + # and consistently with the old way that we handled auth in + # the classic server. self.settings["identity_provider"] = IdentityProvider( - config=self.settings.get("config", None) + config=self.settings.get("config", None), + # For backwards compatibility, pass the token + # from the webapp settings. + token=self.settings.get("token", ""), + # Prefix the cookie name with "model-" to avoid colliding with + # the cookie set by the classic server. + # NOTE: This creates two cookies to authenticate the user + # (1) the token cookie and (2) the user model cookie. + cookie_name="model-" + self.settings.get("cookie_name", default_cookie_name), + cookie_options=self.settings.get("cookie_options", {}), + secure_cookie=self.settings.get("secure_cookie", None), + get_secure_cookie_kwargs=self.settings.get("get_secure_cookie_kwargs", {}), ) return self.settings["identity_provider"]