Skip to content

/create-deals-bulk — Behavior Reference

Endpoint: POST https://txpaxbxhnvnhsjwwaeoy.supabase.co/functions/v1/create-deals-bulk Auth: X-API-Key: cg_...


1. Contact resolution order (per deal)

For each deal in the deals[] array, the function resolves the contact in this exact order:

  1. contact_id — if provided, used directly. No lookup, no creation.
  2. contact_email — searches contacts.emails (array, case-sensitive contains) within the org.
  3. contact_phone — searches contacts.phones (array, exact match) within the org.
  4. create_contact_if_missing: true — only runs if steps 1–3 found nothing.

Key point: if a contact with that phone/email already exists in your org, the deal is linked to the existing contact. A new contact is never created when one is found. is_new_contact: false in the response confirms this.


Phone +201017177777 already exists as contact f2b4f7ab-7033-47ce-be06-b30a47de020a (mahmoud).

curl -X POST 'https://txpaxbxhnvnhsjwwaeoy.supabase.co/functions/v1/create-deals-bulk' \
 -H 'X-API-Key: cg_your_api_key_here' \
 -H 'Content-Type: application/json' \
 -d '{
 "default_currency": "SAR",
 "default_stage": "qualified",
 "skip_if_exists": true,
 "deals": [
 {
 "title": "Order 68297792",
 "value": 11523,
 "contact_phone": "+201017177777",
 "create_contact_if_missing": true,
 "contact_first_name": "Customer"
 }
 ]
 }'

Expected response:

{
 "results": [{
 "index": 0,
 "success": true,
 "deal_id": "...",
 "contact_id": "f2b4f7ab-7033-47ce-be06-b30a47de020a",
 "is_new_contact": false
 }],
 "summary": { "new_contacts_created": 0 }
}

The contact_first_name: "Customer" is ignored because the contact already exists — the existing record (mahmoud) is reused as-is. The bulk endpoint does not update existing contact fields.


3. Curl — create_contact_if_missing: true (new contact)

When no contact matches the phone/email, the function inserts a new row into contacts using only these fields:

Source field Goes into column
contact_first_name first_name
contact_last_name last_name
contact_email emails (as [email])
contact_phone phones (as [phone])
hardcoded source = 'api'
hardcoded tags = ['deal-import']
hardcoded organization_id (from API key)

No other contact fields (company, custom_fields, description, assignee...) are accepted by this endpoint.

curl -X POST 'https://txpaxbxhnvnhsjwwaeoy.supabase.co/functions/v1/create-deals-bulk' \
 -H 'X-API-Key: cg_your_api_key_here' \
 -H 'Content-Type: application/json' \
 -d '{
 "default_currency": "SAR",
 "default_stage": "qualified",
 "deals": [
 {
 "title": "Order 99999001",
 "value": 4500,
 "contact_phone": "+201020000099",
 "contact_email": "newlead@example.com",
 "contact_first_name": "Sara",
 "contact_last_name": "Hassan",
 "create_contact_if_missing": true
 }
 ]
 }'

Result: a new contact is created with first_name=Sara, last_name=Hassan, emails=["newlead@example.com"], phones=["+201020000099"], source=api, tags=["deal-import"]. The deal is linked to it. is_new_contact: true.

You do NOT need a separate contact creation step — the deal-level fields are sufficient for a properly populated contact.

If you need richer contact data (company, custom_fields, description, etc.)

Create the contact first via the REST API proxy, then pass its contact_id to the bulk endpoint:

# Step 1 — create contact with full details
curl -X POST 'https://txpaxbxhnvnhsjwwaeoy.supabase.co/functions/v1/rest-api-proxy/contacts' \
 -H 'X-API-Key: cg_...' -H 'Content-Type: application/json' \
 -d '{
 "first_name": "Sara",
 "last_name": "Hassan",
 "phones": ["+201020000099"],
 "emails": ["newlead@example.com"],
 "description": "VIP from Shopify",
 "tags": ["vip","shopify"],
 "custom_fields": { "shopify_customer_id": "12345" }
 }'
# → returns [{ "id": "uuid-..." }]

# Step 2 — create the deal with contact_id
curl -X POST 'https://txpaxbxhnvnhsjwwaeoy.supabase.co/functions/v1/create-deals-bulk' \
 -H 'X-API-Key: cg_...' -H 'Content-Type: application/json' \
 -d '{ "deals": [{ "title": "Order...", "value": 4500, "contact_id": "uuid-..." }] }'

4. Search a contact by phone (current state of +201017177777)

curl -G 'https://txpaxbxhnvnhsjwwaeoy.supabase.co/functions/v1/rest-api-proxy/contacts' \
 -H 'X-API-Key: cg_your_api_key_here' \
 --data-urlencode 'phones=cs.{"+201017177777"}' \
 --data-urlencode 'select=id,first_name,last_name,emails,phones,source,tags,created_at'

Actual record currently in the DB for that phone:

[{
 "id": "f2b4f7ab-7033-47ce-be06-b30a47de020a",
 "first_name": "mahmoud",
 "last_name": null,
 "emails": ["issmail@gmail.com"],
 "phones": ["+201017177777"],
 "source": null,
 "tags": [],
 "created_at": "2026-04-22T16:00:58.354Z"
}]

Search by email instead:

curl -G '.../rest-api-proxy/contacts' \
 -H 'X-API-Key: cg_...' \
 --data-urlencode 'emails=cs.{"issmail@gmail.com"}'


5. Behavior cheat sheet

Scenario Result is_new_contact
contact_phone matches existing Deal linked to existing contact, name fields ignored false
contact_email matches existing Deal linked to existing contact false
No match, create_contact_if_missing: false (or omitted) Deal fails with "Contact not found" error
No match, create_contact_if_missing: true New contact created from contact_* fields true
contact_id provided Used directly, no lookup false
skip_if_exists: true + same (contact_id, title) exists Returns existing deal_id, no new deal false

⚠️ The bulk endpoint never updates an existing contact. To enrich mahmoud with a proper last_name, company, etc., use a PATCH against /rest-api-proxy/contacts?id=eq.f2b4f7ab-....