Skip to content

feat(integrations): support switching Lark app credentials - #4703

Open
18062706139fcz wants to merge 4 commits into
bytedance:mainfrom
18062706139fcz:feat/feishu-switch-bot
Open

feat(integrations): support switching Lark app credentials#4703
18062706139fcz wants to merge 4 commits into
bytedance:mainfrom
18062706139fcz:feat/feishu-switch-bot

Conversation

@18062706139fcz

@18062706139fcz 18062706139fcz commented Aug 6, 2026

Copy link
Copy Markdown
Collaborator

Why

  • DeerFlow users can reconnect OAuth for the current Lark/Feishu app, but they cannot explicitly switch the underlying Lark/Feishu app/Bot after initial setup.
  • Users need per-account app switching without reinstalling the global skill pack or affecting other DeerFlow users.
  • Switching must not destroy a working configuration when new credentials are invalid, leave the previous OAuth token exposed to the active sandbox, or allow stale authorization flows to overwrite the new state.

How

  • Add a per-user POST /api/integrations/lark/config/credentials endpoint backed by set_lark_app_credentials.
  • Validate new App ID / App Secret in an isolated credential tree before touching the active configuration.
  • Serialize config completion, auth completion, and credential switching with a per-user cross-process lock.
  • Snapshot the active credential tree, restore it on local switch/revoke failures, and revoke/remove the previous OAuth token after a successful switch.
  • Restrict brand to feishu or lark at both HTTP and service boundaries.
  • Add frontend API, hook, and types for switching Lark app credentials.
  • Add a Settings > Integrations Change Lark app panel supporting direct App ID / App Secret switching and browser re-registration.
  • Use one flow generation/busy state across status, config, credential, and auth operations; cancel stale status queries and reject stale async callbacks before they update cache, popup, or pending-flow state.
  • Preserve selected authorization domains/exact scope through both direct switching and browser re-registration.
  • Pre-open the popup synchronously and verify it navigates to the authorization URL.
  • Update docs, localized copy, mocks, unit tests, and E2E coverage.

Validation

  • cd backend && PYTHONPATH=. PYTHONIOENCODING=utf-8 PYTHONUTF8=1 uv run pytest tests/test_lark_cli_integration.py -q (81 passed)
  • cd backend && uv run ruff check packages/harness/deerflow/integrations/lark_cli.py app/gateway/routers/integrations.py tests/test_lark_cli_integration.py
  • cd backend && uv run ruff format --check packages/harness/deerflow/integrations/lark_cli.py app/gateway/routers/integrations.py tests/test_lark_cli_integration.py
  • cd frontend && ./node_modules/.bin/eslint src/components/workspace/settings/integrations-settings-page.tsx src/core/integrations/lark/api.ts src/core/integrations/lark/hooks.ts tests/e2e/integrations.spec.ts tests/unit/core/integrations/lark/api.test.ts
  • cd frontend && rm -rf .next && ./node_modules/.bin/tsc --noEmit
  • cd frontend && ./node_modules/.bin/rstest tests/unit/core/integrations/lark/api.test.ts (8 passed)
  • cd frontend && rm -rf .next test-results && ./node_modules/.bin/playwright test tests/e2e/integrations.spec.ts (5 passed)

@github-actions github-actions Bot added area:backend Gateway / runtime / core backend under backend/ area:docs Documentation and Markdown only area:frontend Next.js frontend under frontend/ needs-validation Touches front/back contract surface; needs real-path validation risk:high High risk: backend API, agents, sandbox, auth, deps, CI size/L PR changes 300-700 lines labels Aug 6, 2026
@github-actions github-actions Bot added size/XL PR changes 700+ lines and removed size/L PR changes 300-700 lines labels Aug 6, 2026
@18062706139fcz
18062706139fcz requested a review from zhfeng August 6, 2026 08:10
@zhfeng

zhfeng commented Aug 6, 2026

Copy link
Copy Markdown
Collaborator

Thanks @18062706139fcz - Nice work and I will take a look!

@zhfeng zhfeng left a comment

Copy link
Copy Markdown
Collaborator

Choose a reason for hiding this comment

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

Found two blocking issues in the app-switch flow.

1. Browser re-registration bypasses the credential-switch transaction

The direct App ID/Secret route uses set_lark_app_credentials: it snapshots the credential tree, writes the new app config, clears the active OAuth data, and revokes the old authorization. The “Re-register in browser” route instead eventually calls complete_lark_config, which only saves the replacement app config.

That leaves the old app’s OAuth token in data after the new app configuration has been written, until the new authorization completes. This conflicts with the stated switching contract and the UI text that says the old authorization is revoked. Route browser re-registration through the same clear-and-revoke transaction after registration succeeds.

2. The lock serializes writes but does not make the newest user choice win

The per-user lock is necessary and correctly prevents simultaneous credential-tree mutation. It cannot, by itself, identify a delayed operation as stale:

  1. Tab A starts browser registration and receives device_code_A.
  2. Tab B directly switches to app B; it obtains the lock and saves B.
  3. Tab A later completes registration. It obtains the lock after B, receives app A credentials, and complete_lark_config writes A over B.

No writes overlap, so the lock works as designed; the final state is nevertheless an older choice. Persist a per-user credential/flow generation under this same lock. Starting a registration associates that generation with the pending flow; a direct switch advances it. Completion must compare its generation with the current generation while holding the lock and reject mismatches as superseded. Apply the same rule to delayed authorization completion. This is a focused state-machine addition, not a replacement for the lock.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

area:backend Gateway / runtime / core backend under backend/ area:docs Documentation and Markdown only area:frontend Next.js frontend under frontend/ needs-validation Touches front/back contract surface; needs real-path validation risk:high High risk: backend API, agents, sandbox, auth, deps, CI size/XL PR changes 700+ lines

Projects

None yet

Development

Successfully merging this pull request may close these issues.

3 participants