Skip to content

refactor(worker): move integration, chat and ai-agent handler data access into business - #1099

Open
realcodesiman wants to merge 1 commit into
mainfrom
refactor/data-access-worker-integration
Open

refactor(worker): move integration, chat and ai-agent handler data access into business#1099
realcodesiman wants to merge 1 commit into
mainfrom
refactor/data-access-worker-integration

Conversation

@realcodesiman

Copy link
Copy Markdown
Contributor

Summary

  • Removes every direct db.* call from apps/worker/src/{integration,chat,ai-agent,services,lib} (inbound message ingestion, flow steps, template sends, coexist import) per .agents/rules/data-access.md. Bodies are moved verbatim; every isNull TOCTOU guard, sql\col + N`increment, untargetedonConflictDoNothing(), sql.identifier()andwithBlockedOwnerGuard call site is preserved (git diff main | grep withBlockedOwnerGuard` is empty).
  • One of seven parallel scope PRs following feat(contacts): cover full public API for MCP, move logic into business services #1093 (contacts); based on main, append-only barrel edits. The deleteContact handler is left on its main form because feat(contacts): cover full public API for MCP, move logic into business services #1093 already migrates it; expect a keep-both merge in handlers/contact.ts, contact/service.ts, tag/service.ts and the two barrels.

Changes

  • Coexist: coexistSyncRunRepository.{claimRunForSync,incrementProgress,findInitState,findLastSyncedAt,findTerminalCounters,findNewestLiveRunId,findFlushResumeState}, whatsappCoexistStagingRepository.{stagePayload,listUnprocessed,markProcessed,hasUnprocessed}, new coexistImportService holding the historical-import transaction and contactRepository.enrichIfNull (COALESCE SQL verbatim). claimRunForSync deliberately does not filter status IN ('init','running') and takes touchUpdatedAt to preserve the two callers' differing SET clauses.
  • Flow steps: contactService.{setFlowFlags,subscribeBroadcastIfUnsubscribed,unsubscribeBroadcast,setAvatarIfEmpty}, contactNoteService.createFromFlow, tagService.{attachByNamesToContact,listIdsByNames,detachTagIdsFromContact,detachTagFromContacts,linkTagToContactsReturningNew,ensureTagByName,ensureTagChannel,...}, contactSequenceService.{isEnrolled,findFirstActiveStep,findSequenceName}, sequenceDispatchUtils.{findRunning,markCompleted,markCanceled,markFailed}.
  • Chat/inbound: conversationService.{recordInboundActivity,recordOutboundFlowStep,recordOutboundMessageActivity,findByIdWithContact}, inboxService.findWithIntegration{Messenger,Whatsapp}ById, approved-template lookups on the integration services, contactInboxRepository.{findWithContact,findWithConversationAndContact,...}.
  • Libs: flowService.{findActiveById,findAnyActive}, flowVersionService.findByIdForWorkspace, new ai-embedding, integration-lookup and import repositories; lib/db.ts keeps its exported names and signatures.
  • Tests re-pointed to the service boundary plus new regression tests for the TOCTOU guards, the claim predicate, the + N increment and the AI-file enqueue.

Deliberate behavior changes

  1. stepBlockContact now goes through contactService.block (adds findByIdOrFail, contact-info-change events and cache invalidation the raw write lacked).
  2. setFlowFlags now invalidates the contact cache (the raw db.update never did).
  3. process-ai-file enqueues only the embedding ids it just inserted (bulkCreatePending(...).returning), instead of re-reading all rows for the file, which double-enqueued prior runs' embeddings on retry.
  4. send-flow-direct and update-avatar now scope by workspaceId (via contactInboxService.listByContactId / contactService.findById / setAvatarIfEmpty); safe by construction, data is already workspace-scoped upstream.
  5. The inbound/outbound activity conversation UPDATEs add workspaceId to their WHERE via updateFlowStepState.
  6. Plan-location deviations: coexist-import is a business service rather than a database repository; approved-template lookups live on the integration services rather than templateService.

Test plan

  • pnpm --filter @chatbotx.io/database check-types && test
  • pnpm --filter @chatbotx.io/business check-types && test (only the pre-existing ads-conversion-rule.service.test.ts failures remain, also red on main)
  • pnpm --filter worker check-types && test (only the pre-existing flow-import-handler.test.ts failures remain, also red on main)
  • pnpm --filter worker build
  • pnpm lint
  • Staging smoke: inbound WhatsApp message; flow with add-tag + assign-conversation; Messenger template broadcast; enable coexist on a Messenger integration

…cess into business

Removes direct db usage from apps/worker/src/{integration,chat,ai-agent,
services,lib} per .agents/rules/data-access.md. Hot-path bodies are
moved verbatim; every isNull TOCTOU guard, sql increment, untargeted
onConflictDoNothing, sql.identifier and withBlockedOwnerGuard call site
is preserved.

- coexist: claimRunForSync/incrementProgress/findInitState/... on the
  coexist-sync-run repository, staging repository methods, and a new
  coexistImportService holding the historical-import transaction
- contact/tag/sequence flow steps, inbox labels, templates, message
  status and received-message activity tracking routed through
  contactService, tagService, contactSequenceService,
  conversationService, inboxService and the integration services
- sequenceDispatchUtils gains findRunning/markCompleted/markCanceled/
  markFailed; new ai-embedding, integration-lookup and import
  repositories; lib/db.ts keeps its exported names and signatures

Deliberate behavior changes (recorded in the PR): stepBlockContact now
goes through contactService.block (emits + invalidates), setFlowFlags
invalidates the contact cache, process-ai-file enqueues only the ids it
inserted, send-flow-direct and update-avatar add workspace scoping, and
the inbound/outbound activity conversation updates add workspaceId to
their WHERE.
@github-actions github-actions Bot added the improvement Refactor or performance improvement label Sep 6, 2026
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

improvement Refactor or performance improvement

Projects

None yet

Development

Successfully merging this pull request may close these issues.

1 participant