What LangChain Is (and Why It’s Used)
LangChain is a Python/TypeScript framework for building LLM-powered applications. It gives you a cohesive set of abstractions for:
-
Prompting (templates, few-shot, chat message assembly)
-
Model I/O (chat/LLMs, embeddings) with structured post-processing via output parsers
-
Runnables + LCEL: a declarative way to wire steps into reliable, composable pipelines that support invoke, batch, stream, async out of the box
The big idea: you describe what your LLM workflow should do by composing “runnables,” and LangChain optimizes how it runs.
A simple example
Goal: Take a messy product review and return structured JSON: { "sentiment": "...","pros":[...], "cons":[...] }.
Code
# pip install langchain langchain-openai# pip install -U langchain-community faiss-cpu
from langchain.prompts import ChatPromptTemplate
from langchain_openai import ChatOpenAI
from langchain_core.output_parsers import JsonOutputParser
# 1) A very explicit prompt that asks for JSON only
prompt = ChatPromptTemplate.from_messages([
("system", "You are a careful analyst. Extract sentiment, pros, and cons in strict JSON."),
("human", "Review: {review}\n\nReturn ONLY JSON with keys: sentiment, pros, cons.")
])
# 2) The model (any chat model adapter works)
llm = ChatOpenAI(model="gpt-4o-mini")
# 3) Parse the model’s text into a Python dict
parser = JsonOutputParser()
# 4) Compose the pipeline left→right with |
chain = prompt | llm | parser
# ---- Run it ----
example = {
"review": "Loved the battery life and the screen. Setup was confusing and the fan gets loud."
}
print(chain.invoke(example))
# Example output (as a Python dict):
# {
# 'sentiment': 'positive',
# 'pros': ['battery life', 'screen'],
# 'cons': ['confusing setup', 'loud fan']
# }
LCEL
LCEL (LangChain Expression Language) lets you connect components like Unix pipes. Each component is a Runnable with standardized methods: .invoke(), .batch(), .stream(), and async equivalents.
Why You See | in LangChain Code
In plain Python, | is bitwise OR. LangChain overloads | for runnables so that left | right means “pipe the output of the left into the input of the right,” returning a new runnable sequence. This makes chains readable and uniform across sync, async, batch, and streaming modes. It isn’t special to prompts—any Runnable can be piped.
LangChain implements operator overloading via __or__ and __ror__ on its Runnable classes.
A Focused RAG Paragraph (Using LangChain)
A typical Retrieval-Augmented Generation (RAG) chain looks like this in LCEL:
-
Retriever: turns a user question into a vector query and returns top-k documents.
-
Prompt: weaves the question + retrieved context into an instruction.
-
LLM: generates a grounded answer.
-
Parser: normalizes the final text (or JSON) for downstream use.
In LCEL, that becomes:
Code
from langchain_openai import ChatOpenAI, OpenAIEmbeddings
from langchain_core.output_parsers import StrOutputParser
from langchain.prompts import ChatPromptTemplate
from langchain_community.vectorstores.faiss import FAISS
# build retriever (once, during setup)
emb = OpenAIEmbeddings()
vs = FAISS.from_texts(
["doc A ...", "doc B ...", "doc C ..."], embedding=emb
)
retriever = vs.as_retriever(search_kwargs={"k": 4})
rag_prompt = ChatPromptTemplate.from_messages([
("system", "Answer using ONLY the provided context. If unsure, say you don't know."),
("human", "Q: {question}\n\nContext:\n{context}")
])
llm = ChatOpenAI(model="gpt-4o-mini")
to_str = StrOutputParser()
# LCEL composition: retrieve -> map into prompt vars -> LLM -> parse
rag_chain = (
{"context": retriever, "question": lambda x: x["question"]}
| rag_prompt
| llm
| to_str
)
print(rag_chain.invoke({"question": "What does doc B say about X?"}))
This pattern mirrors the official RAG tutorial (retriever → prompt → model → parser) and leverages LCEL’s composability and streaming/batching if needed.
Reference
https://python.langchain.com/docs/introduction/
No comments:
Post a Comment