Skip to main content

Close CRM Integration

Close CRM keeps the sales team in sync with onboarding progress. Implementation lives in reformer-platform/services/close-crm.js, with orchestration hooks in services/automation-orchestrator.js.

Environment Variables

CLOSE_API_KEY=api_...

The key is stored in Render/GitHub secrets (see repo memory). automation-orchestrator checks for configuration before syncing; if the key is missing, it logs Close CRM: Not configured.

Core Features

  • Lead management
    • findLeadByEmail, getLeadById, createLead
    • Standard lead payload includes contacts, phone, and custom fields (account name, etc.).
  • Lead updates with retry + verification
    • updateLead(leadId, updates, { retries, retryDelay }) validates custom fields, retries on failure, and double-checks updates via verifyCustomFieldsUpdate.
    • validateAndPrepareUpdatePayload handles null/undefined and type coercion.
  • Enrichment
    • pageSpeed.analyze() integrates PageSpeed Insights; results stored as custom fields + Slack notifications.
    • Dropbox link updates add notes to Close CRM.
  • Statistics & reporting
    • syncStats tracks successes/failures.
    • sendDailySummaryToSlack posts summary via slackNotifier.
    • Slack alerts for failures (WARNING: Close CRM sync failed).

Automation Orchestrator Touchpoints

services/automation-orchestrator.js calls:

  • syncToCloseCRM(member, integration, plan) — initial lead sync.
  • updateCloseCRMWithCompany(member, integration, companyData) — company info updates.
  • updateCloseCRMWithDropboxLink(member, dropboxLink) — attaches Dropbox folder link.

Each step logs success/failure and only runs if Close CRM is configured.

Notes & Future Work

  • Ensure Close CRM custom fields match payload names; validation warnings indicate mismatches.
  • Monitor Slack notifications for retry failures.
  • Daily summary helps confirm the integration runs (check Close CRM Daily Summary in Slack).
  • Add tests for webhook-driven updates once new enrollment flows go live.

Keep this page updated when custom fields or automation logic evolves.***