---
title: "Privacy-conscious person lookup with journey tracking"
method: POST
path: "/crm/lookup/person"
tags: ["CRM Service Calls"]
---

# Privacy-conscious person lookup with journey tracking

`POST /crm/lookup/person`

## Request

- Base URL: `https://fapi.ambivo.com` (the document declares no server; this is the origin it was published from)
- URL: `https://fapi.ambivo.com/crm/lookup/person`
- Auth: API key in header `Authorization`
- TypeScript: <https://skmtc.dev/ambivo/apis/ambivo-api/docs/crm/lookup/person/post.ts> (a function with typed inputs; its response is checked against the schema)

Search for a person by email, phone, internal ID, or external ID and retrieve their complete journey
through the sales pipeline (lead → contact → opportunity).

## Search Options

Provide at least one of:
- **email**: Search by email address
- **phone**: Search by phone number
- **id**: Search by internal CRM record ID (lead or contact)
- **external_id**: Search by external/partner reference ID

## Privacy Notice

This endpoint returns **only aggregate activity metrics**. It does NOT expose:

- Names, IDs, or any identifying information
- Actual comment content or details
- Owner/assigned user information
- Deal values or commission-sensitive data
- Tags or custom fields

## Rate Limits

- **60 requests per minute** per auth token
- Rate limited to prevent abuse

## Search Logic

1. If `id` or `external_id` provided, searches directly by ID (takes priority)
2. Falls back to email/phone search if no ID match or no ID provided
3. Searches contacts first (prioritizes existing relationships)
4. Searches leads (for new prospects)
5. If a contact is found, searches for associated opportunities
6. Returns the complete journey with activity metrics at each stage

## Use Cases

- **Duplicate Detection**: Check if a person already exists before creating a new lead
- **Journey Tracking**: Understand where a person is in the sales pipeline
- **Commission Attribution**: Verify activity within inactivity period for commission eligibility
- **Direct Lookup**: Retrieve journey info for a known record by ID

## Inactivity Period

The `inactivity_days` parameter (default: 30) determines whether activity is considered
"recent". The `has_recent_activity` response field indicates if the most recent
activity falls within this threshold.

## Query parameters

- `inactivity_days` integer: Number of days to consider for inactivity threshold. Activity within this period sets has_recent_activity=true.

## Request body

- PersonLookupRequest: Request for privacy-conscious person lookup. At least one of email, phone, id, or external_id must be provided. Used by third-party integrations to check for duplicate leads and track lead journey without exposing sensitive data.
  - `email` string, nullable: Email address to search for
  - `phone` string, nullable: Phone number to search for (various formats accepted)
  - `id` string, nullable: Internal CRM record ID to search for (lead or contact)
  - `external_id` string, nullable: External/partner reference ID to search for

## Response `200`

Lookup successful

- PersonLookupResponse: Privacy-conscious response for person lookup with full journey tracking. Returns the complete lead → contact → opportunity journey without exposing sensitive business data like names, IDs, values, or specific statuses. **Privacy Notice**: This response does NOT expose: - Names, IDs, or any identifying information - Actual comment content - Owner/assigned user information - Deal values or commission-sensitive data - Tags or custom fields
  - `exists` boolean, required: Whether any matching record was found (lead or contact)
  - `matched_on` 'email' | 'phone' | 'both' | 'id' | 'external_id', nullable: Which identifier matched (email, phone, both, id, or external_id)
  - `has_recent_activity` boolean: True if person has activity within the configured threshold (default 30 days)
  - `lead` LeadJourneyInfo, required: Privacy-safe lead information for journey tracking. Exposes only aggregate activity metrics without PII.
    - `exists` boolean, required: Whether a matching lead record was found
    - `is_active` boolean: Whether the lead is in an active state (not disqualified/inactive)
    - `is_converted` boolean: Whether the lead has been converted to a contact
    - `has_activity` boolean: Whether there has been any activity on this lead
    - `comment_count` integer: Number of comments/touchpoints on the lead
    - `days_since_last_activity` integer, nullable: Days since last activity, null if no activity
    - `activity_summary` string, nullable: Human-readable activity summary
    - `created_date` string, nullable: Date the lead was created (ISO 8601)
  - `contact` ContactJourneyInfo, required: Privacy-safe contact information for journey tracking. Exposes only aggregate activity metrics without PII.
    - `exists` boolean, required: Whether a matching contact record was found
    - `is_active` boolean: Whether the contact is in an active state
    - `has_activity` boolean: Whether there has been any activity on this contact
    - `comment_count` integer: Number of comments/touchpoints on the contact
    - `days_since_last_activity` integer, nullable: Days since last activity, null if no activity
    - `activity_summary` string, nullable: Human-readable activity summary
    - `created_date` string, nullable: Date the contact was created (ISO 8601)
    - `converted_from_lead` boolean: Whether this contact was converted from a lead
  - `opportunity` OpportunityJourneyInfo, required: Privacy-safe opportunity information for journey tracking. Exposes stage and dates only - no values or sensitive details.
    - `exists` boolean, required: Whether an opportunity exists for this person
    - `stage` string, nullable: Current opportunity stage (e.g., discovery, negotiation, closed_won)
    - `is_closed` boolean: Whether the opportunity is in a closed state
    - `is_won` boolean: Whether the opportunity was won (closed_won)
    - `created_date` string, nullable: Date the opportunity was created (ISO 8601)
    - `expected_close_date` string, nullable: Expected close date (ISO 8601)
    - `close_date` string, nullable: Actual close date if closed (ISO 8601)
    - `opportunity_count` integer: Total number of opportunities for this person
  - `journey_stage` 'lead' | 'contact' | 'opportunity' | 'closed', nullable: Current stage in the journey (furthest stage reached)
  - `total_touchpoints` integer: Total touchpoints across all stages
  - `first_seen_date` string, nullable: Earliest date this person entered the system (ISO 8601)

## Other responses

- `401`: Missing or invalid authorization token
- `422`: Validation error (invalid email/phone format or missing both)
- `429`: Rate limit exceeded
- `500`: Internal server error

## Changes

- **2026-08-06** `165a6d16a9a0`: 1 info
  - endpoint added

[Operation history](https://skmtc.dev/ambivo/apis/ambivo-api/changes/crm/lookup/person/post.md)

---

[API](https://skmtc.dev/ambivo/apis/ambivo-api.md) - [All operations](https://skmtc.dev/ambivo/apis/ambivo-api/llms.txt) - [OpenAPI document](https://skmtc.dev/ambivo/apis/ambivo-api/revisions/165a6d16a9a0?raw)
