One index, several unrelated documents
Every earlier lesson indexed a small pile of related documents (the three Nimbus policy files). This lesson makes explicit something those lessons already did implicitly: VectorStoreIndex.from_documents() doesn't care whether the documents it's given are related. It's just as happy indexing two documents about *completely different things*, an internal engineering handbook and a customer-facing product FAQ, in the same index, and retrieval will still find the right Nodes for a given question.
This is the common real-world shape: you don't usually build a separate index per document type, you build one index over everything you have (or everything relevant to a given user/scope), and let similarity search sort out which document actually answers a given question. LangChain's equivalent is the same idea: Chroma.from_documents() doesn't care what kind of documents you hand it either, one vector store, arbitrary content.
The fixture data
This lesson's own data/ folder (pre-staged, read as-is):
engineering_handbook.txt: internal process docs, code review rules, on-call rotation, deploy windows, testing requirements.product_faq.txt: customer-facing FAQ about the Cobalt-1 warehouse robot, battery life, flooring requirements, connectivity behavior, supervision ratio.
The two files share no topical overlap (nothing in the FAQ answers an engineering-process question and vice versa), which makes it easy to verify retrieval is actually distinguishing between them.
Source attribution: response.source_nodes
Every QueryEngine response carries .source_nodes, the list of Nodes actually used to synthesize the answer. Each Node's .metadata["file_name"] (inherited from SimpleDirectoryReader, same as every lesson since Lesson 2) tells you which source document it came from. This is how you verify, after the fact, which document(s) backed a given answer, whether by design (Lesson 11's filters) or, as here, by letting an unfiltered search find the right document(s) on its own.
similarity_top_k matters at small scale
This fixture is tiny on purpose, one Node per document, two Nodes total. as_query_engine()'s default similarity_top_k is 2 (llama_index.core.constants.DEFAULT_SIMILARITY_TOP_K), which at this scale would retrieve *both* documents on every question regardless of relevance, hiding the thing worth demonstrating. Setting similarity_top_k=1 for the single-document questions shows retrieval actually distinguishing between the two documents; similarity_top_k=2 for the cross-document question shows both being retrieved and combined on purpose. At real-world scale (many Nodes per document), the default top_k=2 wouldn't have this problem, this lesson's data/ is just small enough that it needs calling out explicitly.
The code, piece by piece
documents = SimpleDirectoryReader(str(DATA_DIR)).load_data()index = VectorStoreIndex.from_documents(documents)Both files load into one list of Documents and build one index, exactly the same call as every earlier lesson, just pointed at two unrelated files instead of three related ones.
narrow_query_engine = index.as_query_engine(similarity_top_k=1)Retrieves only the single most relevant Node per question, at this fixture's scale this means "only the one document that's actually relevant."
sources = sorted({Path(n.metadata["file_name"]).name for n in response.source_nodes})A set comprehension over response.source_nodes, deduplicated and sorted, printed alongside every answer to show exactly which file(s) backed it.
combined_query_engine = index.as_query_engine(similarity_top_k=2)For the one question whose full answer needs a fact from each document (the robot's own safe-hold timeout from the FAQ, plus the on-call acknowledgment window from the handbook), similarity_top_k=2 retrieves one Node from each document, and the LLM synthesizes across both.
Checkpoint
- One
VectorStoreIndexcan span any number of unrelated documents, nothing aboutfrom_documents()requires the documents to be topically related. response.source_nodes[i].metadata["file_name"]is how you attribute an answer back to its source document(s), whether one document or several backed it.similarity_top_kcontrols how many Nodes retrieval pulls back, at small scale (few Nodes per document) it can determine whether retrieval reads as "found the one relevant document" or "returned everything regardless of relevance."- A question phrased to need facts from multiple documents forces a query engine to retrieve from, and synthesize across, more than one source, visible directly in
source_nodes.
If anything here still feels unclear, ask before moving to Lesson 14.