Install LangChain, build your first chain with LCEL, write prompt templates, and use output parsers. The foundations of every LangChain application.
A content generation pipeline — a chain that takes a topic, generates a blog post title, then expands it into an outline. Two chained LLM calls, properly composed with LCEL.
# Core LangChain + OpenAI integration pip install langchain langchain-openai # Or for Anthropic/Claude pip install langchain langchain-anthropic # Set your API key export OPENAI_API_KEY="sk-..." # or export ANTHROPIC_API_KEY="sk-ant-..."
Which model to use: This course uses OpenAI's gpt-4o-mini and Anthropic's Claude Haiku interchangeably. They're both fast and cheap. The LangChain code is identical except the import and model name.
LCEL is the modern way to compose LangChain components. It uses the pipe operator | to chain components together. Each component's output feeds into the next.
from langchain_openai import ChatOpenAI from langchain_core.prompts import ChatPromptTemplate from langchain_core.output_parsers import StrOutputParser # 1. The model model = ChatOpenAI(model="gpt-4o-mini", temperature=0.7) # 2. A prompt template prompt = ChatPromptTemplate.from_template( "Write a compelling blog post title about: {topic}" ) # 3. An output parser (extracts text from the response) parser = StrOutputParser() # 4. Chain them together with LCEL pipe operator chain = prompt | model | parser # 5. Invoke the chain result = chain.invoke({"topic": "building AI apps with LangChain"}) print(result)
The | operator connects components. The chain reads left to right: prompt formats the input → model generates a response → parser extracts the string.
Hard-coding prompts as strings doesn't scale. Prompt templates let you define the structure once and fill in variables at runtime.
from langchain_core.prompts import ChatPromptTemplate # System + human message template prompt = ChatPromptTemplate.from_messages([ ("system", "You are a {role}. Be {tone}."), ("human", "{question}") ]) # The template needs all variables when invoked chain = prompt | model | StrOutputParser() result = chain.invoke({ "role": "senior software engineer", "tone": "direct and concise", "question": "What are the biggest mistakes in API design?" }) print(result)
The power of LCEL is composing complex multi-step workflows. Here's the content pipeline — title generation feeds into outline generation:
from langchain_openai import ChatOpenAI from langchain_core.prompts import ChatPromptTemplate from langchain_core.output_parsers import StrOutputParser from langchain_core.runnables import RunnablePassthrough model = ChatOpenAI(model="gpt-4o-mini") parser = StrOutputParser() # Chain 1: topic → title title_prompt = ChatPromptTemplate.from_template( "Write ONE compelling blog post title about: {topic}" ) title_chain = title_prompt | model | parser # Chain 2: title → outline outline_prompt = ChatPromptTemplate.from_template( "Create a 5-section blog post outline for this title: {title}" ) outline_chain = outline_prompt | model | parser # Combine: topic → title → outline full_pipeline = ( {"title": title_chain} | outline_chain ) result = full_pipeline.invoke({"topic": "LangChain for production AI"}) print(result)
What's RunnablePassthrough? It passes the input through unchanged — useful when you need to forward original values alongside transformed ones in a chain.
Day 2 shows how to build chatbots that remember context across multiple turns.
Day 2: Memory and ConversationBefore moving on, confirm understanding of these key concepts: