> ## Documentation Index
> Fetch the complete documentation index at: https://docs.api.tamtam.ai/llms.txt
> Use this file to discover all available pages before exploring further.

# Resolve people to LinkedIn profiles

> Turn what a row of your file says about a person — a name, an email, a company — into the LinkedIn profile it most likely is, with a confidence you can threshold, without extracting the profile. Up to 10 people per call, answered in order with your `custom` map echoed.

Each row runs the same waterfall as `POST /v2/people/extract`: Tamtam's own email caches and the account's CRM first, then Sales Navigator, Linkup, and web search with AI verification. The answer says which step found the profile (`source`) and what that step reported about the person — name, headline, company — so a job change can usually be read off the row without an extract.

**Pricing follows the source.** A `cache` or `crm` hit is free. A profile found by `sales_navigator`, `linkup` or `web_search` costs 1 credit, and the row says so with `charged: true`. Nobody found costs nothing. The one whole-batch refusal is **402**, checked before anything runs, when the account could not pay for every row in the batch resolving by search.

A row with nothing to search on (no name, email or company) is answered with `error: insufficient_hint`; a strategy failure with `error: resolution_failed`. Neither stops the other rows.



## OpenAPI

````yaml /reference/openapi.yaml post /v2/people/resolve
openapi: 3.1.0
info:
  title: Tamtam Public API
  version: 2.0.0
servers:
  - url: https://api.tamtam.ai/api
security: []
paths:
  /v2/people/resolve:
    post:
      tags:
        - People Extract
      summary: Resolve people to LinkedIn profiles
      description: >-
        Turn what a row of your file says about a person — a name, an email, a
        company — into the LinkedIn profile it most likely is, with a confidence
        you can threshold, without extracting the profile. Up to 10 people per
        call, answered in order with your `custom` map echoed.


        Each row runs the same waterfall as `POST /v2/people/extract`: Tamtam's
        own email caches and the account's CRM first, then Sales Navigator,
        Linkup, and web search with AI verification. The answer says which step
        found the profile (`source`) and what that step reported about the
        person — name, headline, company — so a job change can usually be read
        off the row without an extract.


        **Pricing follows the source.** A `cache` or `crm` hit is free. A
        profile found by `sales_navigator`, `linkup` or `web_search` costs 1
        credit, and the row says so with `charged: true`. Nobody found costs
        nothing. The one whole-batch refusal is **402**, checked before anything
        runs, when the account could not pay for every row in the batch
        resolving by search.


        A row with nothing to search on (no name, email or company) is answered
        with `error: insufficient_hint`; a strategy failure with `error:
        resolution_failed`. Neither stops the other rows.
      operationId: resolve-people
      requestBody:
        content:
          application/json:
            schema:
              $ref: '#/components/schemas/ResolvePeopleInputBody'
        required: true
      responses:
        '200':
          content:
            application/json:
              schema:
                $ref: '#/components/schemas/ResolvePeopleOutputBody'
          description: OK
        default:
          content:
            application/problem+json:
              schema:
                $ref: '#/components/schemas/ErrorModel'
          description: Error
      security:
        - apikeyAuth: []
        - bearerAuth: []
components:
  schemas:
    ResolvePeopleInputBody:
      additionalProperties: false
      properties:
        requests:
          description: People to resolve, at most 10 per call.
          items:
            $ref: '#/components/schemas/ResolvePersonRequestDto'
          maxItems: 10
          minItems: 1
          type:
            - array
            - 'null'
      required:
        - requests
      type: object
    ResolvePeopleOutputBody:
      additionalProperties: false
      properties:
        results:
          description: One entry per request row, in the same order.
          items:
            $ref: '#/components/schemas/ResolvePersonItemDto'
          type:
            - array
            - 'null'
      required:
        - results
      type: object
    ErrorModel:
      additionalProperties: false
      properties:
        detail:
          description: >-
            A human-readable explanation specific to this occurrence of the
            problem.
          examples:
            - Property foo is required but is missing.
          type: string
        errors:
          description: Optional list of individual error details
          items:
            $ref: '#/components/schemas/ErrorDetail'
          type:
            - array
            - 'null'
        instance:
          description: >-
            A URI reference that identifies the specific occurrence of the
            problem.
          examples:
            - https://example.com/error-log/abc123
          format: uri
          type: string
        status:
          description: HTTP status code
          examples:
            - 400
          format: int64
          type: integer
        title:
          description: >-
            A short, human-readable summary of the problem type. This value
            should not change between occurrences of the error.
          examples:
            - Bad Request
          type: string
        type:
          default: about:blank
          description: A URI reference to human-readable documentation for the error.
          examples:
            - https://example.com/errors/example
          format: uri
          type: string
      type: object
    ResolvePersonRequestDto:
      additionalProperties: false
      properties:
        company_linkedin_id:
          description: >-
            Current company's LinkedIn numeric ID, when known. Lets Sales
            Navigator filter on the company instead of ranking on its name.
          examples:
            - '1441'
          type: string
        company_name:
          description: Current company name, as the file has it.
          examples:
            - Acme Corp
          type: string
        custom:
          additionalProperties:
            type: string
          description: Custom key-value pairs echoed back on the result, e.g. your row id.
          type: object
        email:
          description: >-
            Work email. The strongest hint: it is tried against Tamtam's own
            email caches and the account's CRM before any search runs, and those
            hits are free.
          examples:
            - jean.dupont@acme.com
          type: string
        firstname:
          description: First name.
          examples:
            - Jean
          type: string
        full_name:
          description: >-
            Full name, when the file does not split it. Parsed into first and
            last.
          examples:
            - Jean Dupont
          type: string
        job_title:
          description: >-
            Current job title, when known. Helps rank candidates; not resolvable
            on its own.
          examples:
            - VP Sales
          type: string
        lastname:
          description: Last name.
          examples:
            - Dupont
          type: string
      type: object
    ResolvePersonItemDto:
      additionalProperties: false
      properties:
        charged:
          description: >-
            true when this row consumed a credit: a search strategy found the
            profile. false for a cache or CRM hit, for nobody found, and for an
            errored row.
          type: boolean
        company_name:
          description: Current company as the source reported it.
          examples:
            - Acme Corp
          type: string
        custom:
          additionalProperties:
            type: string
          description: The custom map from the request row, echoed back.
          type: object
        error:
          description: >-
            Why the row was not resolved: insufficient_hint (no name, email or
            company to search on), resolution_failed (a strategy failed; retry
            later). Absent when the row was answered, including when nobody was
            found.
          examples:
            - insufficient_hint
          type: string
        firstname:
          description: First name as the source reported it.
          type: string
        headline:
          description: >-
            LinkedIn headline as the source reported it. Usually names the
            current role and company; not a verified current position.
          examples:
            - VP Sales at Acme Corp
          type: string
        lastname:
          description: Last name as the source reported it.
          type: string
        linkedin_slug:
          description: The profile's public identifier, the part of the URL after /in/.
          examples:
            - jean-dupont
          type: string
        linkedin_url:
          description: >-
            The profile the person resolved to. Absent when nobody was found or
            the row errored.
          examples:
            - https://www.linkedin.com/in/jean-dupont
          type: string
        match_reason:
          description: >-
            What the score rests on: which strategy found the profile, and
            whether and how it was verified.
          examples:
            - >-
              Linkup reported its top result as verified on both name and
              company
          type: string
        match_score:
          description: >-
            How sure we are, 0-100, that this profile is the requested person.
            Below 50 the profile is our best guess and may well be someone else.
            Threshold it before spending on the row.
          examples:
            - 85
          format: int64
          maximum: 100
          minimum: 0
          type: integer
        source:
          description: >-
            What found the profile. cache and crm are Tamtam's own records and
            the account's CRM, free; sales_navigator, linkup and web_search are
            searches we ran, charged.
          enum:
            - cache
            - crm
            - sales_navigator
            - linkup
            - web_search
          examples:
            - linkup
          type: string
      required:
        - charged
      type: object
    ErrorDetail:
      additionalProperties: false
      properties:
        location:
          description: >-
            Where the error occurred, e.g. 'body.items[3].tags' or
            'path.thing-id'
          type: string
        message:
          description: Error message text
          type: string
        value:
          description: The value at the given location
      type: object
  securitySchemes:
    apikeyAuth:
      description: Account API key passed in the Authorization header
      in: header
      name: Authorization
      type: apiKey
    bearerAuth:
      description: Bearer JWT obtained via the OAuth 2.1 authorization flow
      scheme: bearer
      type: http

````