Fix GoHighLevel opportunity pagination and contact dedupe.

GHL search rejects skip; page+location_id is required so nightly CRM sync can complete.

Co-authored-by: Cursor <cursoragent@cursor.com>
This commit is contained in:
4Ventures
2026-10-06 12:06:27 +02:00
parent 487e2c7a2b
commit 0ad89e88e5
2 changed files with 57 additions and 11 deletions

37
scripts/sync_ghl.ts Normal file
View File

@@ -0,0 +1,37 @@
/**
* Sync GoHighLevel contacts/opportunities → warehouse.
* npx tsx scripts/sync_ghl.ts
* TENANT_SLUG=delgado-abogados npx tsx scripts/sync_ghl.ts
*/
import { config } from 'dotenv';
import { resolve } from 'path';
config({ path: resolve(process.cwd(), '.env.local') });
import { syncAllGhlTenants } from '../src/lib/gohighlevel-sync';
import { serviceHeaders, supabaseUrl } from '../src/lib/agency';
async function main() {
const slug = process.env.TENANT_SLUG?.trim();
let tenantId: string | undefined;
if (slug) {
const headers = serviceHeaders();
const base = supabaseUrl();
if (!headers || !base) throw new Error('no service role');
const r = await fetch(
`${base}/rest/v1/tenants?slug=eq.${encodeURIComponent(slug)}&select=id,slug`,
{ headers, cache: 'no-store' }
);
const rows = (await r.json()) as { id: string; slug: string }[];
if (!rows[0]) throw new Error(`tenant ${slug} not found`);
tenantId = rows[0].id;
}
const out = await syncAllGhlTenants({ tenantId });
console.log(JSON.stringify(out, null, 2));
if (out.results.some((x) => x.error)) process.exit(2);
}
main().catch((e) => {
console.error(e);
process.exit(1);
});