Skip to content

refactor(db): introduce ContextVar DAO layer and optimize transaction granularity#678

Merged
yaojin3616 merged 4 commits into
mainfrom
refactor/db-session-and-transactions
Jun 15, 2026
Merged

refactor(db): introduce ContextVar DAO layer and optimize transaction granularity#678
yaojin3616 merged 4 commits into
mainfrom
refactor/db-session-and-transactions

Conversation

@yaojin3616

Copy link
Copy Markdown
Collaborator

💡 Proposed Changes

This PR introduces two major database-related optimizations and a file encoding fix:

  1. Introduced ContextVar-based DAO Layer:
    • Encapsulated standard SQLAlchemy operations inside database Access Objects (DAO).
    • Resolved active AsyncSession seamlessly using ContextVar (_session_ctx), eliminating the need to explicitly pass db/session arguments through registry services, helpers, and handlers.
  2. Optimized DB Transaction Granularity in Auth API:
    • Relocated slow password crypto (e.g. verify_password_async, hash_password_async), external third-party network calls, Redis interactions, and read-only SELECT queries outside async with transaction() blocks.
    • Reduced SQL connection duration from hundreds of milliseconds (during cryptography) down to less than 5ms (simple SELECT/UPDATE).
  3. Email Attachment Non-ASCII Encoding Fix:
    • Handled non-ASCII filenames for email attachments in compliance with RFC standards.

🧪 Verification

Verified that all 38 tests in the authentication, onboarding, registry, password reset, and SSO modules pass cleanly.

@chatgpt-codex-connector chatgpt-codex-connector Bot left a comment

Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

💡 Codex Review

Here are some automated review suggestions for this pull request.

Reviewed commit: 5a72456380

ℹ️ About Codex in GitHub

Codex has been enabled to automatically review pull requests in this repo. Reviews are triggered when you

  • Open a pull request for review
  • Mark a draft as ready
  • Comment "@codex review".

If Codex has suggestions, it will comment; otherwise it will react with 👍.

When you sign up for Codex through ChatGPT, Codex can also answer questions or update the PR, like "@codex address that feedback".

Comment thread backend/app/dao/base.py
Comment on lines +26 to +27
async with async_session() as session:
yield session

Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

P1 Badge Preserve DAO writes outside explicit transactions

When no ContextVar transaction is active, this fallback opens a fresh AsyncSession and yields it, but the DAO write helpers only flush() and this context closes without committing. Several refactored callers still already have a request/session but are not wrapped in transaction() (for example BaseAuthProvider._create_new_user now calls find_or_create_identity(...) without passing its db), so first-time SSO/channel identity creation is rolled back before the subsequent User insert references it, leading to missing identities or FK failures. Bind the caller's session into the context or ensure standalone DAO write sessions commit/rollback.

Useful? React with 👍 / 👎.

"""
# ── OrgMember binding ────────────────────────────────────────────────────

async def bind_org_member(self, user: User) -> None:

Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

P1 Badge Keep bind_org_member compatible with tenant joins

Changing bind_org_member to accept only user leaves existing tenant join/create paths still calling registration_service.bind_org_member(db, new_user/current_user) in backend/app/api/tenants.py (checked lines 216, 230, 344, and 361). Those endpoints will now raise TypeError: ... takes 2 positional arguments but 3 were given after flushing user changes and before committing whenever a user creates or joins an organization/invitation, so update those call sites or retain a compatible signature.

Useful? React with 👍 / 👎.

@chatgpt-codex-connector chatgpt-codex-connector Bot left a comment

Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

💡 Codex Review

Here are some automated review suggestions for this pull request.

Reviewed commit: da0f469b55

ℹ️ About Codex in GitHub

Codex has been enabled to automatically review pull requests in this repo. Reviews are triggered when you

  • Open a pull request for review
  • Mark a draft as ready
  • Comment "@codex review".

If Codex has suggestions, it will comment; otherwise it will react with 👍.

When you sign up for Codex through ChatGPT, Codex can also answer questions or update the PR, like "@codex address that feedback".

tenant,
request: Request | None = None,
*,
sso_redirect_enabled: bool = True,

Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

P2 Badge Restore SSO redirect flag lookup for tenant URLs

With this default the helper no longer reads sso_custom_domain_redirect_enabled; I checked current call sites, and /sso/config, Google Workspace redirects, and enterprise auto-assignment still call get_tenant_sso_base_url(...) without the new argument (backend/app/api/sso.py:113, backend/app/services/google_workspace_oauth.py:82, backend/app/api/enterprise.py:786). In installations where admins disabled custom-domain SSO redirects, those flows will still build tenant-domain/subdomain URLs, so OAuth callbacks can be sent to domains they explicitly disabled.

Useful? React with 👍 / 👎.

tool_name = fn["name"]
raw_args = fn.get("arguments", "{}")
logger.info(f"[LLM] Calling tool: {tool_name}({json.dumps(raw_args, ensure_ascii=False)[:100]})")
logger.info(f"[LLM] Calling tool: {tool_name}({json.dumps(raw_args, ensure_ascii=False)})")

Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

P2 Badge Avoid logging full tool-call arguments

When a tool call includes long or sensitive arguments (for example email bodies/attachments, MCP config secrets, or file contents passed to write/edit tools), this now emits the entire argument JSON to application logs; before this change it was capped at 100 characters. In production that can leak user content or secrets and can bloat logs for large tool calls, so keep truncation or add redaction here.

Useful? React with 👍 / 👎.

@yaojin3616 yaojin3616 merged commit 60ffcb0 into main Jun 15, 2026
1 check was pending
zhangshubin01 pushed a commit to zhangshubin01/Clawith that referenced this pull request Jun 15, 2026
合并 main 分支最新变更:
- chore(release): cut v1.10.2 (dataelement#679)
- refactor(db): ContextVar DAO layer + transaction granularity (dataelement#678)

冲突解决策略:
- database/auth_registry/email/platform/password/system_email: 保留 ours (日志前缀)
- agents/auth/registration/caller/AgentDetailPage/docker-compose: 采用 theirs (main 最新)
zhangshubin01 pushed a commit to zhangshubin01/Clawith that referenced this pull request Jun 15, 2026
- database.py: 添加 _session_ctx ContextVar + transaction() (main dataelement#678 DAO 层依赖)
- caller.py: 添加 _format_friendly_error (lsp4j jsonrpc_router 依赖)
- migration add_chat_message_query_index: SQLAlchemy 2.0 兼容 (engine.connect)
- docker-compose.yml: 恢复 backend ports 映射 (合并时丢失)
@yaojin3616 yaojin3616 deleted the refactor/db-session-and-transactions branch June 16, 2026 09:51
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

1 participant