# AI Job Search & Fit Scorer — 10 Sources + V3 Matching (`nomad-agent/ai-job-fit-scorer`) Actor

All-in-one developer job search and fit scoring: search 10 public sources or score your own jobs against a résumé or profile. Get a gate-aware shortlist with fit evidence, skill gaps, hard-requirement checks, and application links.

- **URL**: https://apify.com/nomad-agent/ai-job-fit-scorer.md
- **Developed by:** [Nomad Dev](https://apify.com/nomad-agent) (community)
- **Categories:** Jobs, AI, Automation
- **Stats:** 2 total users, 1 monthly users, 33.3% runs succeeded, 0 bookmarks
- **User rating**: No ratings yet

## Pricing

$20.00 / 1,000 retained job fit results

This Actor is paid per event. You are not charged for the Apify platform usage, but only a fixed price for specific events.

Learn more: https://docs.apify.com/actors/running/actors-in-store.md#pay-per-event

## What's an Apify Actor?

Actors are web data automations that power AI and operations. They run on the Apify platform to scrape websites, process data, connect APIs, and automate workflows.
In Batch mode, an Actor accepts a well-defined JSON input, performs an action which can take anything from a few seconds to a few hours,
and optionally produces a well-defined JSON output, datasets with results, or files in key-value store.
In Standby mode, an Actor provides a web server which can be used as a website, API, or an MCP server.
Actors are written with capital "A".

## How to integrate an Actor?

If asked about integration, you help developers integrate Actors into their projects.
You adapt to their stack and deliver integrations that are safe, well-documented, and production-ready.
The best way to integrate Actors is as follows.

- **AI agents and MCP clients** — the [Apify MCP server](https://docs.apify.com/integrations/mcp.md) at `https://mcp.apify.com` (remote, streamable HTTP, OAuth on first use).
- **Agentic workflows and local Actor development** — [Agent Skills](https://apify.com/.well-known/agent-skills/index.json) with the [Apify CLI](https://docs.apify.com/cli/docs.md): `npm install -g apify-cli`, then `apify login`.
- **JavaScript/TypeScript projects** — the official [JS/TS client](https://docs.apify.com/api/client/js/docs.md): `npm install apify-client`.
- **Python projects** — the official [Python client](https://docs.apify.com/api/client/python/docs.md): `pip install apify-client`.
- **Any other language** — the [REST API](https://docs.apify.com/api/v2.md).

For usage examples, see the [API](#api) section below.

For more details, see Apify documentation as [Markdown index](https://docs.apify.com/llms.txt) and [Markdown full-text](https://docs.apify.com/llms-full.txt).

# README

## AI Job Search & Fit Scorer — 10 Sources + V3 Matching

Turn one résumé or structured profile into a ranked, source-linked shortlist of
developer jobs. One run can search and deduplicate 10 public job sources, apply
evidence-gated fit scoring, and return both a raw 0–100 fit and a safer 0–5
actionability score. You can also skip search and score normalized jobs you
already have.

No model key is required. In the default shortlist mode, each returned match
costs **$0.02**; scored jobs below the delivery threshold and trustworthy empty
searches have no result-event charge.

> This is an independent, unofficial search integration. It is not affiliated
> with or endorsed by LinkedIn or any source-site operator. Review source terms,
> privacy requirements, and applicable law for your use case.

### What you can build

- **A personal job shortlist:** search current developer roles and see why each
  returned job fits and what is missing. Switch to Audit to inspect blocked or
  held jobs.
- **A career-product matching step:** add an inspectable job-versus-candidate
  score to a job board, coaching workflow, or internal research tool.
- **A scored job tracker:** send stable, deduplicated evaluations to Google
  Sheets through the supplied n8n or Make starters.
- **An agent tool:** let an MCP client run a bounded search, inspect exact-run
  evidence, and read the result dataset.
- **A batch-scoring API:** submit your own `nomad-agent-job-v1` records from an
  upstream Actor run or dataset.

The Actor is stateless. Scheduling, alerts, application actions, user history,
and destination writes belong in your downstream workflow.

### Why use this Actor

- **Search and fit scoring in one run:** no paid child Actor runs or stacked
  source fees.
- **Two scores with different jobs.** Raw fit measures role similarity; the
  0–5 delivery score is reduced by explicit contradictions such as work mode,
  location, language, authorization, seniority, or role family.
- **Evidence, not just a number.** Every row includes a short rationale, gaps,
  blocking gates, static decision, model receipt, source provenance, and stable
  hashes.
- **Bounded by design.** Cap jobs, AI verdicts, concurrency, and total Actor
  charge. A fixed owner-provider circuit breaker stops further AI work rather
  than allowing unbounded spend.
- **Automation-safe identity.** Upsert candidate/job evaluations by `matchKey`;
  preserve `evaluationKey` as the receipt for the exact content and scoring run.

### Quick start: add your candidate evidence

The fresh Apify Console form contains a bounded three-source search and evaluates
at most three jobs (**at most $0.06** in result-event charges), but it deliberately
does not invent candidate evidence. Add exactly one of `candidateProfile`,
`resume`, or `resumeText` before running. Missing candidate evidence fails before
any source is searched or any paid work begins.

The structured-profile example shown in the input help is illustrative only; it
is never inserted into a new run. Replace its values with evidence-backed facts
if you copy it.

For a one-result first run, keep **Search + score**, select one source, set
**Maximum jobs** to `1`, and use an evidence-backed structured profile:

```json
{
  "mode": "search",
  "search": {
    "sources": ["linkedin"],
    "keywords": ["platform engineer"],
    "location": "Madrid",
    "postedWithinDays": 14,
    "maxItemsPerSource": 1
  },
  "candidateProfile": {
    "primaryRole": "Platform Engineer",
    "targetTerms": ["Platform Engineer", "Backend Engineer"],
    "skills": ["Python", "PostgreSQL", "Docker"],
    "seniorityLevels": ["mid"],
    "remoteLocations": ["Spain", "European Union"],
    "hybridLocations": ["Madrid, Spain"],
    "onsiteLocations": [],
    "workArrangementPreferencesComplete": true
  },
  "maxItems": 1,
  "resultMode": "shortlist",
  "minDeliveryScore": 2,
  "aiConcurrency": 1
}
```

Replace the example with facts supported by the candidate's evidence. Leave an
unknown field empty instead of guessing. The complete three-source example is
in [`examples/search-input.json`](examples/search-input.json).

### Score jobs you already have

Set `mode` to `score-jobs`, provide exactly one candidate source, and choose one
job source:

- `jobs`: inline `nomad-agent-job-v1` records;
- `sourceDatasetId`: an existing Apify dataset, read only;
- `sourceActorRunId`: one exact terminal successful Actor run. Add
  `expectedSourceBuild` when you need an immutable upstream-build check.

```json
{
  "mode": "score-jobs",
  "sourceDatasetId": "YOUR_DATASET_ID",
  "candidateProfile": {
    "primaryRole": "Data Engineer",
    "targetTerms": ["Data Engineer", "Analytics Engineer"],
    "skills": ["Python", "SQL", "dbt"],
    "remoteLocations": ["European Union"],
    "hybridLocations": [],
    "onsiteLocations": [],
    "workArrangementPreferencesComplete": true
  },
  "maxItems": 25,
  "resultMode": "shortlist",
  "minDeliveryScore": 2
}
```

See [`examples/inline-input.json`](examples/inline-input.json) for a complete
inline job record.

### Candidate inputs

Choose exactly one:

- `candidateProfile`: structured, evidence-grounded facts and preferences;
- `resume`: a text-based PDF or TXT uploaded in the Apify UI;
- `resumeText`: plain text for API clients.

`preferences` can add explicit role, location, work-mode, language, contract,
or other constraints. The Actor does not invent a search query from a résumé;
`search.keywords` remains required in search mode.

### Search sources

| Input key | Public source |
|---|---|
| `linkedin` | LinkedIn public job pages |
| `remote_boards` | Remote job boards |
| `builtin` | Built In |
| `justjoinit` | Just Join IT |
| `nofluffjobs` | No Fluff Jobs |
| `hackernews` | Hacker News “Who is Hiring?” |
| `ycombinator_was` | Y Combinator Work at a Startup |
| `wttj` | Welcome to the Jungle |
| `infojobs` | InfoJobs |
| `tecnoempleo` | Tecnoempleo |

The default selects LinkedIn, remote boards, and Just Join IT. Cross-source
merging is fair, normalized records are deduplicated before scoring, and full
job-description evidence is required.

Filter support varies. Location is native only on some sources; Built In and No
Fluff Jobs use developer categories instead of native keyword search. A strict
`remoteOnly` search excludes hybrid and unknown arrangements. The exact
per-source result and supported-filter evidence is recorded in `RUN-SUMMARY`.

### Understand the two scores

The Actor uses FindJobs scoring v3:

1. deterministic checks classify hard contradictions, recoverable uncertainty,
   and plausible candidates;
2. eligible jobs receive a pinned AI verdict with a raw `fitScore` from 0–100;
3. hard gates can clamp the separate `deliveryScore` from 0–5;
4. rows are ordered by delivery score first, then raw fit.

Use `fitScore` to understand similarity. Use `deliveryScore`,
`recommendation`, and `blockingGates` to decide whether a match is actionable.
An attractive skills overlap cannot hide a known hard constraint. AI failure is
reported as `ai_failed`, never silently converted to a zero score.

### Choose shortlist or audit output

`resultMode` controls what reaches the dataset and the result-event meter:

- `shortlist` (default) returns only rows with `evaluationStatus: "scored"`
  and `deliveryScore >= minDeliveryScore`. The default threshold is `2`, and
  equality counts. Filtered scores, static drops, holds, and failures are not
  returned or charged.
- `audit` preserves the complete evaluation dataset: scored rows, static
  drops, static and forward-cap holds, and `ai_failed` rows. This keeps the
  previous billing behavior: every retained row except `ai_failed` is charged.
  `minDeliveryScore` is recorded but does not filter Audit output.

Use the gate-adjusted `deliveryScore` for shortlist delivery. A high raw
`fitScore` can coexist with a low delivery score when a hard requirement is
contradicted. `minRankToForward` is different: it controls which jobs reach AI
after static screening, not which completed scores are returned.

### Output

Each returned dataset row follows `nomad-ai-job-fit-v1`. In Shortlist mode all
rows are successfully scored and meet the delivery threshold; in Audit mode
the same schema also represents drops, holds, and failures. This is a compact
excerpt; the actual row preserves the normalized job, gates, static decision,
scoring receipt, provenance, and content hashes:

```json
{
  "schemaVersion": "nomad-ai-job-fit-v1",
  "jobKey": "linkedin:1234567890",
  "fitScore": 82,
  "deliveryScore": 4,
  "recommendation": "strong",
  "evaluationStatus": "scored",
  "title": "Platform Engineer",
  "company": "Example Labs",
  "location": "Madrid, Spain",
  "blockingGates": [],
  "why": "Strong role and Python platform overlap.",
  "gapSummary": "Kubernetes depth is not explicit.",
  "url": "https://www.linkedin.com/jobs/view/1234567890"
}
```

`matchKey` is the stable candidate-plus-job destination key. `evaluationKey`
changes with the exact candidate snapshot, job content, scoring contract, or
evaluation time.

The default key-value store also contains `RUN-SUMMARY` with schema
`nomad-ai-job-fit-run-summary-v4`. It records source outcomes, result policy,
warnings, candidate hashes (not résumé text), model/provider usage, billing
receipts, and the terminal reason. Its counts always include `staticDropped`,
`staticHeld`, `aiScored`, `aiFailed`, `resultFilteredOut`, and `outputRows`, even
when no row is returned. A consumer should reconcile that summary with the
exact run and dataset before writing results downstream.

### API example

This one-result call pins an immutable build and caps the result charge at
`$0.02`:

```bash
curl --request POST \
  --header "Authorization: Bearer $APIFY_TOKEN" \
  --header "Content-Type: application/json" \
  --data @examples/search-input.json \
  "https://api.apify.com/v2/actors/nomad-agent~ai-job-fit-scorer/runs?build=0.1.12&waitForFinish=120&maxItems=1&maxTotalChargeUsd=0.02"
```

Always keep the returned run ID. Continue only after that exact run is
`SUCCEEDED` with exit code `0` and build `0.1.12`; then read its
`defaultDatasetId` and `RUN-SUMMARY`. Storage metadata can settle just after a
run finishes, so boundedly re-read the same run and storages when counts or
charge receipts have not reconciled yet. Never substitute “last run” state.

### Ready-made integrations

The public, credential-free starter pack pins an exact live-verified runtime
build; inspect its evidence manifest before repinning:

- [REST run-and-fetch example](https://github.com/Exdenta/nomad-agent-job-scrapers/tree/main/integrations/api)
- [Hosted Apify MCP call descriptor](https://github.com/Exdenta/nomad-agent-job-scrapers/tree/main/integrations/mcp)
- [n8n → Google Sheets workflow](https://github.com/Exdenta/nomad-agent-job-scrapers/tree/main/integrations/n8n)
- [Make → Google Sheets blueprint](https://github.com/Exdenta/nomad-agent-job-scrapers/tree/main/integrations/make)
- [Zapier editor specification](https://github.com/Exdenta/nomad-agent-job-scrapers/tree/main/integrations/zapier)
- [Contract, setup, and evidence guide](https://github.com/Exdenta/nomad-agent-job-scrapers/blob/main/docs/ai-job-fit-scorer.md)

The files are inactive and contain no credentials. Local contract validation
and live Actor proof do not prove a user's n8n, Make, Zapier, or Google Sheets
destination; test a disposable destination before enabling a schedule.

### Pricing and limits

| Result mode | `job-fit-result` is charged when | Price |
|---|---|---:|
| `shortlist` (default) | A scored row meets `minDeliveryScore` and is returned | **$0.020/returned match ($20 per 1,000)** |
| `audit` | A complete evaluation row is retained; `ai_failed` is never charged | **$0.020/retained non-failure row ($20 per 1,000)** |

Examples: one charged row is `$0.02`, 25 are `$0.50`, and 100 are `$2.00`.
There is no separate search, résumé, run-start, or model-key fee. In Shortlist
mode, scored rows below the threshold, drops, holds, and `ai_failed` rows are
uncharged. Trustworthy empty searches, all-source failures, and work excluded
by the total-charge gate also have no result-event charge.

The owner-funded provider route is capped at `$0.20/M` prompt tokens and
`$1.20/M completion tokens`, allows at most two provider attempts per logical
AI call, and has a fixed $0.25 circuit breaker per run.

The Actor caps a run at 200 unique evaluations, AI concurrency at 8, source
concurrency at 10, résumé uploads at 5 MB / 50 pages / 8,000 readable
characters, and job-description evidence at 20,000 characters. The
owner-provider circuit breaker
can turn later AI-dependent rows into unbilled `ai_failed` results when its
reserved envelope is exhausted.

### Caveats and failure behavior

- Public sites can change, rate-limit, block, or omit fields. One source can be
  partial while other sources still return usable rows.
- A source teaser is not accepted as a full job description. Supplied jobs over
  the description limit fail validation; searched descriptions may be
  explicitly truncated and marked.
- A validated zero-row source is a clean empty outcome. Unverified empties,
  all-source failure, or only invalid/incomplete records fail rather than
  pretending the search was clean.
- Search caches source responses for the configured TTL. Set
  `cacheTtlSeconds: 0` when a canary must force a fresh source request.
- Duplicate source identities with conflicting supplied content fail closed.
- `maxTotalChargeUsd` limits how many jobs can be evaluated before scores are
  known. A low charge cap can therefore bound the evaluated prefix even when
  some later results would have been filtered and uncharged in Shortlist mode.
- The Actor evaluates one candidate per run and does not learn from clicks or
  previous runs.
- Scores are decision support, not facts about a person or a substitute for
  reviewing the source posting.

### Privacy and responsible use

- Only public job pages are in scope. The Actor does not use user cookies,
  borrowed accounts, login/paywall bypasses, or CAPTCHA evasion.
- Résumés are processed in memory and are not written as a separate dataset or
  copied into every fit prompt. The original Actor input/upload remains subject
  to Apify retention controls.
- Extracted candidate evidence and fit prompts are sent through the configured
  OpenRouter/OpenAI route with provider data collection denied. No
  zero-data-retention claim is made.
- File URLs are restricted to Apify upload hosts; arbitrary URL fetching is
  rejected.
- Dataset and upstream-run inputs are read only. The Actor never applies to a
  job, changes source data, or makes an automated hiring decision.

Verify the source posting and keep a human responsible for application and
hiring decisions.

# Actor input Schema

## `mode` (type: `string`):

Choose Search + score to find current jobs, or Score supplied jobs to evaluate normalized jobs you already have.

## `search` (type: `object`):

Used only in Search + score. The fresh form searches three public sources for software engineer roles and fetches at most three jobs per source. Edit sources, terms, and filters for your market. Collectors run inside this Actor—there are no paid child Actor runs or stacked child fees.

## `jobs` (type: `array`):

JSON array of complete nomad-agent-job-v1 records. Every item needs top-level schemaVersion, identity, data, custom, llm, and raw; identity needs source plus externalId or url, and raw.description contains the posting text. Copy the working shape from README → Score jobs you already have or examples/inline-input.json. Use this, sourceDatasetId, or sourceActorRunId—never more than one. Hard limits: 200 records and 20,000 plain-text description characters per job; oversized evidence is rejected, never truncated.

## `sourceDatasetId` (type: `string`):

Paste the immutable Apify dataset ID—not the dataset name or URL. Each dataset item must be one complete nomad-agent-job-v1 record. The dataset is read only and never modified. Use only one supplied-job source.

## `sourceActorRunId` (type: `string`):

Paste the exact upstream run ID—not the Actor ID, build ID, or run URL. The run must be terminal SUCCEEDED with exit code 0; this Actor reads that run's default dataset as nomad-agent-job-v1 records. Use only one supplied-job source.

## `expectedSourceBuild` (type: `string`):

Optional guard for sourceActorRunId. Enter the upstream run's exact immutable build ID or build number; the run fails instead of reading jobs when it does not match.

## `maxItems` (type: `integer`):

Maximum unique jobs to evaluate (1–200). In search mode this caps the merged, deduplicated result set; in score-jobs mode it caps the supplied source.

## `candidateProfile` (type: `object`):

JSON object with at least one of primaryRole, targetTerms, skills, or freeText. Optional seniority, experience, language, location, and contract constraints must be evidence-backed. The displayed example is illustrative and is not prefilled. Use exactly one of this, Résumé, or Résumé text.

## `resume` (type: `string`):

Text-based PDF or UTF-8 text, up to 5 MB, 50 PDF pages, and 8,000 readable characters. It is read in memory and sent once for structured profile extraction; it is not written as a separate dataset artifact or repeated in each fit prompt.

## `resumeText` (type: `string`):

Plain-text alternative for API clients, up to 8,000 readable characters. Use exactly one of candidateProfile, resume, or resumeText.

## `preferences` (type: `string`):

Up to 4,000 characters of explicit role, location, work-mode, language, contract, or other constraints. Unknowns are never guessed.

## `resultMode` (type: `string`):

Shortlist (default) returns and charges only successfully scored rows whose deliveryScore meets minDeliveryScore. Audit returns the complete evaluation dataset, including static\_drop, static\_hold, forward\_cap\_hold, and ai\_failed rows; as before, every Audit row except ai\_failed is charged.

## `minDeliveryScore` (type: `integer`):

Inclusive 0–5 output threshold used only in Shortlist mode. Default 2. deliveryScore includes hard-gate reductions, so it is safer for delivery than raw fitScore alone. Audit mode records this value but does not filter by it.

## `minRankToForward` (type: `integer`):

V3 static candidates below this 0–100 rank are held before AI (default 30). Hard contradictions are always dropped.

## `maxAiItems` (type: `integer`):

Cap AI verdict calls after static selection (0–200). Remaining eligible jobs receive forward\_cap\_hold rather than a fabricated score.

## `recoverHolds` (type: `boolean`):

Also evaluate v3 recoverable holds. Disabled by default so uncertain static evidence remains visibly held.

## `aiConcurrency` (type: `integer`):

Concurrent fit verdict calls (1–8). Lower this for smaller or latency-sensitive batches.

## Actor input object example

```json
{
  "mode": "search",
  "search": {
    "sources": [
      "linkedin",
      "remote_boards",
      "justjoinit"
    ],
    "keywords": [
      "software engineer"
    ],
    "postedWithinDays": 14,
    "maxItemsPerSource": 3,
    "cacheTtlSeconds": 1800,
    "concurrency": 3,
    "sourceTimeoutSecs": 120
  },
  "sourceDatasetId": "a1B2c3D4e5F6g7H8I",
  "sourceActorRunId": "a1B2c3D4e5F6g7H8I",
  "expectedSourceBuild": "0.1.12",
  "maxItems": 3,
  "candidateProfile": {
    "primaryRole": "Software Engineer",
    "targetTerms": [
      "Software Engineer",
      "Backend Engineer"
    ],
    "skills": [
      "Python",
      "TypeScript",
      "SQL",
      "Docker"
    ],
    "seniorityLevels": [
      "mid"
    ],
    "yearsExperience": 4,
    "workableLanguages": [
      {
        "language": "English",
        "level": "professional",
        "evidence": "Fake demo profile: professional working proficiency"
      }
    ],
    "workableLanguagesComplete": false,
    "acceptedWorkArrangements": [
      "remote"
    ],
    "remoteLocations": [
      "Worldwide"
    ],
    "hybridLocations": [],
    "onsiteLocations": [],
    "workArrangementPreferencesComplete": false,
    "acceptedContractTypesComplete": false,
    "freeText": "Fake demo candidate for testing the Actor. Replace every value with your own evidence before using the results."
  },
  "resultMode": "shortlist",
  "minDeliveryScore": 2,
  "minRankToForward": 30,
  "recoverHolds": false,
  "aiConcurrency": 2
}
```

# Actor output Schema

## `dataset` (type: `string`):

No description

## `runSummary` (type: `string`):

No description

# API

You can run this Actor programmatically using our API. Below are code examples in JavaScript, Python, and CLI, as well as the OpenAPI specification and MCP server setup.

## JavaScript example

```javascript
import { ApifyClient } from 'apify-client';

// Initialize the ApifyClient with your Apify API token
// Replace the '<YOUR_API_TOKEN>' with your token
const client = new ApifyClient({
    token: '<YOUR_API_TOKEN>',
});

// Prepare Actor input
const input = {
    "mode": "search",
    "search": {
        "sources": [
            "linkedin",
            "remote_boards",
            "justjoinit"
        ],
        "keywords": [
            "software engineer"
        ],
        "postedWithinDays": 14,
        "maxItemsPerSource": 3,
        "cacheTtlSeconds": 1800,
        "concurrency": 3,
        "sourceTimeoutSecs": 120
    },
    "maxItems": 3,
    "resultMode": "shortlist",
    "minDeliveryScore": 2,
    "aiConcurrency": 2
};

// Run the Actor and wait for it to finish
const run = await client.actor("nomad-agent/ai-job-fit-scorer").call(input);

// Fetch and print Actor results from the run's dataset (if any)
console.log('Results from dataset');
console.log(`💾 Check your data here: https://console.apify.com/storage/datasets/${run.defaultDatasetId}`);
const { items } = await client.dataset(run.defaultDatasetId).listItems();
items.forEach((item) => {
    console.dir(item);
});

// 📚 Want to learn more 📖? Go to → https://docs.apify.com/api/client/js/docs

```

## Python example

```python
from apify_client import ApifyClient

# Initialize the ApifyClient with your Apify API token
# Replace '<YOUR_API_TOKEN>' with your token.
client = ApifyClient("<YOUR_API_TOKEN>")

# Prepare the Actor input
run_input = {
    "mode": "search",
    "search": {
        "sources": [
            "linkedin",
            "remote_boards",
            "justjoinit",
        ],
        "keywords": ["software engineer"],
        "postedWithinDays": 14,
        "maxItemsPerSource": 3,
        "cacheTtlSeconds": 1800,
        "concurrency": 3,
        "sourceTimeoutSecs": 120,
    },
    "maxItems": 3,
    "resultMode": "shortlist",
    "minDeliveryScore": 2,
    "aiConcurrency": 2,
}

# Run the Actor and wait for it to finish
run = client.actor("nomad-agent/ai-job-fit-scorer").call(run_input=run_input)

# Fetch and print Actor results from the run's dataset (if there are any)
print(f"💾 Check your data here: https://console.apify.com/storage/datasets/{run.default_dataset_id}")
for item in client.dataset(run.default_dataset_id).iterate_items():
    print(item)

# 📚 Want to learn more 📖? Go to → https://docs.apify.com/api/client/python/docs/quick-start

```

## CLI example

```bash
echo '{
  "mode": "search",
  "search": {
    "sources": [
      "linkedin",
      "remote_boards",
      "justjoinit"
    ],
    "keywords": [
      "software engineer"
    ],
    "postedWithinDays": 14,
    "maxItemsPerSource": 3,
    "cacheTtlSeconds": 1800,
    "concurrency": 3,
    "sourceTimeoutSecs": 120
  },
  "maxItems": 3,
  "resultMode": "shortlist",
  "minDeliveryScore": 2,
  "aiConcurrency": 2
}' |
apify call nomad-agent/ai-job-fit-scorer --silent --output-dataset

```

## MCP server setup

```json
{
    "mcpServers": {
        "apify": {
            "type": "http",
            "url": "https://mcp.apify.com/?tools=fetch-actor-details,nomad-agent/ai-job-fit-scorer"
        }
    }
}

```

The hosted server signs you in with OAuth on first connect, so no API token belongs in this config. Clients without OAuth support can send an `Authorization: Bearer <APIFY_API_TOKEN>` header instead, using a token from API & Integrations in Apify Console (https://console.apify.com/settings/integrations).

## OpenAPI specification

Download the OpenAPI definition: https://api.apify.com/v2/actors/mBRj1sgHTWmoPJEcb/builds/FWyEWn1da2RW3q7t8/openapi.json
