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

# Work through your ParaAI matches

> List the ParaAI matches hiring managers send you, see which ones need you first, and read each candidate in full.

A ParaAI match is a request from a hiring manager. They looked at a candidate profile and asked for that specific candidate on a specific role. Paraform sends the request to you because the candidate is in your CRM.

This is different from [recommended roles](/recruiter/guides/recommended-roles), where Paraform's model suggests roles for a candidate. Here, a person asked.

You need a personal key with `candidates:read`, `roles:read`, and `submissions:read`. A key with **All read access** has all three.

## List your pending matches

[`GET /recruiter/paraai-recommendations`](/recruiter/api-reference/list-para-ai-recommendations) returns your pending matches, oldest first.

```bash theme={null}
curl "https://external-api.paraform.com/api/external/v1/recruiter/paraai-recommendations" \
  -H "Authorization: Bearer $PARAFORM_API_KEY"
```

| Field | What it tells you |
| - | - |
| `actionBucket` | What to do next. See [Decide what to act on](#decide-what-to-act-on). |
| `daysUntilExpiry` | Whole days left before a pending match expires. `0` on its last day, `null` once the match is resolved. |
| `hiringManagerName`, `hiringManagerNote` | Who asked, and their own words on why they want this candidate |
| `candidate` | Who the candidate is: `name`, `title`, `oneLiner`, `location`, `linkedinUrl`, and the `candidateId` |
| `role` | The role: `name`, `company` (with its confidential search flags), `locations`, `compensation`, your fee as `feePercent`, and its links in `urls` |
| `application` | How far your submission got, once you've submitted. `null` fields until then. |

`role.urls.browse` is the role page. `role.urls.recruit` is your workspace on the role, and is `null` until you're approved on it.

<Warning>
  When `role.company.confidentialSearch` is `true`, the company is running a confidential search. In anything a candidate sees, call the employer `role.company.anonymizedName` and never use `role.company.name`.
</Warning>

## Decide what to act on

A pending match expires 7 days after it's sent. Unresolved expired matches can pause ParaAI matching for you, so the oldest pending matches are the most urgent. Rows come back oldest first, so start at the top. `daysUntilExpiry` tells you how long each one has left.

`actionBucket` says where each match stands:

| `actionBucket` | Meaning |
| - | - |
| `new` | Nobody has contacted the candidate yet |
| `needs_submission` | You marked the candidate as contacted, but haven't submitted them |
| `expired` | The window closed |
| `closed` | You submitted the candidate or passed on the match |

The endpoint is read-only. Contact, pass, and submit in the Paraform app.

## Filter by status

`status` narrows the list. It's `pending` by default.

| `status` | Returns |
| - | - |
| `pending` | Matches still waiting for you |
| `expired` | Matches whose window closed |
| `dismissed` | Matches you passed on |
| `submitted` | Matches you submitted a candidate for |
| `all` | Every match |

```bash theme={null}
curl "https://external-api.paraform.com/api/external/v1/recruiter/paraai-recommendations?status=all" \
  -H "Authorization: Bearer $PARAFORM_API_KEY"
```

Pending matches on closed roles are left out. Resolved matches stay, so you keep your history. A page holds at most 20 matches. See [Pagination](/pagination) for paging through more. The cursor marks a position in the list, so you can contact, pass, or submit matches while you page without skipping any.

## Read the candidate in full

Pass `candidate.candidateId` to [`GET /recruiter/candidates/{candidateId}`](/recruiter/api-reference/get-recruiter-candidate) for the candidate's work history, education, preferences, and your CRM note:

```bash theme={null}
curl "https://external-api.paraform.com/api/external/v1/recruiter/candidates/$CANDIDATE_ID" \
  -H "Authorization: Bearer $PARAFORM_API_KEY"
```

It returns `404` if the candidate has since left your CRM. See [Find a candidate and read their full profile](/recruiter/guides/candidates) for the fields it returns.

## What you can read

* **Only matches sent to you.** A teammate's matches never appear, even if you're an agency owner who can see them in the app.
* **Your fee only when you can see payment.** `role.feePercent` is `null` when your agency hides payment from its members. Agency owners always see it.

## Errors

See [Errors](/errors) for the envelope.

| Status | `type` | What to do |
| - | - | - |
| `403` | `permission_error` | The key is missing `candidates:read`, `roles:read`, or `submissions:read`. Create a key with all three. |


This documentation is built and hosted on [Mintlify](https://mintlify.com), a developer documentation platform.