Skip to main content
For frameworks that have already completed the LLM call and only need to record it, use weave.log_turn and weave.log_conversation. All spans are created and ended immediately without keeping any context managers open. Data logged this way can be historical. No live conversation is needed. Set conversation_id to any stable string that uniquely identifies the conversation. Turns that share the same conversation_id are grouped as a single conversation in the Agents view. If you’re building your own agent loop, use the real-time instrumentation APIs described in Trace your agents instead.

Log a turn

To record a single completed turn after it happens, use weave.log_turn. It accepts a fully-formed turn, including all LLM and tool spans.
weave.init("[YOUR-TEAM]/[YOUR-PROJECT]")

from weave.conversation import LLM, Message, Tool, Usage

llm_span = LLM(
    model="gpt-4o",
    provider_name="openai",
    input_messages=[Message(role="user", content="What is the weather?")],
    output_messages=[Message(role="assistant", content="Let me check.")],
    usage=Usage(input_tokens=100, output_tokens=20),
)

tool_span = Tool(
    name="get_weather",
    arguments='{"city": "Tokyo"}',
    result='"24°C, sunny"',
)

llm_span2 = LLM(
    model="gpt-4o",
    provider_name="openai",
    input_messages=[Message(role="user", content="What is the weather?")],
    output_messages=[Message(role="assistant", content="It is 24°C and sunny.")],
    usage=Usage(input_tokens=150, output_tokens=30),
)

# Log a turn with all its spans.
weave.log_turn(
    conversation_id="my-conversation-abc",
    agent_name="weather-bot",
    messages=[
        Message(role="user", content="What is the weather in Tokyo?"),
        Message(role="assistant", content="It is 24°C and sunny in Tokyo."),
    ],
    spans=[llm_span, tool_span, llm_span2],
)
log_turn returns a LogResult containing the trace IDs of the emitted spans. An optional model parameter on log_turn sets the model on the turn’s own span, not on the child LLM spans. Each LLM span carries its own model independently. If a turn uses multiple models, set model on log_turn to whichever you consider the primary model for that turn.

Log a conversation

To bulk-import a complete, multi-turn conversation at once, use weave.log_conversation. The turns parameter accepts a list of Turn objects, each constructed the same way as the previous log_turn example.
weave.log_conversation(
    conversation_id="my-conversation-abc",
    agent_name="weather-bot",
    turns=[turn_1, turn_2],
)