Skip to content

feat(people): add "Don't auto-sync" option to employee sync source#3312

Merged
tofikwest merged 2 commits into
mainfrom
tofik/cs-576-disable-employee-sync-ui
Jun 30, 2026
Merged

feat(people): add "Don't auto-sync" option to employee sync source#3312
tofikwest merged 2 commits into
mainfrom
tofik/cs-576-disable-employee-sync-ui

Conversation

@tofikwest

@tofikwest tofikwest commented Jun 30, 2026

Copy link
Copy Markdown
Contributor

Problem

CS-576 (re-opened). Customers can pick an employee sync source in the People tab, but once selected there is no way to turn it back off. The dropdown lists only connected providers and has no "none"/"disable" item; selecting one immediately syncs everyone. The only "off" levers today are:

  • Disconnect the integration — but that's a soft-delete labelled "Remove this account and all data" and, critically, it also stops the integration's compliance checks (which the customer wants to keep).
  • The email include/exclude filter in integration settings — which can limit users but has no real "off" (an empty include list silently reverts to "all" by design).

So a customer who wants to stop the daily auto-sync while staying connected for checks has no path in the UI.

Root cause

The capability already exists end-to-end — it was just never wired to a control:

  • POST /v1/integrations/sync/employee-sync-provider accepts { provider: null } ("pass null to disable employee sync").
  • useEmployeeSync.setSyncProvider(null) already calls it.
  • The daily 7 AM cron (syncEmployeesSchedule) only runs for orgs where employeeSyncProvider is not null.

The People-tab dropdown's onValueChange only ever called syncEmployees(...), and the item list contained no "off" option.

Fix

  • Add a "Don't auto-sync" item to the sync-source dropdown. Selecting it routes to a disable handler (setSyncProvider(null)) instead of running a sync, clearing the org's provider so the scheduled job skips it.
  • Already-imported people are left untouched; the integration stays connected (checks keep running).
  • The item shows Active when no provider is selected, so the off-state is visible/discoverable.
  • setSyncProvider now confirms the off action with a toast.
  • Applies to every sync provider (Google Workspace, Rippling, JumpCloud, and dynamic providers like Microsoft Entra ID), not just Entra.
  • Permission-gated: the dropdown is disabled unless canManageMembers; the API still enforces integration:update.

Not included (intentionally)

"Sync only specific Entra groups" — a separate, larger feature that requires editing the shared Entra syncDefinition (Graph group-member resolution + a new variable + UI) and is tracked separately. This PR delivers the customer's core "stop the sync completely" ask.

Tests

  • useEmployeeSync.test.ts: setSyncProvider(null) POSTs { provider: null } and confirms; provider selection POSTs the slug.

Fixes CS-576

🤖 Generated with Claude Code


Summary by cubic

Adds a “Don’t auto-sync” option to the People tab so orgs can pause daily employee imports without disconnecting the integration. This fulfills the “disable auto-sync” part of Linear CS-576 while keeping compliance checks running.

  • New Features

    • Added a “Don’t auto-sync” dropdown item that calls setSyncProvider(null) so the scheduled job skips the org; existing people remain.
    • Shows “Active” when no provider is selected for a clear off-state.
    • Works for all providers, including dynamic ones (e.g., Microsoft Entra ID).
    • Permission-gated: dropdown disabled unless canManageMembers; API enforces integration:update.
    • Toast confirms both disabling and provider selection.
  • Bug Fixes

    • Locked the sync-source dropdown while disabling to prevent races with concurrent provider changes.

Written for commit 541a72f. Summary will update on new commits.

Review in cubic

CS-576 (re-open): customers could select an employee sync source in the
People tab but had no way to turn it back off. The only "off" levers were
disconnecting the integration (which also kills its compliance checks and is
labelled "remove all data") or an email-filter workaround — neither is a real
disable. The org-level `employeeSyncProvider` already supports null end-to-end
(`POST /employee-sync-provider {provider:null}` + `setSyncProvider(null)`), and
the daily 7 AM cron skips orgs whose provider is null — it was just never wired
to a UI control.

This adds a "Don't auto-sync" item to the sync-source dropdown that clears the
provider (stopping the scheduled sync) without disconnecting the integration or
touching already-imported people. Applies to every sync provider, not just
Entra. Selecting it routes to disable (never triggers a sync), and the hook now
confirms with a toast. Gated by `canManageMembers`; backend still enforces
`integration:update`.

Tests: cover setSyncProvider(null) disabling + provider selection.

Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
Claude-Session: https://claude.ai/code/session_01M6zcF9bvPP1UwZgzK21cw1
@linear

linear Bot commented Jun 30, 2026

Copy link
Copy Markdown

CS-576

@vercel

vercel Bot commented Jun 30, 2026

Copy link
Copy Markdown

The latest updates on your projects. Learn more about Vercel for GitHub.

Project Deployment Actions Updated (UTC)
app Ready Ready Preview, Comment Jun 30, 2026 8:51pm
comp-framework-editor Ready Ready Preview, Comment Jun 30, 2026 8:51pm
1 Skipped Deployment
Project Deployment Actions Updated (UTC)
portal Skipped Skipped Jun 30, 2026 8:51pm

Request Review

@cubic-dev-ai cubic-dev-ai Bot left a comment

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

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

cubic analysis

1 issue found across 3 files

Confidence score: 3/5

  • In apps/app/src/app/(app)/[orgId]/people/all/components/TeamMembersClient.tsx, the “Don’t auto-sync” path calls setSyncProvider(null) without setting isSyncing, so the dropdown stays interactive while the request is in flight; users can trigger overlapping changes and end up with inconsistent sync state or confusing UI feedback — set isSyncing before the API call and disable the control until the request settles before merging.

Linked issue analysis

Linked issue: CS-576: Entra Integration — Add ability to disable/limit auto-sync

Status Acceptance criteria Notes
Add a “Don't auto-sync” option to the sync-source dropdown and wire selection to disabling logic (call setSyncProvider(null)). TeamMembersClient adds a NO_SYNC_VALUE SelectItem and the onValueChange branch handles that value by calling handleDisableSync -> setSyncProvider(null).
Persist provider: null via the API so the scheduled daily sync will skip the org. useEmployeeSync.send POSTs provider: null and tests verify the API call; setting provider to null is the mechanism the cron uses to skip orgs.
Show an indicator ('Active') on the 'Don't auto-sync' item when no provider is selected (discoverability of off state). The SelectItem renders a conditional 'Active' label when selectedProvider is falsy.
Confirm disabling action with a success toast to the user. useEmployeeSync now shows a success toast when provider is set to null and the test asserts the toast call.
⚠️ Leave already-imported people untouched and keep the integration connected (so compliance checks continue). PR description explicitly states imported people are left untouched and the integration remains connected; the diff shows only a provider-null API call (no deletion or disconnect logic), but there is no explicit test asserting compliance checks continue or that imported users are unchanged.
Permission-gate the dropdown so only users with manage-members can change the provider. The Select is disabled using the existing canManageMembers guard (disabled={isSyncing || !canManageMembers}), so changing the provider (including selecting Don't auto-sync) remains permission-guarded.

Reply with feedback, questions, or to request a fix.

Fix all with cubic | Re-trigger cubic

Comment thread apps/app/src/app/(app)/[orgId]/people/all/components/TeamMembersClient.tsx Outdated
Addresses cubic P2: the "Don't auto-sync" path called setSyncProvider(null)
without any busy flag, so the dropdown stayed interactive during the request
and a follow-up provider selection could race it to an inconsistent state.

Add an isDisablingSync flag (mirroring isSyncing): set it around the disable
request, include it in the Select's disabled guard, and bail out of the handler
if a disable is already in flight.

Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
Claude-Session: https://claude.ai/code/session_01M6zcF9bvPP1UwZgzK21cw1
@vercel vercel Bot temporarily deployed to Preview – portal June 30, 2026 20:48 Inactive
@tofikwest tofikwest merged commit 3a6d4aa into main Jun 30, 2026
11 checks passed
@tofikwest tofikwest deleted the tofik/cs-576-disable-employee-sync-ui branch June 30, 2026 20:51
@claudfuen

Copy link
Copy Markdown
Contributor

🎉 This PR is included in version 3.94.0 🎉

The release is available on GitHub release

Your semantic-release bot 📦🚀

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

Labels

Projects

None yet

Development

Successfully merging this pull request may close these issues.

2 participants