Skills
Chapter 1 of 10
Migrate Exa, Tavily, Perplexity, or Firecrawl web-data integrations completely to the appropriate Parallel products while preserving application behavior.
11 minutes · 2,433 words · 9 sections
Replace the provider boundary end to end. Treat a successful HTTP response as the midpoint, not completion: migrate request construction, response consumers, dependencies, configuration, tests, and operational behavior.
Resolve <skill-root> to the directory containing this SKILL.md. Resolve every bundled reference and script from that directory, regardless of the current working directory. The scanner uses only the Python standard library. If Python 3.9 or newer is unavailable, perform equivalent repository searches with the harness’s file-search tools and state that the bundled scan was not run.
search_queries.finance_search through Parallel’s general index using Search, Chat, or Task according to the consumed contract, and stop only when a hard market-data coverage, freshness, or raw-result requirement remains unpreserved. Keep Agent API model routing, sandbox, MCP, and existing custom-function capabilities separate unless the user explicitly expands the migration scope.AGENTS.md, CLAUDE.md, and CONTRIBUTING.md. Preserve unrelated work and never reset or discard user changes.Record the current branch and working-tree state before editing. Run the bundled scanner from the target repository:
python3 <skill-root>/scripts/scan_provider_usage.py .Use --format json for machine-readable output. The scanner intentionally skips dependency/generated directories, binaries, unreadable files, and oversized files; it cannot identify provider-neutral consumers from field names alone. Treat it as an inventory aid, not proof of completeness. Inspect the results and then trace each provider response to its consumers. Also inspect:
Run the existing focused tests before editing when feasible. Record which behavior is currently covered, which failures are pre-existing, and which behavior must be verified manually.
Before editing, write a decision row for every provider call site:
| Call site | Provider product | Consumed behavior | Parallel route | Semantic gap | Action |
|---|---|---|---|---|---|
path:line | Search, Scrape, Agent, etc. | Inputs, outputs, lifecycle, and policy the caller relies on | Exact product path, if any | Anything the route cannot preserve | migrate, retain, or block |
Choose exactly one action before changing the call:
migrate only when the proposed route preserves the consumed contract or the user has already approved the named difference;retain when the call is outside the migration boundary or is the smallest safe way to preserve an unsupported capability;block when the requested boundary cannot be completed without a user decision. Name the smallest decision, and continue any independent migrate rows.Do not use a broader Parallel product merely to eliminate a provider import. A plausible result shape is not evidence that source scope, spend controls, model behavior, lifecycle, or privacy policy remains equivalent.
Consider both designs before editing:
Prefer the design that localizes future search-provider changes and minimizes edits to unrelated callers. If the application publishes the old provider’s raw response, either preserve only the documented application contract through a normalizer or update all consumers together.
Build every Parallel Search API request around these facts:
search_queries is required. Supply at least one non-empty keyword query; use two or three diverse keyword queries when the calling flow can provide them.objective is optional but recommended. Put the self-contained web-research goal there, not the whole user conversation or answer-format instructions.https://api.parallel.ai/v1/search, x-api-key, and PARALLEL_API_KEY for direct REST calls.parallel-web package for both Python and TypeScript unless the detected framework has a current first-party Parallel integration that preserves the needed contract.Classify every legacy input before translating it:
objective;search_queries;advanced_settings.source_policy;For static calls, write an explicit objective and two or three keyword probes. For model tools, use the exact-three-query schema in references/integration-patterns.md (opens in a new tab). A one-query direct-call fallback is only for an already keyword-style legacy value and must be evaluated. Do not silently truncate intent, invent keyword variants, add a hidden planner, or move hard filters into prose.
Apply the provider mapping only after that classification. Preserve only settings that implement a real product requirement; unnecessary advanced_settings can reduce quality.
Validate runtime values against the Parallel V1 contract before sending them. Pay particular attention to query count/length, objective length, the combined 200-domain limit, date normalization, and supported location codes. Do not carry the old provider’s numeric ranges forward implicitly.
Update every consumer to the Parallel response shape. The Search API returns ranked results with url, optional title, optional publish_date, and an excerpts array. It does not return the old provider’s relevance score, generated answer, image fields, response time, or full-page body.
Preserve field semantics, not just field names. A date-only publish_date does not restore an old timestamp’s time-of-day precision, a search_id is not a session identifier, and SKU usage counts are not provider credits or dollar cost. Normalize only when the application contract defines the conversion; otherwise make the contract change explicit.
Route non-search behavior explicitly:
session_id.For Firecrawl, classify the product before choosing a route. Search generally maps to Search; public-URL markdown or full content may map to Extract; structured multi-page research may map to Task only when Task preserves the required source scope, spend policy, quality choice, and lifecycle. Exact known-URL structured extraction instead favors Extract plus an application-owned model/parser. Research Index, Crawl, Map, Parse uploads, Browser, Interact, Monitor, screenshots, and other rich scrape behavior are not Search field mappings. Follow references/firecrawl.md (opens in a new tab) and preserve separate capabilities until an explicit replacement is approved.
Do not fill missing fields with plausible-looking constants. Remove obsolete consumers, redesign the application contract, or use the appropriate Parallel API.
parallel-web for Search, Extract, or Task; openai for Chat unless the application already has a compatible client; no SDK when direct REST is the simpler existing pattern.retain row still depends on it, then regenerate the lockfile with the repository’s package manager.migrate rows. Keep shared provider setup until retained calls have their own explicit boundary.PARALLEL_API_KEY to checked-in environment templates, validation schemas, setup scripts, deployment manifests, examples, and docs. Remove a legacy key from those surfaces only when no retained runtime capability still needs it.Never expose or rewrite real secret values in logs, reports, patches, or fixtures.
Add or update tests for:
search_queries, mode, filters, dates, and location;Preserve the repository’s test execution contract. If its focused tests previously stubbed the provider package and ran without installing that SDK, stub the replacement SDK or keep imports behind the injected boundary too. Rerun the exact pre-migration test command in an equivalently clean environment; a pass that depends on an ambient package is not evidence that the repository remains self-contained.
Then run, in order:
python3 <skill-root>/scripts/scan_provider_usage.py . --provider <legacy-provider> --fail-on-legacy when that provider is being removed completely;--fail-on-legacy, classify every finding, and then scan only the migrated roots or use narrow --exclude paths for isolated retained modules; never exclude a mixed search/non-search boundary;exa, tavily, perplexity, sonar-, firecrawl, exact model assignments to sonar, routed perplexity/sonar model IDs, package names, endpoints, and key names, excluding <skill-root> if the skill is installed inside the target repository;PARALLEL_API_KEY is already available, without printing it.An ambient credential does not by itself authorize a paid network call. When authorized, use a small, non-sensitive synthetic query and inspect warnings, result ordering, excerpts, and error behavior. Compare representative production queries only when the user approves sending them to both providers or an existing repository test policy already permits that exact comparison. Do not require the user to paste secrets.
Finish only when all applicable statements are true:
finance_search path preserves the consumed final-answer or finance_results contract through an evaluated Parallel route and, when needed, an application-owned normalizer; unresolved hard coverage or freshness requirements are explicit blockers.migrate, retain, or block decision, and no block row was edited as though the gap were resolved.spark-1-* model choices, and synchronous/asynchronous behavior are preserved or changed only with explicit approval; a domain allow-list, omitted budget, or guessed Task processor does not satisfy this gate.Install this repository
npx skills add parallel-web/parallel-agent-skills/plugin marketplace add parallel-web/parallel-agent-skillsSkills install per repository, not per chapter — the CLI has no documented per-skill form, so we do not print one.
Migrate Exa, Tavily, Perplexity, or Firecrawl web-data integrations completely to the appropriate Parallel products while preserving application behavior. Use when replacing these providers' SDKs or REST calls, dependencies, environment variables, request parameters, response parsing, model tools, search-plus-scrape paths, full-content or answer-synthesis paths, tests, and documentation; separating unsupported research-index, crawl, browser, file-parse, monitor, or other non-search capabilities; auditing for leftover provider usage; or finishing and verifying an in-progress provider migration.
The verbatim description from this skill’s front matter — the string an agent matches on to decide whether to load it.
main, last pushed 3 August 2026.SKILL.md, not by matching a directory convention. One layout observed: skills/*/SKILL.md.h1 and no skipped levels:.claude-plugin/marketplace.json by Parallel Web Systems, declaring 1 plugin. It is read for editorial metadata only — never as the skill index, which is always the repository tree./parallel-web/parallel-agent-skills.md, and each chapter at its own .md URL.9 files · 117 KB
Everything this skill ships beside its prose. All of it is set here, as subchapters of chapter 1.
Documentation the agent loads on demand, rather than up front.
Executable code the skill can run.
Everything else published alongside the skill.