# Open Responses for the Open Source Community

**URL:** <https://community.openai.com/t/open-responses-for-the-open-source-community/1371770>\
**Category:** Announcements\
**Tags:** open-source, responses-api\
**Created:** [January 15, 2026, 8:11pm UTC](https://community.openai.com/t/open-responses-for-the-open-source-community/1371770 "2026-01-15T20:11:25Z")\
**Posts on this page:** 9\
**Page:** 1

<div class="post-metadata">

**Author:** ![VeitB](https://sea2.discourse-cdn.com/openai1/user_avatar/community.openai.com/veitb/32/712987_2.png) [@VeitB](https://community.openai.com/u/VeitB)\
**Post date:** [January 15, 2026, 8:11pm UTC](https://community.openai.com/t/open-responses-for-the-open-source-community/1371770/1 "2026-01-15T20:11:25Z")

</div>

[Open Responses](https://www.openresponses.org/) is an open-source specification and ecosystem inspired by the OpenAI Responses API. It is designed to make it easier to build multi-provider, interoperable LLM interfaces. The project defines a shared schema, client libraries, and tooling that let you call language models, stream outputs, and build agentic workflows without being locked into a single provider.

 ![G-uUID4W0AArXm6](https://us1.discourse-cdn.com/openai1/original/4X/e/6/c/e6cadb1edaaedb658fa797c33393eb3ca6755724.jpeg)

**Motivation and overview**

Most modern LLM platforms now rely on similar building blocks such as messages, tool calls, function calling, and multimodal inputs. The problem is that each provider represents these concepts slightly differently. Open Responses standardizes these primitives so you can focus on building instead of translating APIs.

**With Open Responses, you get:**

- One spec, many providers: Define inputs and outputs once and run them across OpenAI, Anthropic, Gemini, or local models.

- Composable agentic workflows: A unified approach to streaming, tool invocation, and message orchestration.

- Simpler evaluation and routing: Compare providers, route requests, and log results using a shared schema.

- A blueprint for providers: Labs and model vendors can expose their APIs in a common, well-defined format with minimal effort.

Discover more and read the spec here:

> **[Open Responses](https://www.openresponses.org/)**
>
> Open Responses documentation overview.

Find the code on GitHub:

> **[GitHub - openresponses/openresponses](https://github.com/openresponses/openresponses)**
>
> Contribute to openresponses/openresponses development by creating an account on GitHub.

---

<div class="post-metadata">

**Author:** ![VeitB](https://sea2.discourse-cdn.com/openai1/user_avatar/community.openai.com/veitb/32/712987_2.png) [@VeitB](https://community.openai.com/u/VeitB)\
**Post date:** [January 15, 2026, 8:12pm UTC](https://community.openai.com/t/open-responses-for-the-open-source-community/1371770/2 "2026-01-15T20:12:17Z")

</div>



---

<div class="post-metadata">

**Author:** ![jochenschultz](https://sea2.discourse-cdn.com/openai1/user_avatar/community.openai.com/jochenschultz/32/491030_2.png) [@jochenschultz](https://community.openai.com/u/jochenschultz)\
**Post date:** [January 16, 2026, 1:19am UTC](https://community.openai.com/t/open-responses-for-the-open-source-community/1371770/3 "2026-01-16T01:19:47Z")

</div>

That will help some people for sure. I’ll dive into it later.

---

<div class="post-metadata">

**Author:** ![\_j](https://sea2.discourse-cdn.com/openai1/user_avatar/community.openai.com/_j/32/766292_2.png) [@\_j](https://community.openai.com/u/_j)\
**Post date:** [January 16, 2026, 2:40pm UTC](https://community.openai.com/t/open-responses-for-the-open-source-community/1371770/4 "2026-01-16T14:40:09Z")

</div>

You will note if exploring the “Open” version, there is little variation between the API. In fact, it imposes, embraces, and extends OpenAI’s limitations to ensure an uncompetitive surface if employed. Will you find `logit_bias` and others? No. Any “truncation” other than OpenAI’s unbudgeted version? No. I guess they don’t want you to obtain “minimal” reasoning in this enum, and assume someone is going to have a “flex” tier. Only having functions makes this endpoint shape as an internal iterator as its API “selling point” redundant.  
Give Chat Completions a thinking whitespace 'heartbeat" before JSON for keepalive, or Google’s reasoning extension, and you are done.

The only “benefit” is in this spec, they actually spell out blocking image and file inputs to anything other than a user or tool role in this version, so you can’t deliver useful services either; a limit over OpenAI’s own `yaml`. Knocked down the streaming to 23 event types.

I’m just going to leave this here for your perusal, which is directly from parsing the existing OpenAPI specification. The _response_ of responses is massively more lines when documented, so if the “reference” can make a web version of that, more power.

POST [https://api.openai.com/v1/responses](https://api.openai.com/v1/responses)

Parameters (JSON body):  
model: string # required [model ID]  
input: string | array # required [text, or a list of input items]  
├▸ (string): string # [equivalent to a single user text message]  
└▸ (array): InputItem`[]` # [multi-part / multi-turn inputs]  
├▸ message (EasyInputMessage): object  
│ ├▸ type: “message” # required  
│ ├▸ role: “user” | “assistant” | “system” | “developer” # required  
│ └▸ content: string | InputContent`[]` # required  
│ ├▸ (string): string # [plain text]  
│ └▸ (array): InputContent`[]`  
│ ├▸ input\_text: object  
│ │ ├▸ type: “input\_text” # required  
│ │ └▸ text: string # required  
│ ├▸ input\_image: object  
│ │ ├▸ type: “input\_image” # required  
│ │ ├▸ detail: “low” | “high” | “auto” # required (default: auto)  
│ │ ├▸ image\_url: string | null # optional [URL or data URL (base64)]  
│ │ └▸ file\_id: string | null # optional [uploaded file ID]  
│ └▸ input\_file: object  
│ ├▸ type: “input\_file” # required  
│ ├▸ file\_id: string | null # optional  
│ ├▸ filename: string # optional  
│ ├▸ file\_url: string # optional  
│ └▸ file\_data: string # optional [file content (encoded)]  
├▸ item (Item): object # [conversation-state items; may include prior outputs/tool results]  
│ └▸ type: (discriminator; varies) # required  
│ ├▸ message (InputMessage): object  
│ │ ├▸ type: “message” # required  
│ │ ├▸ role: “user” | “system” | “developer” # required  
│ │ └▸ content: InputContent`[]` # required (same InputContent shapes as above)  
│ ├▸ item\_reference: object  
│ │ ├▸ type: “item\_reference” | null # optional (default: item\_reference)  
│ │ └▸ id: string # required  
│ ├▸ (output shapes that can appear in conversation state)  
│ │ ├▸ output\_message (OutputMessage): object  
│ │ │ ├▸ type: “message” # required  
│ │ │ ├▸ role: “assistant” # required  
│ │ │ ├▸ id: string # required  
│ │ │ ├▸ status: “in\_progress” | “completed” | “incomplete” # required  
│ │ │ └▸ content: OutputMessageContent`[]`  
│ │ │ ├▸ output\_text: object  
│ │ │ │ ├▸ type: “output\_text” # required  
│ │ │ │ ├▸ text: string # required  
│ │ │ │ ├▸ annotations: Annotation`[]` # required  
│ │ │ │ └▸ logprobs: LogProb`[]` # optional (only if included via include)  
│ │ │ └▸ refusal: object  
│ │ │ ├▸ type: “refusal” # required  
│ │ │ └▸ refusal: string # required  
│ │ ├▸ file\_search\_call (FileSearchToolCall): object  
│ │ │ ├▸ type: “file\_search\_call” # required  
│ │ │ ├▸ id: string # required  
│ │ │ ├▸ status: “in\_progress” | “searching” | “completed” | “incomplete” | “failed” # required  
│ │ │ ├▸ queries: string`[]` # required  
│ │ │ └▸ results: array | null # optional (only if included via include)  
│ │ ├▸ web\_search\_call (WebSearchToolCall): object  
│ │ │ ├▸ type: “web\_search\_call” # required  
│ │ │ ├▸ id: string # required  
│ │ │ ├▸ status: “in\_progress” | “searching” | “completed” | “failed” # required  
│ │ │ └▸ action: object # required [search/open\_page/find]  
│ │ ├▸ computer\_call (ComputerToolCall): object  
│ │ │ ├▸ type: “computer\_call” # required  
│ │ │ ├▸ id: string # required  
│ │ │ ├▸ call\_id: string # required  
│ │ │ ├▸ action: object # required [click/double\_click/drag/keypress/move/screenshot/scroll/type/wait]  
│ │ │ ├▸ pending\_safety\_checks: ComputerCallSafetyCheckParam`[]` # required  
│ │ │ └▸ status: “in\_progress” | “completed” | “incomplete” # required  
│ │ ├▸ function\_call (FunctionToolCall): object  
│ │ │ ├▸ type: “function\_call” # required  
│ │ │ ├▸ id: string # required  
│ │ │ ├▸ call\_id: string # required  
│ │ │ ├▸ name: string # required  
│ │ │ ├▸ arguments: string # required [JSON string]  
│ │ │ └▸ status: “in\_progress” | “completed” | “incomplete” # required  
│ │ ├▸ function\_call\_output: object  
│ │ │ ├▸ type: “function\_call\_output” # required  
│ │ │ ├▸ call\_id: string # required  
│ │ │ ├▸ output: string | array # required [JSON string, or content list]  
│ │ │ └▸ status: “in\_progress” | “completed” | “incomplete” | null # optional  
│ │ ├▸ reasoning (ReasoningItem): object  
│ │ │ ├▸ type: “reasoning” # required  
│ │ │ ├▸ id: string # required  
│ │ │ ├▸ encrypted\_content: string | null # optional (only if included via include)  
│ │ │ ├▸ summary: Summary`[]` # required  
│ │ │ ├▸ content: ReasoningTextContent`[]` # optional  
│ │ │ └▸ status: “in\_progress” | “completed” | “incomplete” # required  
│ │ ├▸ image\_generation\_call (ImageGenToolCall): object  
│ │ │ ├▸ type: “image\_generation\_call” # required  
│ │ │ ├▸ id: string # required  
│ │ │ ├▸ status: “in\_progress” | “completed” | “generating” | “failed” # required  
│ │ │ └▸ result: string | null # required [base64 image]  
│ │ └▸ code\_interpreter\_call (CodeInterpreterToolCall): object  
│ │ ├▸ type: “code\_interpreter\_call” # required  
│ │ ├▸ id: string # required  
│ │ ├▸ status: “in\_progress” | “completed” | “incomplete” | “interpreting” | “failed” # required  
│ │ ├▸ container\_id: string # required  
│ │ ├▸ code: string | null # required  
│ │ └▸ outputs: array | null # optional (only if included via include)  
└▸ item\_reference: object  
├▸ type: “item\_reference” | null # optional (default: item\_reference)  
└▸ id: string # required [ID of an item to reference]

instructions: string | null # optional [system/developer message inserted into context]  
previous\_response\_id: string | null # optional [multi-turn linkage; cannot be used with conversation]  
conversation: string | object | null # optional [conversation container]  
├▸ (string): string # [conversation ID]  
└▸ (object): object  
└▸ id: string # required

metadata: object | null # optional [up to 16 string→string pairs]  
temperature: number | null # optional (default: 1) [0..2]  
top\_p: number | null # optional (default: 1) [0..1]  
top\_logprobs: integer | null # optional [0..20]

user: string # optional (deprecated)  
safety\_identifier: string # optional  
prompt\_cache\_key: string # optional

service\_tier: “auto” | “default” | “flex” | “scale” | “priority” | null # optional (default: auto)  
prompt\_cache\_retention: “in-memory” | “24h” | null # optional

reasoning: object | null # optional [reasoning configuration]  
├▸ effort: “none” | “minimal” | “low” | “medium” | “high” | “xhigh” | null # optional (default: medium)  
├▸ summary: “auto” | “concise” | “detailed” | null # optional  
└▸ generate\_summary: “auto” | “concise” | “detailed” | null # optional (deprecated)

background: boolean | null # optional (default: false)  
max\_output\_tokens: integer | null # optional  
max\_tool\_calls: integer | null # optional

text: object # optional [text output configuration]  
├▸ format: object # optional (default: {“type”:“text”})  
│ ├▸ text: object  
│ │ └▸ type: “text” # required  
│ ├▸ json\_schema: object # [Structured Outputs]  
│ │ ├▸ type: “json\_schema” # required  
│ │ ├▸ name: string # required  
│ │ ├▸ schema: object # required [JSON Schema]  
│ │ ├▸ description: string # optional  
│ │ └▸ strict: boolean | null # optional (default: false)  
│ └▸ json\_object: object # [older JSON mode]  
│ └▸ type: “json\_object” # required  
└▸ verbosity: “low” | “medium” | “high” | null # optional (default: medium)

tools: Tool`[]` # optional [tools the model may call]  
├▸ function: object  
│ ├▸ type: “function” # required  
│ ├▸ name: string # required  
│ ├▸ description: string | null # optional  
│ ├▸ parameters: object | null # required [JSON Schema]  
│ └▸ strict: boolean | null # required  
├▸ file\_search: object  
│ ├▸ type: “file\_search” # required  
│ ├▸ vector\_store\_ids: string`[]` # required  
│ ├▸ max\_num\_results: integer # optional [1..50]  
│ ├▸ ranking\_options: object # optional  
│ │ ├▸ ranker: “auto” | “default-2024-11-15” # optional  
│ │ ├▸ score\_threshold: number # optional [0..1]  
│ │ └▸ hybrid\_search: object # optional  
│ │ ├▸ embedding\_weight: number # required  
│ │ └▸ text\_weight: number # required  
│ └▸ filters: object | null # optional  
│ ├▸ ComparisonFilter: object  
│ │ ├▸ type: “eq” | “ne” | “gt” | “gte” | “lt” | “lte” # required  
│ │ ├▸ key: string # required  
│ │ └▸ value: string | number | boolean | array # required  
│ └▸ CompoundFilter: object  
│ ├▸ type: “and” | “or” # required  
│ └▸ filters: array # required  
├▸ computer\_use\_preview: object  
│ ├▸ type: “computer\_use\_preview” # required  
│ ├▸ environment: “windows” | “mac” | “linux” | “ubuntu” | “browser” # required  
│ ├▸ display\_width: integer # required  
│ └▸ display\_height: integer # required  
├▸ web\_search: object  
│ ├▸ type: “web\_search” | “web\_search\_2025\_08\_26” # required  
│ ├▸ filters: object | null # optional  
│ │ └▸ allowed\_domains: string`[]` | null # optional  
│ ├▸ user\_location: object | null # optional  
│ │ ├▸ type: “approximate” # required (default: approximate)  
│ │ ├▸ country: string | null # optional  
│ │ ├▸ region: string | null # optional  
│ │ ├▸ city: string | null # optional  
│ │ └▸ timezone: string | null # optional  
│ └▸ search\_context\_size: “low” | “medium” | “high” # required (default: medium)  
├▸ mcp: object  
│ ├▸ type: “mcp” # required  
│ ├▸ server\_label: string # required  
│ ├▸ server\_url: string # optional  
│ ├▸ connector\_id: enum # optional  
│ ├▸ authorization: string # optional  
│ ├▸ server\_description: string # optional  
│ ├▸ headers: object | null # optional  
│ ├▸ allowed\_tools: string`[]` | object | null # optional  
│ │ ├▸ (array): string`[]` # [allowed tool names]  
│ │ └▸ (filter object): object  
│ │ ├▸ tool\_names: string`[]` # optional  
│ │ └▸ read\_only: boolean # optional  
│ └▸ require\_approval: “always” | “never” | object | null # optional (default: always)  
├▸ code\_interpreter: object  
│ ├▸ type: “code\_interpreter” # required  
│ └▸ container: string | object # required  
│ ├▸ (string): string # [container ID]  
│ └▸ (auto object): object  
│ ├▸ type: “auto” # required  
│ ├▸ file\_ids: string`[]` # optional  
│ └▸ memory\_limit: “1g” | “4g” | “16g” | “64g” | null # optional  
├▸ image\_generation: object  
│ ├▸ type: “image\_generation” # required  
│ ├▸ model: string # optional (default: gpt-image-1)  
│ ├▸ quality: “low” | “medium” | “high” | “auto” # optional (default: auto)  
│ ├▸ size: “1024x1024” | “1024x1536” | “1536x1024” | “auto” # optional (default: auto)  
│ ├▸ output\_format: “png” | “webp” | “jpeg” # optional (default: png)  
│ ├▸ output\_compression: integer # optional (default: 100) [0..100]  
│ ├▸ moderation: “auto” | “low” # optional (default: auto)  
│ ├▸ background: “transparent” | “opaque” | “auto” # optional (default: auto)  
│ ├▸ input\_fidelity: “high” | “low” | null # optional  
│ ├▸ input\_image\_mask: object # optional  
│ │ ├▸ image\_url: string # optional  
│ │ └▸ file\_id: string # optional  
│ └▸ partial\_images: integer # optional (default: 0) [0..3]  
├▸ local\_shell: object  
│ └▸ type: “local\_shell” # required  
├▸ shell: object  
│ └▸ type: “shell” # required  
├▸ custom: object  
│ ├▸ type: “custom” # required  
│ ├▸ name: string # required  
│ ├▸ description: string # optional  
│ └▸ format: object # optional  
│ ├▸ text: object  
│ │ └▸ type: “text” # required  
│ └▸ grammar: object  
│ ├▸ type: “grammar” # required  
│ ├▸ syntax: “lark” | “regex” # required  
│ └▸ definition: string # required  
├▸ web\_search\_preview: object  
│ ├▸ type: “web\_search\_preview” | “web\_search\_preview\_2025\_03\_11” # required  
│ ├▸ user\_location: object | null # optional  
│ │ ├▸ type: “approximate” # required (default: approximate)  
│ │ ├▸ country: string | null # optional  
│ │ ├▸ region: string | null # optional  
│ │ ├▸ city: string | null # optional  
│ │ └▸ timezone: string | null # optional  
│ └▸ search\_context\_size: “low” | “medium” | “high” # required (default: medium)  
└▸ apply\_patch: object  
└▸ type: “apply\_patch” # required

tool\_choice: “none” | “auto” | “required” | object # optional  
├▸ (mode string): “none” | “auto” | “required”  
└▸ (object): object  
├▸ allowed\_tools: object  
│ ├▸ type: “allowed\_tools” # required  
│ ├▸ mode: “auto” | “required” # required  
│ └▸ tools: array # required  
├▸ hosted\_tool: object  
│ └▸ type: “file\_search” | “web\_search\_preview” | “web\_search\_preview\_2025\_03\_11” | “computer\_use\_preview” | “image\_generation” | “code\_interpreter” # required  
├▸ function: object  
│ ├▸ type: “function” # required  
│ └▸ name: string # required  
├▸ mcp: object  
│ ├▸ type: “mcp” # required  
│ ├▸ server\_label: string # required  
│ └▸ name: string | null # required  
├▸ custom: object  
│ ├▸ type: “custom” # required  
│ └▸ name: string # required  
├▸ apply\_patch: object  
│ └▸ type: “apply\_patch” # required  
└▸ shell: object  
└▸ type: “shell” # required

prompt: object | null # optional [prompt template reference]  
├▸ id: string # required  
├▸ version: string | null # optional  
└▸ variables: object | null # optional [map of substitutions]  
└▸ \<var\_name\>: string | InputContent # optional  
├▸ (string): string  
├▸ input\_text: object  
│ ├▸ type: “input\_text” # required  
│ └▸ text: string # required  
├▸ input\_image: object  
│ ├▸ type: “input\_image” # required  
│ ├▸ detail: “low” | “high” | “auto” # required (default: auto)  
│ ├▸ image\_url: string | null # optional  
│ └▸ file\_id: string | null # optional  
└▸ input\_file: object  
├▸ type: “input\_file” # required  
├▸ file\_id: string | null # optional  
├▸ filename: string # optional  
├▸ file\_url: string # optional  
└▸ file\_data: string # optional

truncation: “auto” | “disabled” | null # optional (default: disabled)  
include: string`[]` | null # optional  
├▸ “file\_search\_call.results”  
├▸ “web\_search\_call.results”  
├▸ “web\_search\_call.action.sources”  
├▸ “message.input\_image.image\_url”  
├▸ “computer\_call\_output.output.image\_url”  
├▸ “code\_interpreter\_call.outputs”  
├▸ “reasoning.encrypted\_content”  
└▸ “message.output\_text.logprobs”

parallel\_tool\_calls: boolean | null # optional (default: true)  
store: boolean | null # optional (default: true)

stream: boolean | null # optional (default: false)  
stream\_options: object | null # optional  
└▸ include\_obfuscation: boolean # optional

* * *

Unvalidated, captured from field descriptions:

- previous\_response\_id cannot be used together with conversation.
- stream\_options should only be set when stream=true.

Known model IDs in schema (model is typed as “string”, but the schema enumerates these IDs, and when built, the SDK blocks anything else):

- gpt-5.2, gpt-5.2-2025-12-11, gpt-5.2-chat-latest, gpt-5.2-pro, gpt-5.2-pro-2025-12-11
- gpt-5.1, gpt-5.1-2025-11-13, gpt-5.1-codex, gpt-5.1-mini, gpt-5.1-chat-latest
- gpt-5, gpt-5-mini, gpt-5-nano, gpt-5-2025-08-07, gpt-5-mini-2025-08-07, gpt-5-nano-2025-08-07, gpt-5-chat-latest
- gpt-4.1, gpt-4.1-mini, gpt-4.1-nano, gpt-4.1-2025-04-14, gpt-4.1-mini-2025-04-14, gpt-4.1-nano-2025-04-14
- o4-mini, o4-mini-2025-04-16
- o3, o3-2025-04-16, o3-mini, o3-mini-2025-01-31
- o1, o1-2024-12-17, o1-preview, o1-preview-2024-09-12, o1-mini, o1-mini-2024-09-12
- gpt-4o, gpt-4o-2024-11-20, gpt-4o-2024-08-06, gpt-4o-2024-05-13
- gpt-4o-audio-preview, gpt-4o-audio-preview-2024-10-01, gpt-4o-audio-preview-2024-12-17, gpt-4o-audio-preview-2025-06-03
- gpt-4o-mini-audio-preview, gpt-4o-mini-audio-preview-2024-12-17
- gpt-4o-search-preview, gpt-4o-mini-search-preview, gpt-4o-search-preview-2025-03-11, gpt-4o-mini-search-preview-2025-03-11
- chatgpt-4o-latest, codex-mini-latest, gpt-4o-mini, gpt-4o-mini-2024-07-18
- gpt-4-turbo, gpt-4-turbo-2024-04-09, gpt-4-0125-preview, gpt-4-turbo-preview, gpt-4-1106-preview, gpt-4-vision-preview
- gpt-4, gpt-4-0314, gpt-4-0613, gpt-4-32k, gpt-4-32k-0314, gpt-4-32k-0613
- gpt-3.5-turbo, gpt-3.5-turbo-16k, gpt-3.5-turbo-0301, gpt-3.5-turbo-0613, gpt-3.5-turbo-1106, gpt-3.5-turbo-0125, gpt-3.5-turbo-16k-0613
- (Responses-only enum in schema): o1-pro, o1-pro-2025-03-19, o3-pro, o3-pro-2025-06-10, o3-deep-research, o3-deep-research-2025-06-26, o4-mini-deep-research, o4-mini-deep-research-2025-06-26, computer-use-preview, computer-use-preview-2025-03-11, gpt-5-codex, gpt-5-pro, gpt-5-pro-2025-10-06, gpt-5.1-codex-max

---

<div class="post-metadata">

**Author:** ![davidfstr](https://sea2.discourse-cdn.com/openai1/user_avatar/community.openai.com/davidfstr/32/612576_2.png) [@davidfstr](https://community.openai.com/u/davidfstr)\
**Post date:** [January 20, 2026, 5:55pm UTC](https://community.openai.com/t/open-responses-for-the-open-source-community/1371770/5 "2026-01-20T17:55:45Z")

</div>

How is Open Responses different from existing multi-provider libraries like LangChain?

---

<div class="post-metadata">

**Author:** ![tariqsheikh05g](https://avatars.discourse-cdn.com/v4/letter/t/7c8e57/32.png) [@tariqsheikh05g](https://community.openai.com/u/tariqsheikh05g)\
**Post date:** [January 22, 2026, 4:13pm UTC](https://community.openai.com/t/open-responses-for-the-open-source-community/1371770/6 "2026-01-22T16:13:20Z")

</div>

How is open Responses different from existing multi-previder libraries like LangChain?

---

<div class="post-metadata">

**Author:** ![Mahwachi\_Abir](https://sea2.discourse-cdn.com/openai1/user_avatar/community.openai.com/mahwachi_abir/32/511974_2.png) [@Mahwachi\_Abir](https://community.openai.com/u/Mahwachi_Abir)\
**Post date:** [January 22, 2026, 4:17pm UTC](https://community.openai.com/t/open-responses-for-the-open-source-community/1371770/7 "2026-01-22T16:17:58Z")

</div>

Hello 👋

Open Responses differs from LangChain in how it handles model providers. LangChain offers a unified interface to interact with multiple models, but you still need to write the logic for routing and formatting yourself. Open Responses focuses on simplifying responses through a direct API interface, automatically managing coordination between models. This makes it easier to integrate into open-source applications without much complexity​🤍

---

<div class="post-metadata">

**Author:** ![\_j](https://sea2.discourse-cdn.com/openai1/user_avatar/community.openai.com/_j/32/766292_2.png) [@\_j](https://community.openai.com/u/_j)\
**Post date:** [January 22, 2026, 4:34pm UTC](https://community.openai.com/t/open-responses-for-the-open-source-community/1371770/8 "2026-01-22T16:34:16Z")

</div>

> [@tariqsheikh05g](#):
>
> How is open Responses different from existing multi-previder libraries like LangChain?

Better answer, not an AI-powered guess:

Open Responses is an API **specification** for directly consuming an endpoint resource of an AI model provider. It closely mirrors OpenAI’s platform implementation.

Langchain is a multi-turn **agent builder** library, that uses and consumes APIs, and has multi-provider shims for endpoint API interfaces such as Chat Completions, Responses, Google genai, and other proprietary providers.

---

<div class="post-metadata">

**Author:** ![pschell](https://sea2.discourse-cdn.com/openai1/user_avatar/community.openai.com/pschell/32/736058_2.png) [@pschell](https://community.openai.com/u/pschell)\
**Post date:** [March 25, 2026, 2:22pm UTC](https://community.openai.com/t/open-responses-for-the-open-source-community/1371770/9 "2026-03-25T14:22:54Z")

</div>

Awesome! Will definitely try that out!
