How to create a retriever in LangChain

Retrievers are the handoff point between indexed text and a LangChain RAG or search application. They accept a natural-language query and return Document objects, so application code can fetch context without calling one vector store API directly.

A vector store that already contains documents can expose a retriever through as_retriever(). The local smoke test uses InMemoryVectorStore and a small embedding class so the retrieved result is predictable without an API key or model download.

Production retrieval depends on using the same embedding model for indexing and querying. The smoke test keeps the documents in memory, but the as_retriever() call is the same handoff used by persistent vector stores such as Chroma, Qdrant, PGVector, or Pinecone.

Steps to create a LangChain retriever:

  1. Open an activated Python project environment.
  2. Install LangChain Core and NumPy.
    $ python3 -m pip install --upgrade langchain-core numpy

    InMemoryVectorStore uses NumPy for local similarity search.
    Related: How to install LangChain with pip

  3. Create the retriever test script.
    $ cat > langchain-retriever-create.py <<'PY'
    from langchain_core.documents import Document
    from langchain_core.embeddings import Embeddings
    from langchain_core.vectorstores import InMemoryVectorStore
    
    
    class SupportTicketEmbeddings(Embeddings):
        keywords = ("password", "invoice", "vpn")
    
        def _embed(self, text: str) -> list[float]:
            lowered = text.lower()
            return [float(lowered.count(keyword)) for keyword in self.keywords]
    
        def embed_documents(self, texts: list[str]) -> list[list[float]]:
            return [self._embed(text) for text in texts]
    
        def embed_query(self, text: str) -> list[float]:
            return self._embed(text)
    
    
    documents = [
        Document(
            page_content="Password reset requests go to the identity support queue.",
            metadata={"source": "support-runbook", "topic": "identity"},
        ),
        Document(
            page_content="Invoice export issues go to the billing operations queue.",
            metadata={"source": "support-runbook", "topic": "billing"},
        ),
        Document(
            page_content="VPN connection failures go to the network access queue.",
            metadata={"source": "support-runbook", "topic": "network"},
        ),
    ]
    
    embeddings = SupportTicketEmbeddings()
    vector_store = InMemoryVectorStore(embedding=embeddings)
    vector_store.add_documents(
        documents=documents,
        ids=["identity", "billing", "network"],
    )
    retriever = vector_store.as_retriever(
        search_type="similarity",
        search_kwargs={"k": 2},
    )
    
    results = retriever.invoke("How do I route a password reset?")
    
    for position, document in enumerate(results, start=1):
        source = document.metadata["source"]
        topic = document.metadata["topic"]
        print(f"{position}. {source} / {topic}")
        print(f"   {document.page_content}")
    PY

    The local embedding class makes retrieval deterministic for the smoke test. Use the same production embedding model for both document indexing and retriever queries.

  4. Run the retriever script.
    $ python3 langchain-retriever-create.py
    1. support-runbook / identity
       Password reset requests go to the identity support queue.
    2. support-runbook / network
       VPN connection failures go to the network access queue.

    The first result should show identity because the query and that source document both contain password.

  5. Remove the temporary script.
    $ rm langchain-retriever-create.py