Summary and motivation
Parallel is a web research API built for AI agents rather than for humans: search that returns LLM-ready excerpts instead of a page of blue links, plus a research model that answers a question with live web evidence and citations.
This proposal covers the integration in #3762, which adds two components:
ParallelWebSearch fills Haystack's existing web-search slot (the role SerperDevWebSearch and SearchApiWebSearch play today), so it drops into any RAG pipeline that already branches on a web-search component.
ParallelChatGenerator is a ChatGenerator whose answers are grounded in live web research with citations, for pipelines that want a researched answer without assembling retrieval, ranking, and prompting themselves.
Use cases this supports in Haystack:
- Web-grounded RAG where the retrieval step needs excerpts sized for a context window rather than whole pages.
- Freshness-sensitive question answering, where a static document store is stale by construction.
- Research agents that need domain and date filtering (
source_policy, after_date) to constrain what evidence is admissible.
- Cost-sensitive pipelines: the search tiers span roughly two orders of magnitude in price per call, so a pipeline can pick a tier per step rather than paying one blended rate.
Adoption signals
Numbers as of 2026-08-20.
-
GitHub stars of the main repository: parallel-web/parallel-sdk-python has 27 stars and 5 forks. The most-starred public repos in the org are parallel-cookbook (114), parallel-agent-skills (69), parallel-web-tools (46), and parallel-sdk-typescript (25). I want to be straightforward that these star counts are small, and say why below.
-
PyPI downloads in the last 30 days of the Python client/SDK: 3,256,226 for parallel-web. I cross-checked this against the public PyPI download dataset on ClickHouse and got 3,220,565 for the same window. Monthly totals have been between 2.2M and 3.4M every month since March 2026, so this is a sustained level rather than a spike.
This is the signal I would weight most heavily, and it is the one that diverges most from the star count: the SDK is consumed as an API client by services, not starred by people browsing GitHub.
One caveat in the interest of not overstating it: this integration does not depend on parallel-web. It calls the REST API through httpx, so its dependency footprint stays light. The download figure is evidence of API adoption, not of code this integration ships.
-
Release activity: latest release 1.3.0 on 2026-08-12. 23 releases since the first on 2025-04-24, with 1.0.0 in June 2026 and three releases in the last quarter, so roughly monthly with tighter clusters around API changes.
-
Maintenance: parallel-web is the official SDK, maintained by Parallel Web Systems, the company behind the API. The SDK repo had commits on 2026-08-20, the day I filed this, and carries 4 open issues. Both the Python and TypeScript SDKs are generated from the same API spec and released together.
-
Haystack community demand: I do not have Discord threads or GitHub issues to point to, and I would rather say so than pad this section. This is me bringing an integration to Haystack rather than responding to existing requests for it.
-
Anything else that shows adoption:
- LiteLLM: Parallel search shipped and is maintained there. PR #30157 (merged) migrated it from the v1beta to the v1 endpoint, and PR #36704 (open) adds Parallel as an LLM provider.
- LlamaIndex: ships
llama-index-tools-parallel-web-systems as a tool package with docs and an example notebook.
- MCP: an official server at
parallel-web/task-mcp, so the API is already reachable from MCP-speaking clients.
- No LangChain or CrewAI integration exists today, so Haystack would be ahead of both rather than behind.
On why I expect interest to grow: the API is young (first SDK release April 2025, 1.0.0 in June 2026), so GitHub stars mostly reflect that age rather than usage, while 3.2M monthly downloads reflect production traffic. The category is also moving quickly, with agent frameworks converging on search tools that return model-ready excerpts and citations instead of scraped HTML. If the download trend and the maintained LiteLLM and LlamaIndex integrations are not enough of a signal yet, I am happy to revisit this in a few months with updated numbers.
Detailed design
The integration lives in integrations/parallel/, distributed as parallel-haystack, and follows the scaffolding layout. It has one runtime dependency beyond haystack-ai.
ParallelWebSearch
haystack_integrations.components.websearch.parallel.ParallelWebSearch
A @component matching the output contract the other web-search components use, so it is substitutable in existing pipelines:
@component.output_types(documents=list[Document], links=list[str])
def run(self, query: str, search_params: dict[str, Any] | None = None): ...
- Init:
api_key (a Secret, PARALLEL_API_KEY by default), top_k, search_params, timeout.
top_k maps to the API's advanced_settings.max_results, so the Haystack-level knob means what a Haystack user expects while the wire call stays idiomatic.
search_params is a passthrough for the API surface that has no Haystack equivalent: objective (defaults to the query), mode (turbo, basic, advanced), max_chars_total, session_id, client_model, and nested advanced_settings covering source_policy domain and date filters, fetch_policy, excerpt_settings, and location. A search_params passed to run fully replaces the init-time value rather than merging into it, so a per-call override is all-or-nothing. Happy to switch that to a merge if you prefer; replacing is the simpler contract to reason about but it does mean a caller overriding one key has to restate the rest.
- Async:
run_async alongside run.
- Serialization:
to_dict / from_dict with the API key handled as a Secret, so pipelines round-trip through YAML without leaking it.
- Documents: each result becomes a
Document whose content is its excerpts joined with " ... ", with title and url in meta, plus the raw excerpts list and publish_date when the API returns them.
Two corner cases worth naming:
- A result with no excerpts still yields a
Document, with empty content, rather than being dropped.
links only collects results that carry a URL, so documents and links are not guaranteed to be the same length. Callers correlating the two should key on meta["url"] rather than on index.
advanced_settings.max_results is only populated from top_k when the caller has not set it explicitly, so an explicit value wins.
ParallelChatGenerator
haystack_integrations.components.generators.parallel.chat.ParallelChatGenerator
Parallel's Responses API is OpenAI-Responses-compatible (POST /v1/responses), so this subclasses Haystack's own OpenAIResponsesChatGenerator rather than reimplementing streaming, tool calls, and ChatMessage conversion. That keeps it aligned with upstream Haystack behavior for free.
- Model:
parallel, the web-research model.
reasoning.effort selects the research tier, trading latency and cost against depth:
client = ParallelChatGenerator(generation_kwargs={"reasoning": {"effort": "low"}})
- Answers are grounded in live web research and carry citations.
Repo plumbing already in #3762
.github/workflows/parallel.yml running tests on PRs and nightly, matching the other integrations.
.github/labeler.yml entry and the README inventory row.
pydoc/config_docusaurus.yml for docs publishing.
- Unit tests for both components, plus integration tests gated on
PARALLEL_API_KEY.
Checklist
If the request is accepted, ensure the following checklist is complete before closing this issue.
Follow the instructions in https://github.com/deepset-ai/haystack-core-integrations/blob/main/CONTRIBUTING.md#create-a-new-integration and use our scaffolding script for the implementation.
Tasks
Implementation PR: #3762
Summary and motivation
Parallel is a web research API built for AI agents rather than for humans: search that returns LLM-ready excerpts instead of a page of blue links, plus a research model that answers a question with live web evidence and citations.
This proposal covers the integration in #3762, which adds two components:
ParallelWebSearchfills Haystack's existing web-search slot (the roleSerperDevWebSearchandSearchApiWebSearchplay today), so it drops into any RAG pipeline that already branches on a web-search component.ParallelChatGeneratoris aChatGeneratorwhose answers are grounded in live web research with citations, for pipelines that want a researched answer without assembling retrieval, ranking, and prompting themselves.Use cases this supports in Haystack:
source_policy,after_date) to constrain what evidence is admissible.Adoption signals
Numbers as of 2026-08-20.
GitHub stars of the main repository:
parallel-web/parallel-sdk-pythonhas 27 stars and 5 forks. The most-starred public repos in the org areparallel-cookbook(114),parallel-agent-skills(69),parallel-web-tools(46), andparallel-sdk-typescript(25). I want to be straightforward that these star counts are small, and say why below.PyPI downloads in the last 30 days of the Python client/SDK: 3,256,226 for
parallel-web. I cross-checked this against the public PyPI download dataset on ClickHouse and got 3,220,565 for the same window. Monthly totals have been between 2.2M and 3.4M every month since March 2026, so this is a sustained level rather than a spike.This is the signal I would weight most heavily, and it is the one that diverges most from the star count: the SDK is consumed as an API client by services, not starred by people browsing GitHub.
One caveat in the interest of not overstating it: this integration does not depend on
parallel-web. It calls the REST API throughhttpx, so its dependency footprint stays light. The download figure is evidence of API adoption, not of code this integration ships.Release activity: latest release
1.3.0on 2026-08-12. 23 releases since the first on 2025-04-24, with 1.0.0 in June 2026 and three releases in the last quarter, so roughly monthly with tighter clusters around API changes.Maintenance:
parallel-webis the official SDK, maintained by Parallel Web Systems, the company behind the API. The SDK repo had commits on 2026-08-20, the day I filed this, and carries 4 open issues. Both the Python and TypeScript SDKs are generated from the same API spec and released together.Haystack community demand: I do not have Discord threads or GitHub issues to point to, and I would rather say so than pad this section. This is me bringing an integration to Haystack rather than responding to existing requests for it.
Anything else that shows adoption:
llama-index-tools-parallel-web-systemsas a tool package with docs and an example notebook.parallel-web/task-mcp, so the API is already reachable from MCP-speaking clients.On why I expect interest to grow: the API is young (first SDK release April 2025, 1.0.0 in June 2026), so GitHub stars mostly reflect that age rather than usage, while 3.2M monthly downloads reflect production traffic. The category is also moving quickly, with agent frameworks converging on search tools that return model-ready excerpts and citations instead of scraped HTML. If the download trend and the maintained LiteLLM and LlamaIndex integrations are not enough of a signal yet, I am happy to revisit this in a few months with updated numbers.
Detailed design
The integration lives in
integrations/parallel/, distributed asparallel-haystack, and follows the scaffolding layout. It has one runtime dependency beyondhaystack-ai.ParallelWebSearchhaystack_integrations.components.websearch.parallel.ParallelWebSearchA
@componentmatching the output contract the other web-search components use, so it is substitutable in existing pipelines:api_key(aSecret,PARALLEL_API_KEYby default),top_k,search_params,timeout.top_kmaps to the API'sadvanced_settings.max_results, so the Haystack-level knob means what a Haystack user expects while the wire call stays idiomatic.search_paramsis a passthrough for the API surface that has no Haystack equivalent:objective(defaults to the query),mode(turbo,basic,advanced),max_chars_total,session_id,client_model, and nestedadvanced_settingscoveringsource_policydomain and date filters,fetch_policy,excerpt_settings, andlocation. Asearch_paramspassed torunfully replaces the init-time value rather than merging into it, so a per-call override is all-or-nothing. Happy to switch that to a merge if you prefer; replacing is the simpler contract to reason about but it does mean a caller overriding one key has to restate the rest.run_asyncalongsiderun.to_dict/from_dictwith the API key handled as aSecret, so pipelines round-trip through YAML without leaking it.Documentwhose content is its excerpts joined with" ... ", withtitleandurlinmeta, plus the rawexcerptslist andpublish_datewhen the API returns them.Two corner cases worth naming:
Document, with empty content, rather than being dropped.linksonly collects results that carry a URL, sodocumentsandlinksare not guaranteed to be the same length. Callers correlating the two should key onmeta["url"]rather than on index.advanced_settings.max_resultsis only populated fromtop_kwhen the caller has not set it explicitly, so an explicit value wins.ParallelChatGeneratorhaystack_integrations.components.generators.parallel.chat.ParallelChatGeneratorParallel's Responses API is OpenAI-Responses-compatible (
POST /v1/responses), so this subclasses Haystack's ownOpenAIResponsesChatGeneratorrather than reimplementing streaming, tool calls, andChatMessageconversion. That keeps it aligned with upstream Haystack behavior for free.parallel, the web-research model.reasoning.effortselects the research tier, trading latency and cost against depth:Repo plumbing already in #3762
.github/workflows/parallel.ymlrunning tests on PRs and nightly, matching the other integrations..github/labeler.ymlentry and the README inventory row.pydoc/config_docusaurus.ymlfor docs publishing.PARALLEL_API_KEY.Checklist
If the request is accepted, ensure the following checklist is complete before closing this issue.
Follow the instructions in https://github.com/deepset-ai/haystack-core-integrations/blob/main/CONTRIBUTING.md#create-a-new-integration and use our scaffolding script for the implementation.
Tasks
mainbranchintegration:<your integration name>has been added to the list of labels for this repositoryImplementation PR: #3762