> ## Documentation Index
> Fetch the complete documentation index at: https://docs.doconda.com/llms.txt
> Use this file to discover all available pages before exploring further.

# Cómo devolver un archivo Word desde la API de OpenAI

> Pasa doconda.tools() como funciones en Chat Completions: el modelo llama a create_document y devuelve el enlace al .docx y su PDF.

La API de OpenAI devuelve texto, no archivos. Instala `doconda` (o `@doconda/sdk`), pasa `doconda.tools()` como
`tools` en `chat.completions.create` y, cuando el modelo llame a `create_document`, ejecútala con `run()`: recibes el
Word (`.docx`) y su PDF con sus enlaces de descarga.

## Pasos

1. Guarda tu key de OpenAI en `OPENAI_API_KEY` y la de Doconda (panel → **API keys**) en `DOCONDA_API_KEY`.
2. Convierte cada herramienta al formato `function` de OpenAI.
3. Ejecuta el bucle: mientras el mensaje traiga `tool_calls`, ejecutas cada herramienta y le devuelves el resultado.

<CodeGroup>
  ```python Python theme={"theme":{"light":"github-light","dark":"github-dark-dimmed"}}
  # pip install openai doconda
  import json

  from doconda import Doconda
  from openai import OpenAI

  openai = OpenAI()
  tools = Doconda().tools()
  specs = [{"type": "function", "function": {"name": t.name, "description": t.description, "parameters": t.input_schema}} for t in tools]
  messages = [{"role": "user", "content": "Redacta un memo en Word para el equipo: la oficina cierra el viernes"}]

  while True:
      message = openai.chat.completions.create(model="gpt-5", messages=messages, tools=specs).choices[0].message
      messages.append(message)
      if not message.tool_calls:
          break
      for call in message.tool_calls:
          out = next(t for t in tools if t.name == call.function.name).run(json.loads(call.function.arguments))
          messages.append({"role": "tool", "tool_call_id": call.id, "content": json.dumps(out)})

  print(message.content)
  ```

  ```ts TypeScript theme={"theme":{"light":"github-light","dark":"github-dark-dimmed"}}
  // npm install openai @doconda/sdk
  import OpenAI from "openai"
  import { Doconda } from "@doconda/sdk"

  const openai = new OpenAI()
  const docondaTools = new Doconda().tools()
  const tools = docondaTools.map((t) => ({ type: "function" as const, function: { name: t.name, description: t.description, parameters: t.inputSchema } }))
  const messages: any[] = [{ role: "user", content: "Redacta un memo en Word para el equipo: la oficina cierra el viernes" }]

  while (true) {
    const res = await openai.chat.completions.create({ model: "gpt-5", messages, tools })
    const message = res.choices[0]?.message
    if (!message) break
    messages.push(message)
    if (!message.tool_calls?.length) break
    for (const call of message.tool_calls) {
      if (call.type !== "function") continue
      const result = await docondaTools.find((t) => t.name === call.function.name)!.run(JSON.parse(call.function.arguments))
      messages.push({ role: "tool", tool_call_id: call.id, content: JSON.stringify(result) })
    }
  }
  ```
</CodeGroup>

¿Ya tienes el texto del modelo y no quieres un agente? Llama directamente a
`doconda.documents.create(format="docx", content={"markdown": texto})` con su respuesta.

## Qué devuelve

```json theme={"theme":{"light":"github-light","dark":"github-dark-dimmed"}}
{
  "id": "doc_01JAB3…",
  "format": "docx",
  "status": "ready",
  "links": { "docx": "https://…", "pdf": "https://…" },
  "links_note": "Links expire in 5 minutes: call get_document for fresh ones."
}
```

* Un Word editable: el aspecto va en sus estilos (Normal, Título 1…), así lo que se añada después sigue el mismo diseño.
* `status`: `ready`, `ready_with_warnings`, `needs_review` o `failed` (no se cobra).
* Los enlaces caducan a los 5 minutos; el agente pide otros con `get_document`.

## Preguntas frecuentes

<AccordionGroup>
  <Accordion title="¿Puedo descargar el archivo en mi servidor en vez de pasar el enlace?">
    Sí. Con el `id` que devuelve la herramienta, `doconda.documents.download(id, "docx")` te da los bytes.
  </Accordion>

  <Accordion title="¿Y si lo quiero en PDF?">
    Pídelo en el mensaje: `create_document` acepta `format: "pdf"` (solo el PDF). Un Word siempre llega con su PDF.
  </Accordion>

  <Accordion title="¿Funciona con Azure OpenAI?">
    Sí, el mismo código con `AzureOpenAI()`. Ver [Azure OpenAI](/agents/azure).
  </Accordion>

  <Accordion title="¿Cuánto cuesta?">
    Pagas por documento entregado; crear con tu propio Markdown cuesta menos que desde una frase. Ver
    [precios](/guides/account#precios).
  </Accordion>
</AccordionGroup>

## Sigue leyendo

* [OpenAI](/agents/openai): la guía completa, también con OpenAI Codex.
* [Quickstart](/quickstart).


This documentation is built and hosted on [Mintlify](https://mintlify.com), a developer documentation platform.