feat: add granted_at

pull/20494/head
GareArc 11 months ago
parent 88c59f06cb
commit 50d80f6d71
No known key found for this signature in database

@ -1,18 +1,17 @@
import uuid import uuid
from datetime import UTC, datetime, timedelta from datetime import UTC, datetime, timedelta
from flask import request
from flask_restful import Resource
from werkzeug.exceptions import NotFound, Unauthorized
from configs import dify_config from configs import dify_config
from controllers.web import api from controllers.web import api
from controllers.web.error import WebAppAuthRequiredError from controllers.web.error import WebAppAuthRequiredError
from extensions.ext_database import db from extensions.ext_database import db
from flask import request
from flask_restful import Resource
from libs.passport import PassportService from libs.passport import PassportService
from models.model import App, EndUser, Site from models.model import App, EndUser, Site
from services.enterprise.enterprise_service import EnterpriseService from services.enterprise.enterprise_service import EnterpriseService
from services.feature_service import FeatureService from services.feature_service import FeatureService
from werkzeug.exceptions import NotFound, Unauthorized
class PassportResource(Resource): class PassportResource(Resource):
@ -104,8 +103,23 @@ def decode_enterprise_webapp_user_id(jwt_token: str | None):
decoded = PassportService().verify(jwt_token) decoded = PassportService().verify(jwt_token)
source = decoded.get("token_source") source = decoded.get("token_source")
auth_type = decoded.get("auth_type")
granted_at = decoded.get("granted_at")
if not source or source != "webapp_login_token": if not source or source != "webapp_login_token":
raise Unauthorized("Invalid token source. Expected 'webapp_login_token'.") raise Unauthorized("Invalid token source. Expected 'webapp_login_token'.")
if not auth_type:
raise Unauthorized("Missing auth_type in the token.")
if not granted_at:
raise Unauthorized("Missing granted_at in the token.")
# check if sso has been updated
if auth_type == "external":
last_update_time = EnterpriseService.get_app_sso_settings_last_update_time()
if granted_at and datetime.fromisoformat(granted_at) < last_update_time:
raise Unauthorized("SSO settings have been updated. Please re-login.")
elif auth_type == "internal":
last_update_time = EnterpriseService.get_workspace_sso_settings_last_update_time()
if granted_at and datetime.fromisoformat(granted_at) < last_update_time:
raise Unauthorized("SSO settings have been updated. Please re-login.")
return decoded return decoded

@ -1,5 +1,6 @@
from pydantic import BaseModel, Field from datetime import datetime
from pydantic import BaseModel, Field
from services.enterprise.base import EnterpriseRequest from services.enterprise.base import EnterpriseRequest
@ -20,6 +21,30 @@ class EnterpriseService:
def get_workspace_info(cls, tenant_id: str): def get_workspace_info(cls, tenant_id: str):
return EnterpriseRequest.send_request("GET", f"/workspace/{tenant_id}/info") return EnterpriseRequest.send_request("GET", f"/workspace/{tenant_id}/info")
@classmethod
def get_app_sso_settings_last_update_time(cls) -> datetime:
data = EnterpriseRequest.send_request("GET", "/sso/app/last-update-time")
print(data)
if not data:
raise ValueError("No data found.")
try:
# parse the UTC timestamp from the response
return datetime.fromisoformat(data.replace("Z", "+00:00"))
except ValueError as e:
raise ValueError(f"Invalid date format: {data}") from e
@classmethod
def get_workspace_sso_settings_last_update_time(cls) -> datetime:
data = EnterpriseRequest.send_request("GET", "/sso/workspace/last-update-time")
print(data)
if not data:
raise ValueError("No data found.")
try:
# parse the UTC timestamp from the response
return datetime.fromisoformat(data.replace("Z", "+00:00"))
except ValueError as e:
raise ValueError(f"Invalid date format: {data}") from e
class WebAppAuth: class WebAppAuth:
@classmethod @classmethod
def is_user_allowed_to_access_webapp(cls, user_id: str, app_code: str): def is_user_allowed_to_access_webapp(cls, user_id: str, app_code: str):

@ -2,8 +2,6 @@ import random
from datetime import UTC, datetime, timedelta from datetime import UTC, datetime, timedelta
from typing import Any, Optional, cast from typing import Any, Optional, cast
from werkzeug.exceptions import NotFound, Unauthorized
from configs import dify_config from configs import dify_config
from extensions.ext_database import db from extensions.ext_database import db
from libs.helper import TokenManager from libs.helper import TokenManager
@ -13,8 +11,10 @@ from models.account import Account, AccountStatus
from models.model import App, EndUser, Site from models.model import App, EndUser, Site
from services.app_service import AppService from services.app_service import AppService
from services.enterprise.enterprise_service import EnterpriseService from services.enterprise.enterprise_service import EnterpriseService
from services.errors.account import AccountLoginError, AccountNotFoundError, AccountPasswordError from services.errors.account import (AccountLoginError, AccountNotFoundError,
AccountPasswordError)
from tasks.mail_email_code_login import send_email_code_login_mail_task from tasks.mail_email_code_login import send_email_code_login_mail_task
from werkzeug.exceptions import NotFound, Unauthorized
class WebAppAuthService: class WebAppAuthService:
@ -113,6 +113,7 @@ class WebAppAuthService:
"session_id": account.email, "session_id": account.email,
"token_source": "webapp_login_token", "token_source": "webapp_login_token",
"auth_type": "internal", "auth_type": "internal",
"granted_at": datetime.now(UTC).isoformat(),
"exp": exp, "exp": exp,
} }

Loading…
Cancel
Save