Skip to content

feat: improve Chatwoot history import sync#2614

Draft
guirtvidal wants to merge 2 commits into
evolution-foundation:mainfrom
guirtvidal:codex/chatwoot-import-sync-upstream
Draft

feat: improve Chatwoot history import sync#2614
guirtvidal wants to merge 2 commits into
evolution-foundation:mainfrom
guirtvidal:codex/chatwoot-import-sync-upstream

Conversation

@guirtvidal

Copy link
Copy Markdown

Summary

This PR improves the Chatwoot integration import/sync flow for WhatsApp contacts, groups, and historical messages.

It focuses on cases where Evolution API already has local WhatsApp data, but Chatwoot does not receive the right contact names, group names, conversations, or historical messages during import.

What Changed

Manual Chatwoot import endpoint

  • Added a Chatwoot import route:
    • POST /chatwoot/import/{instance}
  • Added controller/service handling for manual import execution.
  • Updated the bundled manager build to expose the import action from the UI.

Historical message import into Chatwoot

  • Import now reads locally stored Evolution API messages within the configured Chatwoot import window.
  • Import creates or resolves the required Chatwoot records before inserting messages:
    • contacts
    • contact inboxes
    • conversations
  • Import now supports existing Chatwoot contacts/conversations instead of only working reliably for fully new records.
  • Message duplicate checks are scoped by account_id and inbox_id to avoid skipping messages from another account/inbox by mistake.
  • Message insertion uses ON CONFLICT DO NOTHING to make repeat imports safer.

WhatsApp group name handling

  • Group contacts imported into Chatwoot now use the WhatsApp group name instead of the last message sender name.
  • Existing valid group names in Evolution API are preserved.
  • The import only attempts group metadata refresh for groups whose local name is missing, GROUP, or the numeric group id.
  • When a valid group subject is discovered, it is persisted back into local Evolution API records:
    • Chat.name
    • Contact.pushName
  • Chatwoot contact upserts update existing group contact names when a better name is available.

Rate-limit protection

  • Added a short backoff when WhatsApp/Baileys returns rate-overlimit for group metadata refresh.
  • Avoids repeated groupMetadata calls while WhatsApp is rate limiting the instance.
  • The import path avoids per-group metadata calls and prefers groupFetchAllParticipating() where available.

SQL/import robustness

  • Fixed ambiguous SQL references around identifier in the Chatwoot import CTEs.
  • Reworked the Chatwoot FK resolution query so it can safely create missing contact_inboxes and conversations for contacts that already exist.
  • Keeps ignored/system WhatsApp JIDs out of Chatwoot history import.

Why

Before this change, Chatwoot imports could show WhatsApp groups as GROUP or as the last sender's name instead of the actual group subject.

Historical imports could also fail to move older messages into Chatwoot when the contact already existed but the related contact_inbox or conversation did not.

In larger group-heavy instances, repeated group metadata lookups could trigger WhatsApp/Baileys rate-overlimit errors.

User Impact

  • Manual Chatwoot import becomes more useful for existing Evolution API deployments.
  • Groups appear in Chatwoot with the correct group name.
  • Existing Chatwoot contacts are updated during sync instead of being left stale.
  • Historical messages already stored in Evolution API are imported more reliably.
  • Imports are safer to retry.

Validation

  • Verified the patch composition with git diff --check.
  • This PR is opened as draft because the local checkout used for preparing the fork did not have a fully installable/working dependency environment for running the complete project build.

Notes For Reviewers

  • The manager changes are bundled manager/dist assets matching the new import action.
  • The Chatwoot import logic writes directly to the configured Chatwoot database, consistent with the existing import implementation.
  • The group-name refresh is conservative: it preserves any existing usable Evolution API group name and only updates groups that currently have no usable local name.

@sourcery-ai sourcery-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.

Sorry @guirtvidal, your pull request is larger than the review limit of 150000 diff characters

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