Files
group_xinghuo_jinrong/app/gateway/ownership.py
T
zhanghongyu_0626 3995cb44d8 Implement authentication and chat functionality with JWT support
- Added `auth.py` for mock login and JWT issuance.
- Introduced `chat.py` for handling chat requests with role-based access control.
- Enhanced `main.py` to include new routers and middleware for tracing.
- Implemented input validation in `input_guard.py` to prevent SQL injection.
- Created repositories for managing agent sessions and audit logs.
- Added exception handling for authorization errors.
- Updated settings to include JWT configuration.
- Introduced tests for authentication and input validation.
2026-09-07 17:20:42 +08:00

54 lines
2.0 KiB
Python

"""数据层归属校验(第二层)。"""
from __future__ import annotations
from app.gateway.jwt_service import permissions_for_roles
from app.model.schemas import AuthContext
from app.repository.advisor_rel_repository import AdvisorRelRepository
from app.repository.audit_repository import AuditRepository
from app.utils.exceptions import ForbiddenError
def audit_denied(ctx: AuthContext, error_code: str, customer_id: str | None) -> None:
AuditRepository().insert(
trace_id=ctx.trace_id,
event_type="auth_denied",
agent_type=ctx.agent_type,
actor_id=ctx.sub,
customer_id=customer_id,
decision=error_code,
input_summary={"roles": ctx.roles, "agent_type": ctx.agent_type},
)
def assert_customer_access(ctx: AuthContext, customer_id: str, *, action: str = "detail") -> None:
if ctx.token_type == "customer":
if ctx.sub != customer_id:
audit_denied(ctx, "AUTH_403_NOT_OWNER", customer_id)
raise ForbiddenError("无权访问该客户数据", error_code="AUTH_403_NOT_OWNER")
return
if "advisor" in ctx.roles:
if not AdvisorRelRepository().is_assigned(ctx.sub, customer_id):
audit_denied(ctx, "AUTH_403_NOT_ASSIGNED", customer_id)
raise ForbiddenError("客户不在您的服务名下", error_code="AUTH_403_NOT_ASSIGNED")
return
if "analyst" in ctx.roles:
if action == "detail" and "core:customer:read:detail" not in ctx.permissions:
audit_denied(ctx, "AUTH_403_SCOPE", customer_id)
raise ForbiddenError("分析员无客户明细权限", error_code="AUTH_403_SCOPE")
return
if "risk_officer" in ctx.roles:
return
audit_denied(ctx, "AUTH_403_ROLE", customer_id)
raise ForbiddenError("当前角色无权访问客户数据", error_code="AUTH_403_ROLE")
def resolve_effective_customer_id(ctx: AuthContext, requested: str | None) -> str | None:
if ctx.token_type == "customer":
return ctx.sub
return requested