mirror of https://github.com/langgenius/dify.git
fix(api): add session_id validation for webapp JWT authentication (#28297)
Co-authored-by: autofix-ci[bot] <114827586+autofix-ci[bot]@users.noreply.github.com>
This commit is contained in:
parent
3cf19dc07f
commit
a4c4d18f42
|
|
@ -81,6 +81,7 @@ class LoginStatusApi(Resource):
|
|||
)
|
||||
def get(self):
|
||||
app_code = request.args.get("app_code")
|
||||
user_id = request.args.get("user_id")
|
||||
token = extract_webapp_access_token(request)
|
||||
if not app_code:
|
||||
return {
|
||||
|
|
@ -103,7 +104,7 @@ class LoginStatusApi(Resource):
|
|||
user_logged_in = False
|
||||
|
||||
try:
|
||||
_ = decode_jwt_token(app_code=app_code)
|
||||
_ = decode_jwt_token(app_code=app_code, user_id=user_id)
|
||||
app_logged_in = True
|
||||
except Exception:
|
||||
app_logged_in = False
|
||||
|
|
|
|||
|
|
@ -38,7 +38,7 @@ def validate_jwt_token(view: Callable[Concatenate[App, EndUser, P], R] | None =
|
|||
return decorator
|
||||
|
||||
|
||||
def decode_jwt_token(app_code: str | None = None):
|
||||
def decode_jwt_token(app_code: str | None = None, user_id: str | None = None):
|
||||
system_features = FeatureService.get_system_features()
|
||||
if not app_code:
|
||||
app_code = str(request.headers.get(HEADER_NAME_APP_CODE))
|
||||
|
|
@ -63,6 +63,10 @@ def decode_jwt_token(app_code: str | None = None):
|
|||
if not end_user:
|
||||
raise NotFound()
|
||||
|
||||
# Validate user_id against end_user's session_id if provided
|
||||
if user_id is not None and end_user.session_id != user_id:
|
||||
raise Unauthorized("Authentication has expired.")
|
||||
|
||||
# for enterprise webapp auth
|
||||
app_web_auth_enabled = False
|
||||
webapp_settings = None
|
||||
|
|
|
|||
|
|
@ -58,7 +58,7 @@ const Splash: FC<PropsWithChildren> = ({ children }) => {
|
|||
|
||||
(async () => {
|
||||
// if access mode is public, user login is always true, but the app login(passport) may be expired
|
||||
const { userLoggedIn, appLoggedIn } = await webAppLoginStatus(shareCode!)
|
||||
const { userLoggedIn, appLoggedIn } = await webAppLoginStatus(shareCode!, embeddedUserId || undefined)
|
||||
if (userLoggedIn && appLoggedIn) {
|
||||
redirectOrFinish()
|
||||
}
|
||||
|
|
|
|||
|
|
@ -30,10 +30,13 @@ type isWebAppLogin = {
|
|||
app_logged_in: boolean
|
||||
}
|
||||
|
||||
export async function webAppLoginStatus(shareCode: string) {
|
||||
export async function webAppLoginStatus(shareCode: string, userId?: string) {
|
||||
// always need to check login to prevent passport from being outdated
|
||||
// check remotely, the access token could be in cookie (enterprise SSO redirected with https)
|
||||
const { logged_in, app_logged_in } = await getPublic<isWebAppLogin>(`/login/status?app_code=${shareCode}`)
|
||||
const params = new URLSearchParams({ app_code: shareCode })
|
||||
if (userId)
|
||||
params.append('user_id', userId)
|
||||
const { logged_in, app_logged_in } = await getPublic<isWebAppLogin>(`/login/status?${params.toString()}`)
|
||||
return {
|
||||
userLoggedIn: logged_in,
|
||||
appLoggedIn: app_logged_in,
|
||||
|
|
|
|||
Loading…
Reference in New Issue