Aller au contenu

Textos API Documentation

This document describes the Textos REST API. All endpoints are prefixed with /api/v1 unless otherwise noted.

Authentication

The API uses JWT (JSON Web Token) for authentication. Include the access token in the Authorization header:

Authorization: Bearer <access_token>

Obtaining Tokens

Login

POST /api/v1/auth/login

Request:

{
  "email": "user@example.com",
  "password": "your-password"
}

Response:

{
  "user": { ... },
  "access_token": "eyJ...",
  "refresh_token": "eyJ..."
}

Refresh Token

POST /api/v1/auth/refresh
Authorization: Bearer <refresh_token>

Response:

{
  "access_token": "eyJ..."
}

Using API Keys

For programmatic access, you can use API keys instead of JWT tokens. Include the API key in the X-API-Key header:

X-API-Key: your-api-key

Authentication Endpoints

Register with Invitation

POST /api/v1/auth/register

Register a new user using an invitation token.

Request:

{
  "token": "invitation-token",
  "password": "secure-password",
  "name": "John Doe",
  "language": "fr"
}

Get Current User

GET /api/v1/auth/me

Returns the authenticated user's profile.

Update Current User

PATCH /api/v1/auth/me

Request:

{
  "name": "New Name",
  "language": "en",
  "password": "new-password"
}

Forgot Password

POST /api/v1/auth/forgot-password

Request:

{
  "email": "user@example.com"
}

Reset Password

POST /api/v1/auth/reset-password

Request:

{
  "token": "reset-token",
  "password": "new-password"
}

OAuth Providers

GET /api/v1/auth/oauth/providers

Returns list of enabled OAuth providers for the current domain.


SMS & Conversations

Send SMS

POST /api/v1/sms/send

Request:

{
  "to": "+15141234567",
  "body": "Hello from Textos!",
  "team_id": "optional-team-id"
}

Response:

{
  "message": {
    "id": "...",
    "direction": "outbound",
    "status": "sent",
    "body": "Hello from Textos!",
    "from_number": "+15149876543",
    "to_number": "+15141234567",
    "created_at": "2024-01-15T10:30:00Z"
  },
  "conversation": { ... }
}

List Conversations

GET /api/v1/conversations

Query Parameters: | Parameter | Type | Description | |-----------|------|-------------| | team_id | string | Filter by team | | status | string | open or closed | | skip | integer | Pagination offset | | limit | integer | Results per page (max 100) |

Get Conversation

GET /api/v1/conversations/{conversation_id}

Returns conversation details with messages.

Query Parameters: | Parameter | Type | Description | |-----------|------|-------------| | skip | integer | Message pagination offset | | limit | integer | Messages per page (max 100) |

Close Conversation

POST /api/v1/conversations/{conversation_id}/close

Reopen Conversation

POST /api/v1/conversations/{conversation_id}/reopen

List Messages

GET /api/v1/messages

Query Parameters: | Parameter | Type | Description | |-----------|------|-------------| | team_id | string | Filter by team | | direction | string | inbound or outbound | | status | string | Message status | | skip | integer | Pagination offset | | limit | integer | Results per page |


Teams

List Teams

GET /api/v1/teams

Returns teams accessible to the current user.

Get Team

GET /api/v1/teams/{team_id}

Create Team

POST /api/v1/teams

Request:

{
  "name": "Support Team",
  "phone_number": "+15149876543"
}

Update Team

PUT /api/v1/teams/{team_id}

Request:

{
  "name": "Updated Team Name",
  "phone_number": "+15149876543",
  "business_hours": [
    { "day": 0, "start": "09:00", "end": "17:00" },
    { "day": 1, "start": "09:00", "end": "17:00" }
  ],
  "outside_hours_behavior": "queue",
  "auto_reply_message": "We're currently closed...",
  "welcome_message": "Thank you for contacting us!",
  "timezone": "America/Montreal"
}

Delete Team

DELETE /api/v1/teams/{team_id}

Update Business Hours

PUT /api/v1/teams/{team_id}/hours

Request:

{
  "business_hours": [
    { "day": 0, "start": "09:00", "end": "17:00" },
    { "day": 1, "start": "09:00", "end": "17:00" },
    { "day": 2, "start": "09:00", "end": "17:00" },
    { "day": 3, "start": "09:00", "end": "17:00" },
    { "day": 4, "start": "09:00", "end": "17:00" }
  ],
  "outside_hours_behavior": "queue",
  "auto_reply_message": "We're currently closed. We'll respond during business hours.",
  "timezone": "America/Montreal"
}

Notes: - Day 0 = Monday, 6 = Sunday - outside_hours_behavior: queue or reject - auto_reply_message: optional, sent when SMS received outside hours (for both behaviors)

Team Members

List Members

GET /api/v1/teams/{team_id}/members

Add Member

POST /api/v1/teams/{team_id}/members

Request:

{
  "user_id": "user-id-to-add"
}

Remove Member

DELETE /api/v1/teams/{team_id}/members/{user_id}

Team Phone Numbers

GET /api/v1/teams/{team_id}/phone-numbers

Regenerate Webhook

POST /api/v1/teams/{team_id}/webhook/regenerate

Organizations

My Organizations

GET /api/v1/organizations/my

Returns all organizations the current user belongs to.

Switch Organization

POST /api/v1/organizations/switch

Request:

{
  "organization_id": "org-id"
}

Current Organization

GET /api/v1/organizations/current

Update Current Organization

PUT /api/v1/organizations/current

Request:

{
  "name": "New Organization Name"
}

Organization Members

GET /api/v1/organizations/current/members

Invitations

List Invitations

GET /api/v1/invitations

Create Invitation

POST /api/v1/invitations

Request:

{
  "email": "newuser@example.com",
  "role": "agent",
  "team_id": "optional-team-id"
}

Response includes token for the invitation URL.

Delete Invitation

DELETE /api/v1/invitations/{invitation_id}

Verify Invitation (Public)

GET /api/v1/invitations/verify/{token}

API Keys

List API Keys

GET /api/v1/api-keys

Create API Key

POST /api/v1/api-keys

Request:

{
  "name": "My Integration Key",
  "team_id": "optional-team-id"
}

Response includes key field - save it as it's only shown once!

Get API Key

GET /api/v1/api-keys/{key_id}

Revoke API Key

DELETE /api/v1/api-keys/{key_id}
or
POST /api/v1/api-keys/{key_id}/revoke


Metrics

Overview

GET /api/v1/metrics/overview

Query Parameters: | Parameter | Type | Description | |-----------|------|-------------| | team_id | string | Filter by team (admin only) | | start_date | string | ISO date | | end_date | string | ISO date | | days | integer | Days to look back (default 30) |

Volume

GET /api/v1/metrics/volume

Query Parameters: | Parameter | Type | Description | |-----------|------|-------------| | team_id | string | Filter by team | | start_date | string | ISO date | | end_date | string | ISO date | | days | integer | Days to look back | | granularity | string | hour, day, week, or month |

Performance

GET /api/v1/metrics/performance

Team Metrics

GET /api/v1/metrics/team/{team_id}

User Metrics

GET /api/v1/metrics/user/{user_id}

Export Metrics

GET /api/v1/metrics/export

Webhooks

These endpoints are called by SMS providers to deliver incoming messages.

Receive SMS (Team)

POST /webhook/sms/{secret_token}

The secret_token is the team's webhook secret.

Receive SMS (Domain)

POST /webhook/domain/{provider}/{secret_token}
  • provider: ubity or isp_telecom
  • secret_token: Domain's webhook secret

Message Status Update

POST /webhook/sms/{secret_token}/status

Admin Endpoints (Super Admin Only)

Organizations

List All Organizations

GET /api/v1/organizations

Create Organization

POST /api/v1/organizations

Request:

{
  "name": "New Organization",
  "owner_email": "owner@example.com"
}

Get Organization

GET /api/v1/organizations/{org_id}

Notes: - Super admins can access any organization - Organization admins can only access their own organization

Get Organization Invitations

GET /api/v1/organizations/{org_id}/invitations

Notes: - Super admins can access any organization - Organization admins can only access their own organization

Update Organization

PUT /api/v1/organizations/{org_id}

Delete Organization

DELETE /api/v1/organizations/{org_id}

Update Organization Member

PUT /api/v1/organizations/{org_id}/members/{user_id}

Request:

{
  "role": "admin",
  "is_active": true
}

Delete Organization Member

DELETE /api/v1/organizations/{org_id}/members/{user_id}

Domains

List Domains

GET /api/v1/domains

Create Domain

POST /api/v1/domains

Request:

{
  "name": "my-domain",
  "hostnames": ["app.example.com", "app.example.com:8080"],
  "display_name": "My Domain"
}

Get Domain

GET /api/v1/domains/{domain_id}

Update Domain

PUT /api/v1/domains/{domain_id}

Delete Domain

DELETE /api/v1/domains/{domain_id}

Get Current Domain (Public)

GET /api/v1/domains/current

Domain Settings

SMTP Settings

GET /api/v1/domains/{domain_id}/settings/smtp
PUT /api/v1/domains/{domain_id}/settings/smtp

OAuth Settings

GET /api/v1/domains/{domain_id}/settings/oauth
PUT /api/v1/domains/{domain_id}/settings/oauth/{provider}

SMS Providers

GET /api/v1/domains/{domain_id}/sms-providers
PUT /api/v1/domains/{domain_id}/sms-providers/{provider}

Domain Phone Numbers

List Phone Numbers

GET /api/v1/domains/{domain_id}/phone-numbers

Create Phone Number(s)

POST /api/v1/domains/{domain_id}/phone-numbers

Request (batch):

{
  "numbers": ["+15141234567", "+15149876543"],
  "provider": "ubity"
}

Update Phone Number

PUT /api/v1/domains/{domain_id}/phone-numbers/{phone_id}

Configure Provider

PUT /api/v1/domains/{domain_id}/phone-numbers/{phone_id}/provider

Request:

{
  "provider": "ubity",
  "config": { "api_key": "..." },
  "test_first": true
}

Assign to Organization

POST /api/v1/domains/{domain_id}/phone-numbers/{phone_id}/assign

Request:

{
  "organization_id": "org-id"
}

Delete Phone Number

DELETE /api/v1/domains/{domain_id}/phone-numbers/{phone_id}

Domain Webhooks

GET /api/v1/domains/{domain_id}/webhook
POST /api/v1/domains/{domain_id}/webhook/regenerate

Domain SMS Logs

GET /api/v1/domains/{domain_id}/sms-logs

Query Parameters: | Parameter | Type | Description | |-----------|------|-------------| | direction | string | inbound or outbound | | provider | string | Filter by provider | | start_date | string | ISO date | | end_date | string | ISO date | | skip | integer | Pagination offset | | limit | integer | Results per page (max 100) |


Error Responses

All errors follow this format:

{
  "error": "error_code",
  "message": "Human-readable error message"
}

Common error codes: - validation_error - Invalid request data - unauthorized - Authentication required - forbidden - Insufficient permissions - not_found - Resource not found - send_failed - SMS sending failed - provider_error - SMS provider error


Rate Limits

Endpoint Limit
POST /auth/login 20/minute
POST /auth/register 10/hour
POST /auth/forgot-password 5/hour
POST /auth/reset-password 10/hour
POST /sms/send 100/hour

Roles & Permissions

Role Description
super_admin Full system access, can manage all domains and organizations
admin Organization administrator, can manage teams and members
manager Team manager, can configure team settings and view metrics
agent Can handle conversations assigned to their team