Acceso a la API
VoiceBooker ofrece acceso programático a la API para integrar otras aplicaciones y automatizar flujos, como la recuperación de uso, el despliegue de bots y la integración con pipelines de CI/CD.
URL base
https://voicebooker.de/app/api/v1Autenticación
Envíe un token API en cada solicitud mediante este header:
X-API-TOKEN: <su-token-api>El token determina el contexto de empresa de la solicitud. Manténgalo seguro.
Exportar un bot
GET /exportBots/{botId} exporta un bot de la empresa asociada al token API. Use pretty=true para obtener HJSON legible.
curl --get 'https://voicebooker.de/app/api/v1/exportBots/<bot-id>' \
--header 'X-API-TOKEN: <su-token-api>' \
--data-urlencode 'pretty=true'Ejemplo de respuesta:
{
"name": "Asistente de recepción",
"id": "kqrmxaveli",
"stages": [
{
"name": "Welcome",
"id": "mavotirenu",
"linkId": "qeluzanopi",
"template": false,
"prompt": "Saluda a la persona que llama.",
"tools": [],
"functions": [],
"settings": {},
"stageConfig": [],
"x": 0,
"y": 0,
"order": 0,
"instanceSettings": {}
}
],
"settings": {},
"wizard": {}
}Importar un bot
POST /importBots importa una definición de bot en la empresa asociada al token. Envíe la definición exportada en contents. Para HJSON, filename debe terminar en .hjson. overwriteBotStages, overwriteTemplates y replaceBotStages son parámetros booleanos opcionales.
curl --request POST \
--url https://voicebooker.de/app/api/v1/importBots \
--header 'X-API-TOKEN: <su-token-api>' \
--header 'Content-Type: application/json' \
--data '{"filename":"bot.json","contents":{"name":"Asistente de recepción","settings":{},"stages":[]},"overwriteBotStages":false,"overwriteTemplates":false,"replaceBotStages":false}'Ejemplo de respuesta:
{
"id": "vexorimaku",
"name": "Asistente de recepción",
"settings": {},
"invisible": false
}Realizar llamadas salientes
Para realizar una llamada saliente, envíe una solicitud POST a:
https://voicebooker.de/app/api/v1/makeCallContent-Type: application/json
X-API-TOKEN: <su-token-api>Ejemplo de solicitud:
{
"dest": "+49-351-123456789",
"botId": "kqrmxaveli",
"sipAccountId": "lupenakori",
"ringTimeout": 25,
"startTimeout": 10,
"state": {
"customerId": "zpjwletodo"
}
}| Parámetro | Descripción |
|---|---|
dest | Número de destino en formato E.164. |
botId | Bot utilizado para la llamada. |
sipAccountId | Cuenta SIP utilizada; su número aparece al destinatario. |
ringTimeout | Segundos que sonará antes de cancelar si nadie responde. Por defecto: 30 segundos. |
startTimeout | Segundos que espera el bot antes de empezar a hablar. |
state | Datos para webhooks o llamadas API durante la llamada, como un ID de cliente. |
La API devuelve un callId:
{
"callId": "xavurimeto"
}Gestionar pruebas de bots
Las pruebas de bots comparan un bot de origen/llamada con un bot de destino/respuesta. Las solicitudes con clave API están limitadas a la empresa asociada al token; ambos bots deben pertenecer a esa empresa.
| Método | Endpoint | Función |
|---|---|---|
GET | /bot_test_setups | Listar pruebas. |
POST | /bot_test_setups | Crear una prueba. |
PUT | /bot_test_setups/{id} | Actualizar una prueba. |
DELETE | /bot_test_setups/{id} | Eliminar una prueba. |
La respuesta pública contiene únicamente id, name, settings, srcBotId y destBotId. settings puede incluir
convInitBot, maxConvTurns, asCall, startTimeout y stateUpdate. Al actualizar, los campos omitidos se conservan.
Obtener una grabación de llamada
GET /getRecording/{id} devuelve la grabación MP3 de una sesión de llamada. Usa como id el ID de sesión de llamada devuelto por /usage. La grabación debe haberse activado para la llamada.
La respuesta se transmite como audio/mpeg y puede guardarse directamente como archivo .mp3:
curl --request GET \
--url https://voicebooker.de/app/api/v1/getRecording/<id-de-sesion> \
--header 'X-API-TOKEN: <su-token-api>' \
--output grabacion.mp3El endpoint devuelve 404 Not Found cuando la sesión o su grabación no están disponibles para el token de API. Devuelve 401 Unauthorized si el token de API falta o no es válido.
Listar sesiones de llamadas y obtener transcripciones
Usa GET /call_sessions para listar sesiones de llamadas o GET /conversations para listar sesiones con transcripciones visibles. Al listar sesiones, ambos endpoints requieren las fechas start y end y devuelven 30 elementos por página de forma predeterminada. El campo call indica si la sesión es una llamada telefónica.
curl --get https://voicebooker.de/app/api/v1/call_sessions \
--header 'X-API-TOKEN: <tu-token-api>' \
--data-urlencode 'start=2026-01-01' \
--data-urlencode 'end=2026-01-31' \
--data-urlencode 'page=1'Usa el ID de sesión de una lista para obtener la transcripción (cs.id en /call_sessions e id en /conversations):
curl --get 'https://voicebooker.de/app/api/v1/conversations/<id-de-sesion>' \
--header 'X-API-TOKEN: <tu-token-api>' \
--data-urlencode 'trace=true' \
--data-urlencode 'page=1'Con trace=true, cada página incluye hasta 1.000 turnos cronológicos de la transcripción, además de los prompts, el estado, la pila y los detalles fsCalls de funciones/webhooks disponibles. Omite trace para obtener la página estándar de 30 elementos. Usa page para obtener páginas posteriores. El acceso se limita a las empresas disponibles para el token.
Si ya conoces el ID de contexto telefónico, GET /conversations?contextUId=<id-de-contexto> devuelve una transcripción compacta.
Obtener uso
GET /usage devuelve sesiones telefónicas y de chat de la empresa autenticada y de sus empresas asociadas disponibles.
Sin businessId se incluyen todas las empresas disponibles. Use businessId para seleccionar una empresa y start y end para filtrar por la fecha de creación de la sesión.
curl --get https://voicebooker.de/app/api/v1/usage \
--header 'X-API-TOKEN: <su-token-api>' \
--data-urlencode 'businessId=zpjwletodo' \
--data-urlencode 'start=2026-01-01T00:00:00Z' \
--data-urlencode 'end=2026-02-01T00:00:00Z'start y end son inclusivos. Use fechas ISO 8601 que puedan analizarse. Una empresa fuera del alcance del token produce 403 Forbidden.
Ejemplo de respuesta:
[
{
"id": "xavurimeto", "businessId": "zpjwletodo", "botId": "kqrmxaveli",
"isCall": true, "direction": "inbound", "phoneNumberCaller": "+341701234567",
"phoneNumberCallee": "+34911234567", "duration": 184, "costs": 0.46,
"start": "2026-01-15T10:30:00.000Z"
}
]Listar empresas asociadas
Para integraciones de socios y revendedores, GET /partnerClients devuelve las empresas visibles conectadas con la empresa autenticada. Sus IDs pueden utilizarse como filtro businessId en el endpoint de uso.
curl --request GET \
--url https://voicebooker.de/app/api/v1/partnerClients \
--header 'X-API-TOKEN: <su-token-api>'Ejemplo de respuesta:
[
{
"id": "zpjwletodo",
"name": "Empresa de ejemplo",
"city": "Madrid",
"country": "ES"
}
]Gestionar archivos de la base de conocimientos y archivos multimedia
Las claves API pueden listar, cargar y eliminar archivos de la empresa asociada al token.
Listar archivos de la base de conocimientos
GET /knowledgeBase devuelve id, name, fileSize y tokens.
curl --request GET \
--url https://voicebooker.de/app/api/v1/knowledgeBase \
--header 'X-API-TOKEN: <su-token-api>'Cargar un archivo de la base de conocimientos
POST /knowledgeBase acepta una carga multipart con los campos file y name.
curl --request POST \
--url https://voicebooker.de/app/api/v1/knowledgeBase \
--header 'X-API-TOKEN: <su-token-api>' \
--form 'name=manual.pdf' \
--form 'file=@manual.pdf'Eliminar un archivo de la base de conocimientos
curl --request DELETE \
--url https://voicebooker.de/app/api/v1/knowledgeBase/<id-archivo> \
--header 'X-API-TOKEN: <su-token-api>'Listar y cargar archivos multimedia
GET /mediaFiles devuelve id, name y fileSize. POST /mediaFiles utiliza los mismos campos multipart.
curl --request GET \
--url https://voicebooker.de/app/api/v1/mediaFiles \
--header 'X-API-TOKEN: <su-token-api>'
curl --request POST \
--url https://voicebooker.de/app/api/v1/mediaFiles \
--header 'X-API-TOKEN: <su-token-api>' \
--form 'name=musica.mp3' \
--form 'file=@musica.mp3'Eliminar un archivo multimedia
curl --request DELETE \
--url https://voicebooker.de/app/api/v1/mediaFiles/<id-archivo> \
--header 'X-API-TOKEN: <su-token-api>'Especificación OpenAPI
openapi: 3.1.0
info:
title: VoiceBooker Partner API
version: 1.0.0
description: API para consultar empresas asociadas y datos de uso.
servers: [{url: https://voicebooker.de/app/api/v1}]
paths:
/exportBots/{botId}:
get:
summary: Exportar un bot
operationId: exportBot
security: [{apiToken: []}]
parameters:
- {name: botId, in: path, required: true, schema: {type: string}}
- {name: pretty, in: query, schema: {type: boolean, default: false}}
responses:
'200': {description: Definición del bot exportado., content: {application/json: {schema: {type: object, properties: {id: {type: string}, name: {type: string}, stages: {type: array, items: {type: object}}, settings: {type: object}, wizard: {type: object}}}}}}
'401': {$ref: '#/components/responses/Unauthorized'}
'403': {description: El bot no pertenece a la empresa del token.}
/importBots:
post:
summary: Importar un bot
operationId: importBot
security: [{apiToken: []}]
requestBody:
required: true
content:
application/json:
schema:
type: object
required: [contents]
properties:
filename: {type: string}
contents: {oneOf: [{type: object}, {type: string}]}
overwriteBotStages: {type: boolean, default: false}
overwriteTemplates: {type: boolean, default: false}
replaceBotStages: {type: boolean, default: false}
responses:
'200': {description: Bot importado., content: {application/json: {schema: {type: object, properties: {id: {type: string}, name: {type: string}}}}}}
'401': {$ref: '#/components/responses/Unauthorized'}
/makeCall:
post:
summary: Realizar una llamada saliente
operationId: makeOutboundCall
security: [{apiToken: []}]
requestBody:
required: true
content:
application/json:
schema:
type: object
required: [dest, botId, sipAccountId]
properties:
dest: {type: string}
botId: {type: string}
sipAccountId: {type: string}
ringTimeout: {type: integer, default: 30}
startTimeout: {type: integer, default: 0}
state: {type: object, additionalProperties: true}
responses:
'200': {description: Llamada saliente iniciada., content: {application/json: {schema: {type: object, properties: {callId: {type: string}}}}}}
'401': {$ref: '#/components/responses/Unauthorized'}
/getRecording/{id}:
get:
summary: Obtener una grabación de llamada
operationId: getCallRecording
security: [{apiToken: []}]
parameters:
- {name: id, in: path, required: true, schema: {type: string}, description: ID de la sesión de llamada.}
responses:
'200': {description: Grabación de llamada., content: {audio/mpeg: {schema: {type: string, format: binary}}}}
'401': {$ref: '#/components/responses/Unauthorized'}
'404': {description: La sesión o grabación no está disponible para este token de API.}
/call_sessions:
get:
tags: [Partner access]
operationId: listCallSessions
summary: Listar sesiones de llamadas
description: Devuelve sesiones de llamadas de las empresas disponibles para el token API.
security: [{apiToken: []}]
parameters:
- {name: start, in: query, required: true, description: Fecha de inicio inclusiva (AAAA-MM-DD)., schema: {type: string, format: date}}
- {name: end, in: query, required: true, description: Fecha de fin inclusiva (AAAA-MM-DD)., schema: {type: string, format: date}}
- {name: page, in: query, required: false, schema: {type: integer, minimum: 1, default: 1}}
responses:
'200': {description: Página de sesiones de llamadas (30 elementos por página)., content: {application/json: {schema: {type: array, items: {type: object, additionalProperties: true}}}}}
'401': {$ref: '#/components/responses/Unauthorized'}
/conversations:
get:
tags: [Partner access]
operationId: listTranscribedSessions
summary: Listar sesiones con transcripción
description: Devuelve sesiones visibles con transcripciones de las empresas disponibles para el token API. El parámetro contextUId permite obtener en su lugar una transcripción compacta para un contexto telefónico conocido.
security: [{apiToken: []}]
parameters:
- {name: start, in: query, required: false, description: Obligatorio al listar sesiones., schema: {type: string, format: date}}
- {name: end, in: query, required: false, description: Obligatorio al listar sesiones., schema: {type: string, format: date}}
- {name: page, in: query, required: false, schema: {type: integer, minimum: 1, default: 1}}
- {name: contextUId, in: query, required: false, description: Devuelve una transcripción compacta de este contexto telefónico en lugar de una lista de sesiones., schema: {type: string}}
responses:
'200': {description: Página de sesiones con transcripción o transcripción compacta del contexto., content: {application/json: {schema: {type: array, items: {type: object, additionalProperties: true}}}}}
'401': {$ref: '#/components/responses/Unauthorized'}
/conversations/{id}:
get:
tags: [Partner access]
operationId: getCallTranscript
summary: Obtener una transcripción de llamada
description: Devuelve turnos cronológicos de la transcripción y datos asociados a la llamada para una sesión disponible. trace=true incluye hasta 1.000 turnos por página, con prompts, estado, pila y llamadas a funciones/webhooks disponibles.
security: [{apiToken: []}]
parameters:
- {name: id, in: path, required: true, description: ID de sesión obtenido de una lista., schema: {type: string}}
- {name: page, in: query, required: false, schema: {type: integer, minimum: 1, default: 1}}
- {name: trace, in: query, required: false, description: Establécelo en true para obtener el seguimiento detallado; omítelo para la respuesta estándar., schema: {type: boolean}}
responses:
'200': {description: Turnos de la transcripción de la página solicitada., content: {application/json: {schema: {type: array, items: {type: object, additionalProperties: true}}}}}
'401': {$ref: '#/components/responses/Unauthorized'}
/usage:
get:
summary: Obtener uso
operationId: listUsage
security: [{apiToken: []}]
parameters:
- {name: businessId, in: query, schema: {type: string}, description: Empresa que se desea consultar.}
- {name: start, in: query, schema: {type: string, format: date-time}, description: Inicio inclusivo.}
- {name: end, in: query, schema: {type: string, format: date-time}, description: Fin inclusivo.}
responses:
'200': {description: Registros de uso., content: {application/json: {schema: {type: array, items: {$ref: '#/components/schemas/UsageRecord'}}}}}
'401': {$ref: '#/components/responses/Unauthorized'}
'403': {description: La empresa no está disponible para este token.}
/partnerClients:
get:
summary: Listar empresas asociadas
operationId: listPartnerClients
security: [{apiToken: []}]
responses:
'200': {description: Lista de empresas., content: {application/json: {schema: {type: array, items: {$ref: '#/components/schemas/PartnerBusiness'}}}}}
'401': {$ref: '#/components/responses/Unauthorized'}
/knowledgeBase:
get:
operationId: listKnowledgeBaseFiles
security: [{apiToken: []}]
responses:
'200': {description: Archivos de la base de conocimientos., content: {application/json: {schema: {type: array, items: {$ref: '#/components/schemas/KnowledgeBaseFile'}}}}}
'401': {$ref: '#/components/responses/Unauthorized'}
post:
operationId: uploadKnowledgeBaseFile
security: [{apiToken: []}]
requestBody: {required: true, content: {multipart/form-data: {schema: {type: object, required: [file, name], properties: {file: {type: string, format: binary}, name: {type: string}}}}}}
responses:
'200': {description: ID del archivo cargado., content: {application/json: {schema: {type: object, properties: {id: {type: string}}}}}}
'401': {$ref: '#/components/responses/Unauthorized'}
/knowledgeBase/{fileId}:
delete:
operationId: deleteKnowledgeBaseFile
security: [{apiToken: []}]
parameters: [{name: fileId, in: path, required: true, schema: {type: string}}]
responses: {'200': {description: Archivo eliminado.}, '401': {$ref: '#/components/responses/Unauthorized'}, '403': {description: Archivo fuera del alcance del token.}}
/mediaFiles:
get:
operationId: listMediaFiles
security: [{apiToken: []}]
responses: {'200': {description: Archivos multimedia., content: {application/json: {schema: {type: array, items: {$ref: '#/components/schemas/MediaFile'}}}}}, '401': {$ref: '#/components/responses/Unauthorized'}}
post:
operationId: uploadMediaFile
security: [{apiToken: []}]
requestBody: {required: true, content: {multipart/form-data: {schema: {type: object, required: [file, name], properties: {file: {type: string, format: binary}, name: {type: string}}}}}}
responses: {'200': {description: ID del archivo cargado., content: {application/json: {schema: {type: object, properties: {id: {type: string}}}}}}, '401': {$ref: '#/components/responses/Unauthorized'}}
/mediaFiles/{fileId}:
delete:
operationId: deleteMediaFile
security: [{apiToken: []}]
parameters: [{name: fileId, in: path, required: true, schema: {type: string}}]
responses: {'200': {description: Archivo eliminado.}, '401': {$ref: '#/components/responses/Unauthorized'}, '403': {description: Archivo fuera del alcance del token.}}
/bot_test_setups:
get:
operationId: listBotTests
security: [{apiToken: []}]
responses: {'200': {description: Pruebas de bots., content: {application/json: {schema: {type: array, items: {$ref: '#/components/schemas/BotTestSetup'}}}}}, '401': {$ref: '#/components/responses/Unauthorized'}}
post:
operationId: createBotTest
security: [{apiToken: []}]
requestBody: {required: true, content: {application/json: {schema: {$ref: '#/components/schemas/BotTestSetupInput'}}}}
responses: {'200': {description: Prueba creada., content: {application/json: {schema: {$ref: '#/components/schemas/BotTestSetup'}}}}, '401': {$ref: '#/components/responses/Unauthorized'}, '403': {description: Bot fuera del alcance o bots idénticos.}}
/bot_test_setups/{id}:
put:
operationId: updateBotTest
security: [{apiToken: []}]
parameters: [{name: id, in: path, required: true, schema: {type: string}}]
requestBody: {required: true, content: {application/json: {schema: {$ref: '#/components/schemas/BotTestSetupUpdate'}}}}
responses: {'200': {description: Prueba actualizada., content: {application/json: {schema: {$ref: '#/components/schemas/BotTestSetup'}}}}, '401': {$ref: '#/components/responses/Unauthorized'}, '403': {description: Bot fuera del alcance o bots idénticos.}, '404': {description: Prueba no encontrada.}}
delete:
operationId: deleteBotTest
security: [{apiToken: []}]
parameters: [{name: id, in: path, required: true, schema: {type: string}}]
responses: {'200': {description: Prueba eliminada.}, '401': {$ref: '#/components/responses/Unauthorized'}, '404': {description: Prueba no encontrada.}}
components:
securitySchemes:
apiToken: {type: apiKey, in: header, name: X-API-TOKEN}
schemas:
PartnerBusiness: {type: object, properties: {id: {type: string}, name: {type: string}}}
UsageRecord:
type: object
properties:
id: {type: string}
businessId: {type: string}
botId: {type: string, nullable: true}
isCall: {type: boolean}
direction: {type: string, enum: [inbound, outbound]}
phoneNumberCaller: {type: string, nullable: true}
phoneNumberCallee: {type: string, nullable: true}
duration: {type: integer}
costs: {type: number}
start: {type: string, format: date-time}
KnowledgeBaseFile:
type: object
properties: {id: {type: string}, name: {type: string}, fileSize: {type: integer}, tokens: {type: integer}}
MediaFile:
type: object
properties: {id: {type: string}, name: {type: string}, fileSize: {type: integer}}
BotTestSetup:
type: object
properties: {id: {type: string}, name: {type: string}, settings: {type: object, additionalProperties: true}, srcBotId: {type: string}, destBotId: {type: string}}
BotTestSetupInput:
type: object
required: [name, srcBotId, destBotId]
properties: {name: {type: string}, settings: {type: object, additionalProperties: true}, srcBotId: {type: string}, destBotId: {type: string}}
BotTestSetupUpdate:
type: object
properties: {name: {type: string}, settings: {type: object, additionalProperties: true}, srcBotId: {type: string}, destBotId: {type: string}}
responses:
Unauthorized: {description: El token falta o no es válido.}Errores HTTP
401 Unauthorized: falta el token API o no es válido.403 Forbidden: la empresa solicitada no está disponible para el token.