Build AI Apps with LangChain and Python — 2026 Guide

Sanjeev SharmaSanjeev Sharma
5 min read

Advertisement

Introduction

Why This Matters

LangChain is the most widely adopted framework for building production AI applications in Python. It provides the abstractions needed to go from "hello world with an LLM" to fully featured applications with memory, retrieval, tool use, and multi-step reasoning — all without writing all the plumbing from scratch.

In 2026, AI-augmented applications are mainstream. Backend engineers are expected to integrate LLMs into APIs, build document Q&A systems, create internal chatbots, and automate workflows using language model reasoning. LangChain's modular design works with OpenAI, Anthropic, Google Gemini, and open-source models alike.

Understanding LangChain's core abstractions — chains, prompts, retrievers, and agents — makes you significantly more effective at building AI features quickly and reliably.

Installation

pip install langchain langchain-openai langchain-community chromadb pypdf

Set your API key:

import os
os.environ["OPENAI_API_KEY"] = "your-key-here"

Basic LLM Call

from langchain_openai import ChatOpenAI
from langchain_core.messages import HumanMessage, SystemMessage
 
llm = ChatOpenAI(model="gpt-4o", temperature=0)
 
messages = [
    SystemMessage(content="You are a helpful Python tutor."),
    HumanMessage(content="Explain Python decorators in one paragraph."),
]
 
response = llm.invoke(messages)
print(response.content)

Prompt Templates

from langchain_core.prompts import ChatPromptTemplate
 
template = ChatPromptTemplate.from_messages([
    ("system", "You are an expert in {domain}. Answer concisely."),
    ("human", "{question}"),
])
 
prompt = template.invoke({
    "domain": "Python performance optimization",
    "question": "When should I use multiprocessing vs asyncio?",
})
 
llm = ChatOpenAI(model="gpt-4o")
response = llm.invoke(prompt)
print(response.content)

LCEL Chains (LangChain Expression Language)

from langchain_core.prompts import ChatPromptTemplate
from langchain_openai import ChatOpenAI
from langchain_core.output_parsers import StrOutputParser
 
llm = ChatOpenAI(model="gpt-4o")
 
prompt = ChatPromptTemplate.from_template(
    "Summarize this text in 3 bullet points:\n\n{text}"
)
 
chain = prompt | llm | StrOutputParser()
 
result = chain.invoke({
    "text": """
    Python is a high-level, general-purpose programming language. Its design philosophy
    emphasizes code readability with the use of significant indentation. Python is
    dynamically typed and garbage-collected. It supports multiple programming paradigms.
    """
})
print(result)

Retrieval-Augmented Generation (RAG)

from langchain_community.document_loaders import PyPDFLoader
from langchain.text_splitter import RecursiveCharacterTextSplitter
from langchain_openai import OpenAIEmbeddings, ChatOpenAI
from langchain_community.vectorstores import Chroma
from langchain_core.prompts import ChatPromptTemplate
from langchain_core.output_parsers import StrOutputParser
from langchain_core.runnables import RunnablePassthrough
 
# Load and split documents
loader = PyPDFLoader("document.pdf")
docs = loader.load()
 
splitter = RecursiveCharacterTextSplitter(chunk_size=1000, chunk_overlap=200)
chunks = splitter.split_documents(docs)
 
# Create vector store
embeddings = OpenAIEmbeddings()
vectorstore = Chroma.from_documents(chunks, embeddings)
retriever = vectorstore.as_retriever(search_kwargs={"k": 4})
 
# Build RAG chain
template = """Answer the question based only on the context below.
If you cannot answer, say "I don't know".
 
Context: {context}
 
Question: {question}"""
 
prompt = ChatPromptTemplate.from_template(template)
llm = ChatOpenAI(model="gpt-4o")
 
def format_docs(docs):
    return "\n\n".join(doc.page_content for doc in docs)
 
rag_chain = (
    {"context": retriever | format_docs, "question": RunnablePassthrough()}
    | prompt
    | llm
    | StrOutputParser()
)
 
answer = rag_chain.invoke("What is the main topic of this document?")
print(answer)

Conversation Memory

from langchain_openai import ChatOpenAI
from langchain_core.prompts import ChatPromptTemplate, MessagesPlaceholder
from langchain_core.messages import HumanMessage, AIMessage
 
llm = ChatOpenAI(model="gpt-4o")
 
prompt = ChatPromptTemplate.from_messages([
    ("system", "You are a helpful assistant."),
    MessagesPlaceholder(variable_name="history"),
    ("human", "{input}"),
])
 
chain = prompt | llm
 
history = []
 
def chat(user_message: str) -> str:
    response = chain.invoke({"input": user_message, "history": history})
    history.append(HumanMessage(content=user_message))
    history.append(AIMessage(content=response.content))
    return response.content
 
print(chat("My name is Alice."))
print(chat("What is my name?"))  # Should remember "Alice"

LangChain Agents with Tools

from langchain_openai import ChatOpenAI
from langchain_core.tools import tool
from langchain.agents import create_tool_calling_agent, AgentExecutor
from langchain_core.prompts import ChatPromptTemplate, MessagesPlaceholder
 
@tool
def get_weather(city: str) -> str:
    """Get the current weather for a city."""
    # Replace with real weather API call
    return f"It is sunny and 22°C in {city}."
 
@tool
def calculate(expression: str) -> str:
    """Evaluate a mathematical expression safely."""
    try:
        result = eval(expression, {"__builtins__": {}})
        return str(result)
    except Exception as e:
        return f"Error: {e}"
 
tools = [get_weather, calculate]
llm = ChatOpenAI(model="gpt-4o")
 
prompt = ChatPromptTemplate.from_messages([
    ("system", "You are a helpful assistant with access to tools."),
    ("human", "{input}"),
    MessagesPlaceholder(variable_name="agent_scratchpad"),
])
 
agent = create_tool_calling_agent(llm, tools, prompt)
executor = AgentExecutor(agent=agent, tools=tools, verbose=True)
 
result = executor.invoke({"input": "What is the weather in Tokyo and what is 15 * 24?"})
print(result["output"])

Common Mistakes

  • Using deprecated LLMChain instead of LCEL (prompt | llm | parser)
  • Not chunking documents before embedding — context windows are limited
  • Storing API keys in source code — use environment variables or secret managers
  • Using too large a chunk size — reduces retrieval precision
  • Not adding overlap between chunks — causes context loss at boundaries

Best Practices

  • Use LCEL chains (| operator) for composable, type-safe pipelines
  • Set temperature=0 for deterministic outputs; use higher values for creativity
  • Implement streaming for long-running responses in user-facing applications
  • Use langsmith for tracing and debugging LangChain applications
  • Cache embeddings with a persistent vector store to avoid re-computing on restart

Key Takeaways

  • LangChain provides abstractions for prompts, LLMs, retrievers, memory, and agents
  • LCEL (LangChain Expression Language) uses | to compose chains: prompt | llm | parser
  • RAG combines document retrieval with LLM generation for knowledge-grounded answers
  • @tool decorator turns a Python function into an agent-usable tool
  • ChatPromptTemplate with MessagesPlaceholder enables conversation memory
  • LangChain works with OpenAI, Anthropic, Google Gemini, and open-source Ollama models
  • Use LangSmith for tracing, debugging, and evaluating LangChain applications in production

Advertisement

Sanjeev Sharma

Written by

Sanjeev Sharma

Full Stack Engineer · E-mopro

Related reading