Chapter 4: Building a research summarization engine
The introduction frames a research summarization engine as an LLM application that turns a user query and web search results into a summary.
After this chapter you will be able to
- Research summarization engine purpose. Describe, at a high level, how the research summarization engine uses a user query, web searches, and the findings to produce a summary.
- Research summararization workflow. Explain how a researcher can use an LLM to summarize multiple web pages and how an automated engine removes the repeated manual steps.
- Project virtual environment. Describe creating and activating a virtual environment from the ch04 terminal, then installing the project’s required packages.
- Virtual environment run configuration. Explain why the section recommends a custom VS Code run configuration and identify the operating-system difference it gives for the Python interpreter path.
- Core engine dependencies. Describe the three capabilities the research summarization engine needs: web search, text extraction from related web pages, and a utility to initialize an LLM client.
- Search results and URLs. Describe what the DuckDuckGo search wrapper’s results method returns and what the test script should print.
- Scraped web result content. Explain that the engine uses Beautiful Soup to scrape pages from the search result list, and that the scraped content can include irrelevant material because the LLM will extract the relevant parts.
- OpenAI client setup. Describe how to prepare the OpenAI API key and where to put the function that instantiates the client for this use case.
- LLM JSON conversion utility. Describe how the utility handles JSON text from the LLM, including what it returns when the JSON is malformed.
- Multiple targeted web searches. Explain how query rewriting changes the research engine: an LLM turns one research request into multiple targeted queries, and the engine searches and gathers results for each. Describe how clearer, more focused queries can improve the research.
- Research assistant instruction prompt. Explain how a dedicated prompt selects a suitable research assistant and generates instructions tailored to the user’s question. Describe how its three examples clarify the requested output and why it returns JSON.
- Web search prompt handoff. Trace how the web search prompt uses the instructions produced by the assistant-selection prompt, and explain why it returns JSON and includes the original user question.
- Search volume and budget tradeoff. Explain how the number of web searches and results per search affects report accuracy and diversity while increasing the amount of web content to summarize and the cost to consider.
- Instructions to search queries. Trace how the user’s research question leads to research-assistant instructions and then to a list of web search queries. Explain that the instructions are the primary input to the search-query prompt.
- Search results as query–URL pairs. Describe how web_search() results are collected and then flattened from dictionaries with multiple URLs per query into dictionaries with one query and one result URL each.
- Web result text collection. Describe how the implementation collects page text from search results and what it stores in result_text_list.
- Web result summary records. Describe how the language model uses SUMMARY_PROMPT_TEMPLATE to summarize each web page and what information is retained with each summary.
- Final report input preparation. Trace how the engine turns summarized web results into input for the final report prompt and uses that input to generate a report.
- LCEL chain composition. Explain how LCEL organizes LLM application components into chains and what the Runnable protocol provides.
- Web Research chain architecture. Trace how the master Web Research chain combines the engine’s mini-chains to produce a report.
- Two levels of parallelization. Explain where the chain-based engine runs work in parallel and why this improves efficiency.
- Research assistant selection flow. Trace how the selection prompt feeds into the LLM so it can select a research assistant and prompt instructions based on the user’s question.
- Parsed assistant selection output. Describe how StrOutputParser() and to_obj() turn the LLM response into output that is easier to use in the chain.
- Web Searches chain input. Explain how the Web Searches chain uses the previous chain’s output to generate web searches related to the user’s query.
- Search result URL handoff. Explain how the Search Result URLs sub-chain uses a query from the Web Searches chain and prepares its results for later stages.
- Per-page summary construction. Describe what the Search Result Text and Summary sub-chain does for one URL and how RunnableParallel is used within it.
- Parallel summaries and joining. Trace how the assembled chain turns multiple URL results into one joined text block.
- Web Research chain flow. Trace how the Web Research chain turns web searches into a final report, including the role of map() in running summarization sub-chains concurrently.
What it builds on
- Summarizing across documents (chapter 3) · Summarizing across documents provides context for combining information from multiple pages.
- Setting up the environment for this chapter (chapter 2) · Earlier environment setup provides background for creating and activating a Python environment.
Section by section
Introduction
The introduction frames a research summarization engine as an LLM application that turns a user query and web search results into a summary.
- Research summarization engine purpose: Describe, at a high level, how the research summarization engine uses a user query, web searches, and the findings to produce a summary.
Why it matters: This gives you the overall purpose of the application before the chapter develops its components.
Key terms: research summarization engine, user queries, web searches
4.1 Overview of a research summarization engine
The section contrasts manually using an LLM to summarize web pages with an engine that automates research searches, summaries, and a final report.
- Research summararization workflow: Explain how a researcher can use an LLM to summarize multiple web pages and how an automated engine removes the repeated manual steps.
Why it matters: This distinction explains what work the research summarization engine is meant to automate.
Key terms: semiautomated summarization, research summarization engine, consolidated summary, final report
4.2 Setting up the project
This section sets up a VS Code Python workspace and virtual environment for the chapter, then configures VS Code to run and debug code with that environment.
- VS Code Python setup: Describe how to prepare VS Code for the project by installing the Microsoft Python extension and opening the ch04 folder with an integrated terminal.
Why it matters: This gives you a workspace and terminal in the right folder before you set up the project environment. - Project virtual environment: Describe creating and activating a virtual environment from the ch04 terminal, then installing the project’s required packages.
Why it matters: The project needs its virtual environment and packages in place before you run the chapter’s code. - Virtual environment run configuration: Explain why the section recommends a custom VS Code run configuration and identify the operating-system difference it gives for the Python interpreter path.
Why it matters: Selecting the right interpreter keeps VS Code’s run and debug actions in the environment you prepared.
Key terms: VS Code, Python extension, ch04, terminal, virtual environment, required packages, run configuration, launch.json, env_ch04, python field
4.3 Implementing the core functionality
Identifies the capabilities the research summarization engine needs before its core functionality can be implemented.
- Core engine dependencies: Describe the three capabilities the research summarization engine needs: web search, text extraction from related web pages, and a utility to initialize an LLM client.
Why it matters: These dependencies define what the engine needs to gather web content and use an LLM.
Key terms: research summarization engine, web searches, extracting text, LLM client
4.3.1 Implementing web searching
This section introduces a DuckDuckGo web-search wrapper, shows how to test the search function, and explains why that wrapper was chosen.
- Search results and URLs: Describe what the DuckDuckGo search wrapper’s results method returns and what the test script should print.
Why it matters: The URL output shows what the search function supplies to the rest of the research engine. - DuckDuckGo wrapper choice: Explain why the section chooses DuckDuckGoSearchAPIWrapper over the named alternatives.
Why it matters: The choice lets the project perform searches without obtaining a search-engine API key.
Key terms: DuckDuckGo, results method, link, web_searching_try.py, DuckDuckGoSearchAPIWrapper, TavilySearchResults, GoogleSearchAPIWrapper, API key
4.3.2 Implementing web scraping
This section introduces scraping pages from web search results with Beautiful Soup and explains why irrelevant scraped content is acceptable at this stage.
- Scraped web result content: Explain that the engine uses Beautiful Soup to scrape pages from the search result list, and that the scraped content can include irrelevant material because the LLM will extract the relevant parts.
Why it matters: It clarifies what the scraping step provides and why its raw output does not have to be clean.
Key terms: Beautiful Soup, web scraping, result list, LLM
4.3.3 Instantiating the LLM client
This subsection prepares the OpenAI API key and a client-instantiation function for the research summarization engine.
- OpenAI client setup: Describe how to prepare the OpenAI API key and where to put the function that instantiates the client for this use case.
Why it matters: These steps prepare the credentials and client function used by the engine.
Key terms: OpenAI GPT-5 nano, OpenAI API key, .env, .env_example, llm_models.py
4.3.4 JSON to Python object converter
This subsection introduces a utility for converting LLM-generated JSON text into Python data, with a fallback for malformed JSON.
- LLM JSON conversion utility: Describe how the utility handles JSON text from the LLM, including what it returns when the JSON is malformed.
Why it matters: It gives the engine a predictable fallback when the LLM produces invalid JSON.
Key terms: JSON text, Python object, dictionary, list, utilities.py
4.4 Enhancing the architecture with query rewriting
This section adds LLM-generated search queries to the research engine and explains why the extra searches may improve results while increasing sequential response time.
- Multiple targeted web searches: Explain how query rewriting changes the research engine: an LLM turns one research request into multiple targeted queries, and the engine searches and gathers results for each. Describe how clearer, more focused queries can improve the research.
Why it matters: Targeted searches can give the engine more useful results to draw on for its report. - Sequential search response cost: Explain the response-time cost of adding web searches when they run sequentially, and distinguish that initial approach from the later possibility of parallel processing.
Why it matters: Better search coverage has a response-time trade-off in the initial implementation.
Key terms: query rewriting, multiple query generation, targeted searches, sequential processing, response time, parallelization
4.5 Prompt engineering
This section previews prompt engineering for the research summarization engine before its building blocks are assembled.
4.5.1 Crafting web search prompts
The section explains how two prompts prepare a research assistant’s instructions and web search queries from a user’s question.
- Research assistant instruction prompt: Explain how a dedicated prompt selects a suitable research assistant and generates instructions tailored to the user’s question. Describe how its three examples clarify the requested output and why it returns JSON.
Why it matters: Tailored instructions give the later web search prompt a relevant perspective for the user’s question. - Web search prompt handoff: Trace how the web search prompt uses the instructions produced by the assistant-selection prompt, and explain why it returns JSON and includes the original user question.
Why it matters: The handoff keeps search generation aligned with the selected assistant and preserves structured output for later processing.
Key terms: persona, research assistant, few-shot prompt, JSON, {assistant_instructions}, web search prompt, user question
4.5.2 Crafting summarization prompts
4.5.3 Research report prompt
4.6 Initial implementation
Introduces the initial, easy-to-follow implementation of the research summarization engine and previews the workflow and later LCEL-based improvements.
4.6.1 Importing functions and prompt templates
4.6.2 Setting constants and input variables
This subsection sets the research engine’s search-volume configuration and identifies the user’s research question as its sole input variable.
- Search volume and budget tradeoff: Explain how the number of web searches and results per search affects report accuracy and diversity while increasing the amount of web content to summarize and the cost to consider.
Why it matters: These settings determine the scope of each research request and its expected cost. - Research question input variable: State what the application’s sole input variable captures.
Why it matters: It separates what the user supplies from the application’s configuration settings.
Key terms: web searches, results per search, tokens, budget, input variable, research question
4.6.3 Instantiating the LLM client
4.6.4 Generating the web searches and collecting the results
This section generates web search queries from research-assistant instructions, collects result URLs, and flattens them into query–URL pairs for the next stage.
- Instructions to search queries: Trace how the user’s research question leads to research-assistant instructions and then to a list of web search queries. Explain that the instructions are the primary input to the search-query prompt.
Why it matters: The searches are generated using instructions chosen for the reader’s research question. - Search results as query–URL pairs: Describe how web_search() results are collected and then flattened from dictionaries with multiple URLs per query into dictionaries with one query and one result URL each.
Why it matters: Individual query–URL pairs make the collected links ready for the following scraping stage. - Debugger inspection of instructions: Describe how to pause the code in VS Code and inspect the generated assistant_instructions, either in the Variables panel or by printing it in the Debug Console.
Why it matters: Inspecting the intermediate value lets you see what instructions the later query-generation prompt receives.
Key terms: assistant_instructions, content property, assistant_instructions_dict, web_search_queries_list, web_search(), searches_and_result_urls, search_query_and_result_url_list, flatten, breakpoint, Python Debugger: Current File
4.6.5 Scraping the web results
This section uses web_scrape() to collect text from pages linked in the search results and stores it for later summarization.
- Web result text collection: Describe how the implementation collects page text from search results and what it stores in result_text_list.
Why it matters: Collecting the page text supplies the material for the next summarization step.
Key terms: web_scrape(), result_text_list, search results
4.6.6 Summarizing the web results
This section summarizes each scraped web page and preserves its search query and URL for the final research report.
- Web result summary records: Describe how the language model uses SUMMARY_PROMPT_TEMPLATE to summarize each web page and what information is retained with each summary.
Why it matters: Keeping each summary with its source and search query makes the collected research usable in the final report.
Key terms: SUMMARY_PROMPT_TEMPLATE, result_text_summary_list, search queries, URLs
4.6.7 Generating the research report
This section combines web-result summaries and source URLs into a final research report, then notes a speed limitation of the sequential implementation.
- Final report input preparation: Trace how the engine turns summarized web results into input for the final report prompt and uses that input to generate a report.
Why it matters: The report prompt needs the collected summaries and their sources together to produce the final response. - Sequential processing speed limit: Explain why the initial research engine becomes slow when the number of web searches and results increases.
Why it matters: It explains the performance limitation of the working first implementation.
Key terms: stringified_summary_list, RESEARCH_REPORT_INSTRUCTIONS, summaries, source URL, sequentially, web searches, results
4.7 Reimplementing the research summary engine in LCEL
This section explains how LCEL organizes the research summarization engine into composable chains and where that design enables parallel execution.
- LCEL chain composition: Explain how LCEL organizes LLM application components into chains and what the Runnable protocol provides.
Why it matters: The common interface makes the engine’s separate processing steps easier to assemble into a workflow. - LCEL execution advantages: Describe the execution and operational benefits the section attributes to LCEL.
Why it matters: These capabilities explain why the section recommends LCEL beyond simply organizing code. - Web Research chain architecture: Trace how the master Web Research chain combines the engine’s mini-chains to produce a report.
Why it matters: This architecture shows how the earlier engine’s steps fit into one chain-based workflow. - Two levels of parallelization: Explain where the chain-based engine runs work in parallel and why this improves efficiency.
Why it matters: The two parallel stages are the section’s concrete example of how the LCEL redesign improves efficiency.
Key terms: LCEL, chain, Runnable protocol, invoke(), stream(), batch(), fallback, parallel execution, execution modes, LangSmith tracing
4.7.1 Assistant Instructions chain
This section builds an LCEL chain that selects a research assistant for a user question, then makes its input and output easier to use in subsequent steps.
- Research assistant selection flow: Trace how the selection prompt feeds into the LLM so it can select a research assistant and prompt instructions based on the user’s question.
Why it matters: The rest of the research process needs an assistant selected for the question. - Explicit question input mapping: Explain why the revised chain uses RunnablePassthrough() to map the input question to a user_question property in a Python dictionary.
Why it matters: Explicit mapping makes the question’s place in the chain clear and preserves it for later steps. - Parsed assistant selection output: Describe how StrOutputParser() and to_obj() turn the LLM response into output that is easier to use in the chain.
Why it matters: These steps replace manual extraction and leave the chain with a dictionary it can work with.
Key terms: assistant_instructions_chain, selection prompt, research assistant, RunnablePassthrough(), user_question, ASSISTANT_SELECTION_PROMPT_TEMPLATE, StrOutputParser(), content property, to_obj(), Python dictionary
4.7.2 Web Searches chain
This section connects the Assistant Instructions chain to a Web Searches chain and shows how to test it with mock input.
- Web Searches chain input: Explain how the Web Searches chain uses the previous chain’s output to generate web searches related to the user’s query.
Why it matters: The prompt needs input in the right format before the LLM can generate searches. - Mock chain test input: Describe how the section tests the Web Searches chain using mock input.
Why it matters: Mocking the preceding chain’s output lets you test this chain on its own.
Key terms: RunnableLambda, WEB_SEARCH_PROMPT_TEMPLATE, Assistant Instructions chain, web searches, assistant_instruction_str, mock input
4.7.3 Search and Summarization chain
This section builds an LCEL chain that finds web pages for a search query, summarizes each page, and joins the summaries.
- Search result URL handoff: Explain how the Search Result URLs sub-chain uses a query from the Web Searches chain and prepares its results for later stages.
Why it matters: Keeping the query and question with each URL gives the later stages the context they need. - Per-page summary construction: Describe what the Search Result Text and Summary sub-chain does for one URL and how RunnableParallel is used within it.
Why it matters: The per-page chain produces summaries that remain tied to their sources. - Parallel summaries and joining: Trace how the assembled chain turns multiple URL results into one joined text block.
Why it matters: This explains how separate page summaries become one result for the larger research workflow.
Key terms: Search Result URLs chain, web_query, web_search(), Web Searches chain, Search Result Text and Summary chain, RunnableParallel, text_summary, source URL, Search and Summarization chain, map()
4.7.4 Web Research chain
This section explains how the LCEL Web Research chain turns multiple web searches into parallel summaries and combines them into a final research report.
- Web Research chain flow: Trace how the Web Research chain turns web searches into a final report, including the role of map() in running summarization sub-chains concurrently.
Why it matters: This flow shows how smaller LCEL chains work together to produce one research report from several searches.
Key terms: Web Research chain, Web Searches chain, Search and Summarization chain, map(), Research Report chain
4.8 Summary
The section recaps how a research summarization engine turns a question into a multisource report and how LCEL organizes its operations.
Where this is used later
- LangGraph basics (chapter 5) · Presents the earlier chain-based research summarization implementation.
- Moving from LangChain chains to LangGraph (chapter 5) · The earlier implementation of a research engine with LangChain chains.
- Original LangChain implementation overview (chapter 5) · The later agent conversion starts from an overview of the original LangChain implementation.
Concepts explained in this chapter
- LCELLCEL is LangChain's composition language for building modular and expressive large-language-model pipelines.
- web searchWeb search is the retrieval of information from publicly accessible internet resources in response to a query.
- scrapingPage scraping is the programmatic extraction of content from web pages.
- pipelineA multi-step workflow is a process composed of several ordered or coordinated operations that collectively accomplish a task.
- parallelismParallel processing is the simultaneous execution of the same or related operations on multiple independent inputs.
- web research chainThe Web Research chain is a workflow that performs multiple web searches, summarizes their results, and combines those summaries into a research report.
- Runnable interfaceThe Runnable interface is a common LangChain programming interface for components that can be invoked and composed in workflows.
- summarizerA summarization engine is a system that generates condensed representations of source content without requiring conversational interaction.
- SQLAn SQL query is a statement written in SQL that specifies data to retrieve or filter from a relational database.
- summarizationSummarization is the generation of a shorter representation that preserves the important information in source content.
- templateA prompt template is a reusable structure that combines user input, context, and optionally examples into a model request.
- prompt engineeringPrompt design is the practice of formulating instructions and context to influence a language model's behavior and output.
- query rewritingQuery rewriting is a technique that transforms an original search request into one or more clearer or more targeted queries to improve retrieval results.
- RunnableParallelRunnableParallel is a LangChain runnable component that executes runnable operations across inputs in parallel.
- pipe operatorThe pipe operator is syntax that passes the output of one operation to the next operation in a chain.
- few-shot learningPrompt examples are illustrative instances supplied in a prompt to guide a language model toward a desired task behavior or output pattern.
- LangChainLangChain is an open-source framework for building applications that combine language models with data sources, tools, and multi-step workflows.
- language modelA large language model is a neural language model trained on extensive text data to understand and generate language and perform text-based reasoning.
- LLM applicationAn LLM application is software that provides a use-case-specific interface or workflow around a large language model.
- GPT-5-nanoGPT-5-nano is a small GPT-5 model variant intended for fast, lower-cost language processing.
- promptA system prompt is an instruction message supplied to a language model to establish high-level behavior or constraints.
- personaA persona is a prompt specification of the role, expertise, or perspective that a language model should adopt.
These guides are generated from the text of Manning books by Manning's knowledge graph and link to the sections they draw on. The full books are available on liveBook and at manning.com.
