Messages and Content API Reference

Purpose and Scope

Messages are the unit of conversation state that LangChain chat models consume and produce. In the core Python package, a message combines the visible payload sent to or returned from a model with metadata that helps agents, tracing systems, tools, and provider adapters preserve what happened. This reference focuses on the API surface around base message objects, multimodal content blocks, tool result messages, and provider-specific block translators. It is intended for developers implementing model integrations, agent middleware, trace rendering, or application code that needs reliable message inspection rather than one-off prompt strings.

Sources: libs/core/langchain_core/messages/base.py, libs/core/langchain_core/messages/content.py, libs/core/langchain_core/messages/tool.py

LangChain standardizes messages because model providers expose similar concepts through incompatible schemas. A chat turn may contain text, an image, a file, reasoning content, a tool call, or a tool result, and the project needs those pieces to move through runnables, agents, and observability without being rewritten for every provider. The core design is deliberately provider-agnostic: application code can operate on BaseMessage and ContentBlock structures, while provider adapters translate to OpenAI, Anthropic, or another API at the boundary.

Sources: libs/core/langchain_core/messages/content.py, libs/core/langchain_core/messages/block_translators/openai.py, libs/core/langchain_core/messages/block_translators/anthropic.py

Relevant Source Files

  • libs/core/langchain_core/messages/base.py - Defines the base message contract, text access compatibility behavior, shared metadata fields, and reasoning extraction from provider-specific additional kwargs.
  • libs/core/langchain_core/messages/content.py - Defines the standard multimodal content block vocabulary, rationale for provider-neutral blocks, extension strategy through extras, and factory usage patterns.
  • libs/core/langchain_core/messages/utils.py - Provides the message utility surface used by the package for working with message collections and conversions.
  • libs/core/langchain_core/messages/tool.py - Defines tool output messages, tool output coercion behavior, tool-call correlation, artifacts, status, and tool message validation.
  • libs/core/langchain_core/messages/block_translators/openai.py - Converts standard content blocks into OpenAI Chat Completions or Responses API payload shapes and validates unsupported cases.
  • libs/core/langchain_core/messages/block_translators/anthropic.py - Converts Anthropic-format blocks into LangChain v1 content blocks while preserving unknown provider fields in extras.

Base Message Contract

BaseMessage is the abstract message class for chat model input and output. Its central field is content, typed as either a string or an ordered list containing strings and dictionaries. It also carries additional_kwargs for provider payloads that do not fit the standard fields, response_metadata for response headers, logprobs, token counts, or model names, and a string type that must uniquely identify the message kind for serialization. Concrete message classes such as human, AI, and system messages build on this contract.

Sources: libs/core/langchain_core/messages/base.py

A practical implication is that application code should not assume a message is only plain text. The same message abstraction can represent a simple human utterance, a multimodal model input, or a provider response with encoded tool calls in additional_kwargs. The base module also includes _extract_reasoning_from_additional_kwargs, which recognizes string reasoning_content values used by providers such as Ollama, DeepSeek, xAI, and Groq and converts them into a standard reasoning content block. This keeps reasoning display and downstream processing consistent when providers expose reasoning in different places.

Sources: libs/core/langchain_core/messages/base.py, libs/core/langchain_core/messages/content.py

The base module also preserves a compatibility path for accessing text. TextAccessor is a string-like object that supports modern property access with message.text and legacy callable access with message.text(). Calling it as a method emits a deprecation warning because LangChain Core 1.0 moved toward property access and plans removal of the method form in 2.0. Code that needs long-term compatibility should read text as a property and treat non-text content through content blocks instead of flattening it too early.

Sources: libs/core/langchain_core/messages/base.py

Content Blocks and Multimodal Payloads

The content.py module defines standard multimodal content blocks for LLM input and output. Its rationale is that provider APIs disagree on the shape of text, images, files, and related payloads, but LangChain components need a common internal representation. A message can therefore carry a list of content blocks, allowing text, images, files, or other blocks to appear in a single ordered sequence. Provider adapters are responsible for converting those blocks into the schema expected by a particular model API.

Sources: libs/core/langchain_core/messages/content.py

The standard block model is intentionally extensible. Provider-specific fields inside a standard block belong in the extras field, so integrations can keep metadata without breaking the shared shape. Data that has not yet been mapped to a standard block can be represented as a NonStandardContentBlock, preserving original provider data while still letting the rest of the system type-check and validate known blocks. The module documentation also notes a future direction around PEP 728, where provider-specific fields may become first-class extra typed-dict items rather than always living inside extras.

Sources: libs/core/langchain_core/messages/content.py

For construction, the content module supports both direct typed-dict creation and factory helpers. The documented examples show TextContentBlock and ImageContentBlock used in a multimodal AI message, and equivalent factory calls such as create_text_block and create_image_block. Factories reduce repetitive boilerplate because callers do not need to manually specify the type field, and they can provide conveniences such as automatic ID generation when no ID is supplied. Prefer factories when building blocks dynamically in application or integration code.

Sources: libs/core/langchain_core/messages/content.py

Tool Message API

Tool results are represented by ToolMessage, which extends BaseMessage and ToolOutputMixin. A tool message carries the result of executing a tool back to the model, usually through the content field. Its most important required field is tool_call_id, which correlates the result with the model's tool call request. That correlation is essential when a model requests multiple tools in parallel because each returned result must be matched to the correct request before the next model call.

Sources: libs/core/langchain_core/messages/tool.py

ToolMessage separates model-visible content from application-visible artifacts. The artifact field can store the full tool output when only a subset should be sent back to the model. For example, a tool can place concise stdout in content while keeping stderr, image data, or structured artifacts outside the model context. The status field is either success or error, allowing agent runtimes and UIs to distinguish successful tool execution from failed calls without parsing natural language text.

Sources: libs/core/langchain_core/messages/tool.py

The tool module also defines validation and coercion behavior. ToolOutputMixin marks objects that tools can return directly; if a custom tool output is not such an object, the tool runtime may coerce it to a string and wrap it in a ToolMessage. The ToolMessage.coerce_args model validator accepts string content and list content, converts tuple content into a list, and attempts to coerce other values to strings. If coercion fails, it raises a value error explaining that tool message content must be a string or a list of strings and dictionaries.

Sources: libs/core/langchain_core/messages/tool.py

Provider Block Translators

OpenAI translation lives in block_translators/openai.py. convert_to_openai_image_block converts a standard image block with a URL into OpenAI's image_url form, or converts base64 image data into a data URL when mime_type is present. If the image source is unsupported, or required base64 metadata is missing, it raises ValueError. convert_to_openai_data_block handles standard data blocks for either the chat/completions or responses API, including the different input_image shape required by the Responses API.

Sources: libs/core/langchain_core/messages/block_translators/openai.py

The OpenAI data translator also handles file blocks and backward-compatible shapes. For base64 files it constructs a file_data data URL using the block MIME type and chooses a filename from filename, extras.filename, or backward-compatible metadata. If no filename can be inferred, it uses a placeholder default for compatibility. This behavior matters for integration authors because it shows where validation is strict, such as unsupported sources, and where the adapter preserves compatibility for older LangChain content block conventions.

Sources: libs/core/langchain_core/messages/block_translators/openai.py

Anthropic translation lives in block_translators/anthropic.py. The helper _convert_to_v1_from_anthropic_input processes a list of content blocks and attempts to unpack blocks previously treated as non_standard into v1 LangChain blocks when they match Anthropic shapes. For Anthropic document sources, it maps base64 sources to file blocks with base64 data and MIME type, URL sources to file URL blocks, file sources to file ID blocks, and text sources to plain text blocks. Blocks that cannot be converted remain non-standard.

Sources: libs/core/langchain_core/messages/block_translators/anthropic.py

The Anthropic module uses _populate_extras to preserve unknown provider fields. When a converted block is a standard block, fields that are not part of the known conversion set are copied into extras; non-standard blocks are left unchanged. This is the same extension philosophy used by the content block model itself: normalize what LangChain understands, but avoid discarding provider-specific detail that may be needed for tracing, replay, or a future adapter revision.

Sources: libs/core/langchain_core/messages/block_translators/anthropic.py, libs/core/langchain_core/messages/content.py

Compact API Reference

API surfaceSourceContract
BaseMessagelibs/core/langchain_core/messages/base.pyAbstract chat message with content, additional_kwargs, response_metadata, and unique string type.
TextAccessorlibs/core/langchain_core/messages/base.pyString-like compatibility wrapper; prefer message.text over deprecated message.text().
_extract_reasoning_from_additional_kwargs(message)libs/core/langchain_core/messages/base.pyReturns a standard reasoning block when additional_kwargs['reasoning_content'] is a string.
Content block typed dictslibs/core/langchain_core/messages/content.pyProvider-neutral multimodal block vocabulary for text, images, files, reasoning, and non-standard data.
create_text_block, create_image_blocklibs/core/langchain_core/messages/content.pyFactory helpers documented for constructing standard blocks without manually setting type.
ToolOutputMixinlibs/core/langchain_core/messages/tool.pyMarker for tool outputs that can be returned directly instead of coerced into a string tool message.
ToolMessagelibs/core/langchain_core/messages/tool.pyTool result message with tool_call_id, artifact, status, and validated content coercion.
convert_to_openai_image_block(block)libs/core/langchain_core/messages/block_translators/openai.pyConverts standard image blocks to OpenAI image payloads; supports URL and base64 sources.
convert_to_openai_data_block(block, api='chat/completions')libs/core/langchain_core/messages/block_translators/openai.pyConverts standard data blocks for OpenAI Chat Completions or Responses API payloads.
_convert_to_v1_from_anthropic_input(content)libs/core/langchain_core/messages/block_translators/anthropic.pyConverts recognizable Anthropic blocks into v1 LangChain content blocks, leaving unknown data non-standard.

Usage Guidance and Next Steps

When writing application code, keep messages structured for as long as possible. Use BaseMessage fields for metadata, use content blocks for multimodal payloads, and avoid collapsing a message to text unless the next component truly only accepts text. When writing tools, return ToolMessage content that is safe for the model and put larger raw outputs in artifact. When writing provider integrations, translate only at the provider boundary and preserve unknown fields in extras or non-standard blocks so tracing and debugging can still reconstruct the original exchange.

Sources: libs/core/langchain_core/messages/base.py, libs/core/langchain_core/messages/content.py, libs/core/langchain_core/messages/tool.py, libs/core/langchain_core/messages/block_translators/openai.py, libs/core/langchain_core/messages/block_translators/anthropic.py

Related pages: messages, language-models-api-reference, tools, structured-output, callbacks-observability.