Skip to main content

Command Palette

Search for a command to run...

LangChain, LangGraph, LangSmith — 첫 AI 에이전트를 만들기 전에 알아야 하는 세 도구의 역할

Updated
13 min read

처음으로 AI 에이전트를 만들어 보려는 백엔드 개발자를 대상으로 합니다. 이름이 비슷한 세 도구 — LangChain, LangGraph, LangSmith — 가 각각 어떤 문제를 풀려고 등장했는지, 어떤 관계로 묶여 있는지, 그리고 어디서부터 손을 대야 하는지를 한 흐름으로 정리합니다. 함께 자주 등장하는 단어(Tool, ReAct, Function Calling, MCP, LangFlow)도 같은 자리에서 짚습니다.

1. 왜 비슷한 이름의 도구가 셋이나 있을까

LLM 애플리케이션이 1년 사이에 부쩍 복잡해졌습니다. "프롬프트에 사용자 입력을 넣고 답을 받는" 한 줄짜리 호출은 데모에서나 통합니다. 실제 서비스는 다음 같은 요구를 받습니다.

  • 사용자 질문을 받아 외부 문서를 검색해 프롬프트에 끼워 넣는 RAG.
  • 모델이 직접 API를 호출하고, 그 결과를 다시 모델이 받아 추론을 이어가는 도구 호출(tool calling).
  • 여러 단계를 거치며 일부 단계에서는 사람이 끼어들고, 또 일부 단계에서는 실패하면 되돌아가는 워크플로.
  • 매 요청마다 어떤 프롬프트, 어떤 입력, 어떤 도구가 어떤 순서로 실행됐는지 사후 추적.
  • 모델·프롬프트를 바꿔도 같은 입력 집합에서 품질이 유지되는지 자동 평가.

이 다섯 가지를 한 라이브러리가 다 해결하면 그 라이브러리는 너무 거대해집니다. LangChain 진영은 책임을 셋으로 쪼개는 길을 택했습니다.

  • LangChain — LLM 애플리케이션을 만들 때 반복되는 "부품"을 표준 인터페이스로 묶은 SDK입니다. 모델, 임베딩, 벡터 스토어, 파서, 메모리, 프롬프트 템플릿, 도구를 같은 모양으로 다룰 수 있게 합니다.
  • LangGraph — 부품들을 조립해서 만든 에이전트가 "상태를 들고 여러 단계를 도는" 워크플로를 그릴 수 있게 해주는 그래프 오케스트레이터입니다. 분기·반복·중단·재개·사람 개입을 정식 모델로 다룹니다.
  • LangSmith — 위 두 도구로 만든(혹은 어떤 프레임워크로 만들든 상관없는) LLM 애플리케이션의 실행을 추적·평가·모니터링하는 별도 SaaS·라이브러리입니다.

세 도구는 경쟁 관계가 아닙니다. LangChain으로 만들고, 복잡해지면 LangGraph로 옮기고, 운영하려면 LangSmith로 들여다본다는 흐름이 공식 문서가 권장하는 표준 동선입니다.

flowchart LR
    USER[App Code] --> LC[LangChain SDK]
    LC -.uses.-> LG[LangGraph Runtime]
    LC --> MODEL[Model Provider]
    LC --> TOOL[Tools / Retrievers]
    LG --> CHK[Checkpointer Store]
    LC -.emits traces.-> LS[LangSmith Platform]
    LG -.emits traces.-> LS

위 그림에서 LangChain은 호출되는 SDK, LangGraph는 그 위에 있는 실행 엔진, LangSmith는 옆에서 모든 실행을 받아 보는 관측 백엔드라는 점만 머리에 넣어 두면 다음 절부터 자연스럽게 이어집니다.

2. LangChain — LLM 애플리케이션의 부품 상자

LangChain은 LLM과 그 주변 컴포넌트를 동일한 인터페이스로 묶는 데 초점을 둔 프레임워크입니다. 공식 저장소는 LangChain을 "agents and LLM-powered applications를 만들기 위한 framework"로 정의합니다.

2.1 모듈 구조

LangChain은 패키지가 여럿입니다. 처음 보면 헷갈리지만, 의존 방향만 잡으면 단순합니다.

  • langchain-coreRunnable, BaseChatModel, BaseRetriever, Document, BaseTool 같은 기본 추상화. 다른 모든 패키지가 의존합니다.
  • langchain — 위 추상화를 조합한 표준 유틸. create_retrieval_chain, create_stuff_documents_chain 같은 함수가 들어 있습니다.
  • langchain-community — 커뮤니티가 기여한 통합. 빠르게 늘었다 줄어들 수 있어서 안정성은 partner 패키지보다 낮습니다.
  • langchain-openai, langchain-anthropic, langchain-google-vertexai 등 partner 패키지 — 특정 공급자별 통합을 별도 배포해서 한 공급자가 변경돼도 다른 사용자가 영향을 받지 않게 분리한 형태입니다.

이렇게 쪼개진 이유는 단순합니다. LLM 제공자 SDK는 분기마다 바뀌고, 통합 코드는 그 변화에 즉시 따라가야 합니다. core를 고정하고 통합만 갈아 끼울 수 있어야 사용자가 한 줄도 안 고치고 새 모델로 옮길 수 있습니다.

2.2 핵심 추상화: Runnable과 LCEL

LangChain v0.1부터 자리잡은 핵심 추상은 Runnable 인터페이스입니다. 입력을 받아 출력을 내보내는 모든 컴포넌트가 Runnable을 구현하면, 파이프 연산자 |로 직렬 합성할 수 있습니다. 이 표기법을 LangChain Expression Language(LCEL)라 부릅니다.

from langchain_openai import ChatOpenAI
from langchain_core.prompts import ChatPromptTemplate
from langchain_core.output_parsers import StrOutputParser

prompt = ChatPromptTemplate.from_messages([
    ("system", "You are a helpful assistant."),
    ("human", "{question}"),
])
model = ChatOpenAI(model="gpt-4o-mini")
parser = StrOutputParser()

chain = prompt | model | parser

print(chain.invoke({"question": "Explain LCEL in one sentence."}))

chain은 한 묶음의 Runnable이고, invoke, stream, batch, ainvoke(비동기)를 모두 지원합니다. 한 번 합성하면 동기/비동기/스트리밍/배치가 같이 따라옵니다. 이 점이 v0.1 이전의 Chain 클래스보다 한 단계 추상이 올라간 부분입니다.

2.3 LangChain이 잘하는 것

다음 같은 일은 LangChain만으로 충분합니다.

  • 단일 모델 호출 + 출력 파싱.
  • 검색-증강 생성(RAG)의 인덱싱·질의 파이프라인 구성.
  • 여러 벡터 스토어/임베딩 공급자를 같은 인터페이스로 다루기.
  • 모델 공급자 교체 ("OpenAI → Anthropic" 같은 한 줄 변경).

2.4 LangChain이 어색해지는 경계

반대로, 다음 같은 요구가 들어오면 LangChain 단독 구성은 빠르게 한계에 부딪힙니다.

  • 상태(state)가 단계마다 누적되고 분기·반복하는 흐름.
  • 도중에 사람이 끼어들어 입력을 수정·승인하는 흐름.
  • 장시간 실행되며 중간 실패 후 그 지점부터 재개해야 하는 흐름.

LCEL은 본질적으로 DAG(방향성 비순환 그래프)에 가까운 파이프라인 합성기입니다. 위 요구는 사이클이 있는 그래프와 영속 상태를 요구합니다. 그래서 등장한 것이 LangGraph입니다.

3. LangGraph — 상태를 들고 도는 에이전트의 그래프

LangGraph 공식 문서는 자신을 "low-level orchestration framework for building stateful agents"로 소개합니다. 두 단어가 핵심입니다. low-level, stateful.

3.1 왜 그래프인가

에이전트는 일반적으로 다음 같은 순환을 돕니다.

  1. 모델이 사용자의 입력과 현재까지의 메시지를 보고, 도구를 호출할지 답을 낼지 결정합니다.
  2. 도구 호출이 결정되면 그 도구를 실행하고, 결과를 다시 메시지 큐에 넣습니다.
  3. 다시 1로 돌아갑니다. 종료 조건은 "모델이 더 이상 도구를 호출하지 않을 때"입니다.

이 흐름은 사이클(loop)이 본질이고, 분기 조건이 있고, 매 노드 사이에 상태가 흐릅니다. LangGraph는 그래서 노드, 엣지, 상태라는 세 가지 1차 시민으로 이 흐름을 모델링합니다.

flowchart LR
    START([START]) --> AGENT[Agent Node\nLLM call]
    AGENT -- has tool_calls --> TOOLS[Tools Node\nrun tools]
    TOOLS --> AGENT
    AGENT -- no tool_calls --> END([END])

3.2 State, StateGraph, MessagesState

LangGraph에서 상태(State) 는 그래프 전체가 공유하는 한 덩어리 딕셔너리입니다. 노드는 상태를 읽고, 일부 키를 갱신해 반환합니다. 갱신은 곧바로 다음 노드에서 보입니다.

상태 스키마는 보통 TypedDict 또는 Pydantic 모델로 선언합니다. 채팅 메시지 리스트가 거의 모든 에이전트에서 등장하기 때문에, 라이브러리는 미리 정의된 MessagesState를 제공합니다.

from typing import Annotated, TypedDict
from langgraph.graph import StateGraph, START, END, MessagesState
from langgraph.prebuilt import ToolNode, tools_condition
from langchain_openai import ChatOpenAI
from langchain_core.tools import tool

@tool
def add(a: int, b: int) -> int:
    """Return a + b."""
    return a + b

model = ChatOpenAI(model="gpt-4o-mini").bind_tools([add])

def call_model(state: MessagesState) -> dict:
    response = model.invoke(state["messages"])
    return {"messages": [response]}

graph = StateGraph(MessagesState)
graph.add_node("agent", call_model)
graph.add_node("tools", ToolNode([add]))

graph.add_edge(START, "agent")
graph.add_conditional_edges("agent", tools_condition)
graph.add_edge("tools", "agent")

app = graph.compile()

graph.compile()이 반환하는 객체 자체가 Runnable이라, LangChain의 다른 컴포넌트와 그대로 합성할 수 있습니다. 즉 LangGraph는 LangChain의 합성 모델을 깨지 않고 그 위에 사이클·상태를 얹습니다.

3.3 Checkpointer — 영속 상태와 재개

LangGraph가 단순한 라이브러리 이상으로 평가받는 이유는 체크포인터(Checkpointer) 추상에 있습니다. 그래프를 컴파일할 때 체크포인터를 끼우면, 각 단계마다 상태가 외부 저장소(메모리·SQLite·PostgreSQL·Redis 등)로 직렬화됩니다.

from langgraph.checkpoint.memory import MemorySaver

app = graph.compile(checkpointer=MemorySaver())

config = {"configurable": {"thread_id": "user-42"}}
app.invoke({"messages": [("user", "1 + 2는?")]}, config=config)
# 며칠 뒤
app.invoke({"messages": [("user", "그 결과에 3을 더해줘.")]}, config=config)

thread_id만 일치시키면 이전 대화 상태가 그대로 살아납니다. 사람이 끼어들어 상태를 수정하거나, 특정 단계에서 멈췄다 다시 시작하는 시간 여행(time travel) 디버깅도 같은 메커니즘 위에서 동작합니다. 개발 단계에서는 MemorySaver, 운영에서는 PostgresSaver처럼 같은 인터페이스의 구현체만 갈아 끼우는 구조입니다.

3.4 prebuilt — create_react_agent

매번 그래프를 손으로 만들 필요는 없습니다. langgraph.prebuilt.create_react_agent는 "도구를 가진 단일 LLM 에이전트"라는 가장 흔한 패턴을 한 줄로 만들어 줍니다.

from langgraph.prebuilt import create_react_agent
from langchain_openai import ChatOpenAI

agent = create_react_agent(
    model=ChatOpenAI(model="gpt-4o-mini"),
    tools=[add],
    prompt="You are a careful arithmetic helper.",
)

result = agent.invoke({"messages": [("user", "12와 30의 합은?")]})
print(result["messages"][-1].content)

내부 구현은 3.2의 그래프와 거의 같습니다. 처음에는 prebuilt로 시작하고, 분기 조건이 복잡해지면 StateGraph를 직접 짜는 단계로 옮겨가면 됩니다.

3.5 LangGraph가 풀어 주는 것

  • 사이클을 정식 모델로 다룬다. 무한 루프 방지를 위한 recursion_limit 같은 안전장치가 내장입니다.
  • 영속 상태(persistence)와 thread별 격리. 사용자 단위·세션 단위 메모리를 직접 짜지 않아도 됩니다.
  • Human-in-the-loop. 특정 노드 앞·뒤에 인터럽트(interrupt)를 걸어 사람의 입력을 기다릴 수 있습니다.
  • 스트리밍과 비동기. 그래프 단위, 노드 단위, 토큰 단위 스트리밍이 모두 가능합니다.

4. LangSmith — 무엇이 왜 잘못됐는지 보기

LangSmith 공식 SDK 저장소는 자신을 "your team이 language model과 intelligent agent를 debug·evaluate·monitor하도록 돕는다"고 소개합니다. 그리고 framework-agnostic임을 명시합니다. LangChain·LangGraph 없이 OpenAI SDK만 직접 쓰는 코드에서도 동작합니다.

4.1 세 가지 기능 축

LangSmith 기능은 크게 셋입니다.

  1. Tracing(추적) — 한 번의 사용자 요청이 만든 호출 트리를 시각화. 입력·출력·토큰 사용량·지연·예외가 노드별로 기록됩니다.
  2. Evaluation(평가) — 데이터셋과 평가자(evaluator)를 이용해 모델·프롬프트 변경 전후 품질을 객관 점수로 비교.
  3. Monitoring·Prompt Management — 운영 환경의 트래픽 통계, 프롬프트 버전 관리, A/B 비교.

4.2 traceable — 가장 작은 통합 단위

LangChain 안에서는 환경변수 LANGSMITH_API_KEYLANGSMITH_TRACING=true만 설정해도 모든 Runnable 호출이 자동으로 LangSmith로 흘러갑니다. 반면 외부 코드에서도 동일한 추적을 원할 때 쓰는 것이 @traceable 데코레이터입니다.

import openai
from langsmith import traceable
from langsmith.wrappers import wrap_openai

client = wrap_openai(openai.Client())

@traceable
def summarize(text: str) -> str:
    resp = client.chat.completions.create(
        model="gpt-4o-mini",
        messages=[{"role": "user", "content": f"Summarize: {text}"}],
    )
    return resp.choices[0].message.content

wrap_openai는 OpenAI 클라이언트의 호출을 자동으로 LangSmith run으로 감쌉니다. @traceable은 그 위에 추가로 함수 단위 부모 run을 만듭니다. 둘이 합쳐져서 한 요청의 호출 트리가 만들어집니다.

4.3 Evaluation — evaluate()

LangSmith의 평가 모델은 "데이터셋 × 타깃 함수 × 평가자"의 곱입니다. 공식 SDK는 이 세 가지를 인자로 받는 evaluate() 헬퍼를 제공합니다.

from langsmith import Client
from langsmith.evaluation import evaluate

client = Client()

def target(inputs: dict) -> dict:
    return {"answer": summarize(inputs["text"])}

def length_under_200(run, example) -> dict:
    out = run.outputs["answer"]
    return {"key": "length_under_200", "score": int(len(out) < 200)}

experiment = evaluate(
    target,
    data="my-summarization-dataset",
    evaluators=[length_under_200],
)

evaluate() 한 번이 곧 한 개의 Experiment입니다. UI에서 두 Experiment를 나란히 놓고 점수 차이를 보면, 프롬프트 변경이 정량적으로 좋은지 나쁜지가 한 화면에 나옵니다. 평가는 사전(offline) 평가와 운영 트래픽 위의 사후(online) 평가 두 가지로 나뉘며, 둘 다 같은 데이터 모델 위에서 동작합니다.

4.4 framework-agnostic의 의미

LangSmith 자체는 추적 프로토콜과 백엔드입니다. LangChain·LangGraph가 아닌 코드도, @traceable 또는 자체 클라이언트로 LangSmith run을 만들 수 있다는 뜻입니다. LlamaIndex·Haystack 같은 다른 프레임워크도 LangSmith 통합을 가집니다. 따라서 "이미 자체 프레임워크가 있는데 추적만 붙이고 싶다"는 요구는 LangSmith로 충분히 풀립니다.

5. 세 도구가 한 흐름으로 어떻게 협업하는가

세 도구가 한 요청을 어떻게 통과하는지 한 그림으로 정리합니다.

flowchart TB
    USER[User Request] --> APP[App Handler]
    APP --> LG[LangGraph App]
    LG --> AGENT[Agent Node]
    AGENT --> MODEL[ChatModel\nLangChain]
    AGENT -- tool_calls --> TOOLS[Tool Node]
    TOOLS --> RETRIEVER[Retriever / API]
    TOOLS --> AGENT
    AGENT -- final --> RESP[Response]
    LG --> CHK[(Checkpointer)]
    AGENT -.trace.-> LS[LangSmith]
    TOOLS -.trace.-> LS
    MODEL -.trace.-> LS
  • 앱 코드는 LangGraph가 컴파일한 그래프를 호출합니다.
  • 그래프 안의 노드는 LangChain의 ChatModel, Retriever, Tool을 그대로 사용합니다.
  • 상태는 체크포인터로 영속화돼 thread별 메모리가 살아남습니다.
  • 모든 노드와 LLM 호출은 LangSmith로 trace가 흘러갑니다. 실패하면 어디서 어떤 입력으로 실패했는지가 한 화면에 보입니다.
  • 운영 중에 데이터셋이 충분히 쌓이면, LangSmith에서 evaluate()로 회귀 테스트를 돌립니다.

같은 코드가 개발·운영·평가의 세 무대를 모두 통과하는 구조라는 점이 가장 큰 가치입니다.

6. 언제 무엇을 골라야 하는가

상황 1순위 도구 이유
단일 LLM 호출 + 출력 파싱 LangChain LCEL 한 줄로 끝납니다.
RAG 인덱싱/질의 파이프라인 LangChain 통합된 Retriever 인터페이스가 풍부합니다.
도구를 호출하며 사이클 도는 에이전트 LangGraph 사이클·상태가 1차 시민입니다.
사람이 중간에 승인/수정해야 하는 워크플로 LangGraph interrupt와 checkpoint로 정식 지원합니다.
운영 중 모든 호출 추적 LangSmith LANGSMITH_TRACING=true 한 줄.
프롬프트 변경 전후 품질 비교 LangSmith evaluate() + Dataset.
LangChain을 쓰지 않는데 추적만 필요 LangSmith framework-agnostic.

가장 자주 하는 실수는 두 가지입니다. 첫째, 단일 호출에 LangGraph를 끌어다 쓰는 것 — 상태도 없고 사이클도 없는데 그래프부터 그리면 코드가 무겁기만 합니다. 둘째, 에이전트를 LangChain의 LCEL만으로 짜려고 끝까지 버티는 것 — 분기·반복이 늘면 결국 자기만의 그래프 엔진을 만들고 있게 됩니다. 그쯤이면 LangGraph로 옮길 신호입니다.

7. 첫 에이전트 — 한 파일에서 끝까지

위 흐름을 한 파일로 압축한 예시입니다. 의존성은 pip install -U langchain langgraph langsmith langchain-openai입니다. 환경변수는 OPENAI_API_KEY, LANGSMITH_API_KEY, LANGSMITH_TRACING=true를 가정합니다.

import os
from langchain_openai import ChatOpenAI
from langchain_core.tools import tool
from langgraph.prebuilt import create_react_agent

@tool
def get_weather(city: str) -> str:
    """Return today's weather in the given city (mocked)."""
    table = {"seoul": "맑음, 18도", "tokyo": "흐림, 16도"}
    return table.get(city.lower(), "데이터 없음")

@tool
def add(a: int, b: int) -> int:
    """Return a + b."""
    return a + b

agent = create_react_agent(
    model=ChatOpenAI(model="gpt-4o-mini", temperature=0),
    tools=[get_weather, add],
    prompt="너는 도시 날씨를 알려주고 간단한 산술을 돕는 비서다. 모르면 모른다고 답한다.",
)

if __name__ == "__main__":
    out = agent.invoke({"messages": [
        ("user", "서울 날씨와 7 + 35의 결과를 함께 알려줘."),
    ]})
    print(out["messages"][-1].content)

이 22줄짜리 파일이 풀어 주는 것은 다음과 같습니다.

  • 모델은 도구 호출 결정을 스스로 합니다. ReAct 패턴이 prebuilt 안에 들어 있어서 따로 구현할 필요가 없습니다.
  • LANGSMITH_TRACING=true만 켜져 있으면, 위 한 번의 호출이 LangSmith에 한 개의 trace로 나타납니다. 도구 호출 두 번, 모델 호출 세 번이 트리 구조로 보입니다.
  • create_react_agent가 반환한 agentRunnable이라 invoke/stream/ainvoke가 그대로 동작합니다.

같은 코드에 checkpointer=MemorySaver()만 더하면 thread별 대화 메모리도 얻습니다. 처음부터 직접 그래프를 그릴 필요가 없다는 점, 그리고 그 그래프가 필요해지는 순간 prebuilt를 풀어 자기 그래프를 짜기 쉽다는 점이 LangGraph의 진입 곡선을 부드럽게 만듭니다.

8. 함께 자주 등장하는 단어들

이 셋을 학습하다 보면 같은 자리에서 자주 마주치는 단어가 있습니다. 한 곳에 모아 짧게 짚습니다.

8.1 Tool, Function Calling

Function Calling은 OpenAI가 2023년에 도입한 모델 기능입니다. 모델이 자연어가 아니라 "어떤 함수를 어떤 인자로 호출할지" 구조화된 JSON으로 반환하게 만드는 방식입니다. LangChain의 @tool 데코레이터로 만든 함수가 모델에 바인딩되면, 내부적으로 이 기능 호출이 일어납니다. LangGraph의 ToolNode는 이 호출을 받아 실제 파이썬 함수로 디스패치하는 역할을 합니다.

8.2 ReAct

ReAct(Reason + Act)는 Yao 등이 2022년에 제안한 프롬프팅 패턴으로, 모델이 "생각 → 행동(도구 호출) → 관찰 → 다시 생각"을 한 메시지 안에서 반복하게 만드는 형태입니다. create_react_agent는 이 패턴을 그래프로 굳혀 둔 prebuilt입니다.

8.3 MCP (Model Context Protocol)

MCP는 Anthropic이 주도해 표준화 중인 프로토콜로, 도구·리소스·프롬프트를 "서버" 형태로 노출하고 LLM 클라이언트가 이를 일관된 방식으로 사용하게 합니다. LangChain·LangGraph도 MCP 서버를 도구로 끌어와 쓸 수 있는 통합을 제공합니다. 한 번 만든 도구 서버를 여러 모델·여러 프레임워크에서 재사용하려는 발상입니다.

8.4 LangFlow, LangServe

  • LangFlow — LangChain/LangGraph 위에 올린 시각적 워크플로 에디터. 코드 없이 노드를 끌어다 붙여 프로토타입을 만들 때 유용합니다.
  • LangServe — LangChain Runnable을 FastAPI 엔드포인트로 노출시켜 주는 라이브러리입니다. 다만 v0.3 시점에 점차 LangGraph 기반 배포 모델로 흡수되는 추세입니다. 새 프로젝트라면 LangGraph의 deployment 가이드를 먼저 봅니다.

8.5 LangChain vs 다른 에이전트 프레임워크

같은 자리에서 자주 비교되는 다른 프레임워크에는 LlamaIndex(인덱싱·RAG 중심), Haystack(파이프라인·DocStore 중심), 그리고 JVM 진영의 Spring AI·Koog가 있습니다. 어느 쪽이 절대 우위라는 결론은 없습니다. 다만 "사이클·상태·human-in-the-loop를 정식 모델로 다루는가"의 기준에서 보면, LangGraph는 현 시점에 가장 정돈된 선택지 중 하나입니다.

9. 왜 지금 이 셋이 핫한가

세 도구가 동시에 주목받는 이유는 한 가지로 모입니다. 에이전트의 신뢰성·관측·평가가 동시에 시장의 요구가 됐기 때문입니다.

  • 모델 그 자체의 성능은 더 이상 단독 변수가 아닙니다. 같은 모델이라도 도구·프롬프트·메모리 설계가 결과를 갈라놓습니다. → 부품 표준화가 필요합니다(LangChain).
  • 데모를 넘어 운영에 올라간 에이전트는 사이클·상태·재개를 요구합니다. → 그래프 오케스트레이션이 필요합니다(LangGraph).
  • 운영에 올라간 에이전트는 "왜 이렇게 답했는지"가 매번 재현 가능해야 합니다. → trace와 evaluation이 필요합니다(LangSmith).

같은 회사가 이 세 축을 모두 가지면서, "한 번 배운 추상이 개발·운영·평가에서 모두 통한다"는 일관성을 만들어 낸 점이 시장이 이 생태계를 빠르게 받아들인 이유입니다. 어떤 도구가 영원히 1등이라는 보장은 없습니다. 다만 첫 에이전트를 만들려는 입장에서는 "공식 문서가 가장 두껍고, 실패 사례가 가장 많이 공개돼 있고, 통합이 가장 풍부한" 선택지를 먼저 학습하는 편이 시간 대비 효율이 좋습니다. 그 자리에 현재로서는 LangChain·LangGraph·LangSmith의 조합이 놓여 있습니다.

10. 마무리

세 도구의 역할을 한 줄씩으로 압축하면 다음과 같습니다.

  • LangChain은 LLM과 그 주변 부품의 표준 인터페이스를 제공합니다.
  • LangGraph는 그 부품을 사이클·상태·사람 개입이 있는 그래프로 묶어 줍니다.
  • LangSmith는 위 둘이(또는 다른 프레임워크가) 만든 실행을 추적·평가·모니터링합니다.

첫 에이전트를 만들 때는 create_react_agent 한 줄에서 시작해도 충분합니다. 분기와 반복이 늘면 StateGraph를 손으로 그립니다. 운영을 시작하는 날, LangSmith의 환경변수 두 줄을 추가합니다. 이 세 단계가 거의 모든 입문자가 거치는 동선이고, 각 단계마다 다음 단계로 넘어갈 신호가 코드 안에서 자연스럽게 보입니다.

참고자료

More from this blog

Spring @Transactional 동작 원리 — 프록시, 트랜잭션 매니저, 전파와 롤백의 진실

메서드 위에 @Transactional 한 줄을 붙이면 Spring은 그 호출을 가로채 트랜잭션을 시작하고, 예외가 나면 롤백하고, 정상 종료되면 커밋합니다. 이 글은 그 한 줄 뒤에서 일어나는 일을 코드 흐름과 함께 풀어냅니다. 프록시가 어떻게 메서드를 가로채는지, TransactionInterceptor가 어떤 순서로 매니저를 호출하는지, 전파 속성과

May 14, 202612 min read

끄적끄적 테크 블로그

47 posts

물류 회사에 다니고 있는 개발자 블로그입니다. 개발을 너무 좋아해서 정신없이 작업하다가 중간에 끄적거리며 내용들을 몇개 적어봅니다 ㅎㅎ