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

> ## Agent Instructions
> Every Lath operation is POST https://platform.trylath.com/<operation name with dots replaced by slashes>, with a JSON body and `Authorization: Bearer <key>`. `email.send` is POST /email/send.
> Branch on `error.code`, never on `error.message`. Every refusal also carries `error.fix`, which names the next step.
> Send an `Idempotency-Key` header on any operation that is not retry-safe, so a retry cannot run it twice.
> A `lath_test_` key emails only the account's own members and sends no SMS; a `lath_live_` key reaches real recipients and is billed.
> The OpenAPI document, generated from the same registry as the routes, is at https://platform.trylath.com/openapi.json.

# sms.send

> Sends one SMS to one number in E.164 form, from the environment's configured sender. The body may carry {{variables}}. Asks the audience policy first: a number that has replied STOP is recorded as suppressed, not sent. Billing counts segments, not messages — a body outside the GSM alphabet costs more than twice as much per character, and the reply says how many segments were counted. If the environment cannot text anyone yet (no active carrier registration, or no number to send from) the message is still stored and the reply carries `blocked` saying why — do not wait on a status that cannot change until that clears.



## OpenAPI

````yaml /api-reference/openapi.json post /sms/send
openapi: 3.1.0
info:
  title: Lath API
  version: 0.1.0
  description: >-
    Every operation is one POST. The same set is reachable over MCP, the SDK and
    the CLI; nothing is dashboard-only.
servers:
  - url: https://platform.trylath.com
    description: This deployment
security: []
paths:
  /sms/send:
    post:
      tags:
        - sms
      summary: sms.send
      description: >-
        Sends one SMS to one number in E.164 form, from the environment's
        configured sender. The body may carry {{variables}}. Asks the audience
        policy first: a number that has replied STOP is recorded as suppressed,
        not sent. Billing counts segments, not messages — a body outside the GSM
        alphabet costs more than twice as much per character, and the reply says
        how many segments were counted. If the environment cannot text anyone
        yet (no active carrier registration, or no number to send from) the
        message is still stored and the reply carries `blocked` saying why — do
        not wait on a status that cannot change until that clears.
      operationId: sms.send
      parameters:
        - name: Idempotency-Key
          in: header
          required: false
          schema:
            type: string
          description: >-
            Replays the stored response for the same key and input; refuses
            different input.
      requestBody:
        required: true
        content:
          application/json:
            schema:
              $schema: https://json-schema.org/draft/2020-12/schema
              type: object
              properties:
                to:
                  type: string
                  pattern: ^\+[1-9]\d{6,14}$
                  description: One recipient, E.164, e.g. +14155550100
                template:
                  description: >-
                    An SMS template name; provide variables with it. Use instead
                    of body, not with it.
                  type: string
                  minLength: 1
                  maxLength: 120
                locale:
                  description: >-
                    Send the template's variant for this language, falling back
                    to the broader language and then the default. Omit to use
                    the recipient's own locale if one is recorded.
                  type: string
                  maxLength: 20
                body:
                  description: 'Inline send: the message; may reference {{variables}}'
                  type: string
                  minLength: 1
                  maxLength: 1600
                variables:
                  type: object
                  propertyNames:
                    type: string
                    pattern: ^[A-Za-z_][A-Za-z0-9_]*$
                  additionalProperties: {}
                sendAfter:
                  description: >-
                    Hold the message until this moment; omit to send now. Until
                    it is sent it can be stopped with sms.message.cancel.
                  type: string
                  format: date-time
                  pattern: >-
                    ^(?:(?:\d\d[2468][048]|\d\d[13579][26]|\d\d0[48]|[02468][048]00|[13579][26]00)-02-29|\d{4}-(?:(?:0[13578]|1[02])-(?:0[1-9]|[12]\d|3[01])|(?:0[469]|11)-(?:0[1-9]|[12]\d|30)|(?:02)-(?:0[1-9]|1\d|2[0-8])))T(?:(?:[01]\d|2[0-3]):[0-5]\d:[0-5]\d(?:\.\d+)?(?:Z|([+-](?:[01]\d|2[0-3]):[0-5]\d)))$
                topic:
                  description: >-
                    A consent topic for marketing; omit for transactional, which
                    only a suppression stops
                  type: string
                  minLength: 1
                  maxLength: 64
                metadata:
                  description: >-
                    Up to 20 key/values echoed on every webhook about this
                    message
                  type: object
                  propertyNames:
                    type: string
                    maxLength: 40
                  additionalProperties:
                    anyOf:
                      - type: string
                        maxLength: 500
                      - type: number
                      - type: boolean
              required:
                - to
              additionalProperties: false
      responses:
        '200':
          description: '{ activityId, result }. activityId is empty for reads.'
          content:
            application/json:
              schema:
                type: object
                properties:
                  activityId:
                    type: string
                    description: The activity this call created, or empty for a read.
                  result:
                    $schema: https://json-schema.org/draft/2020-12/schema
                    type: object
                    properties:
                      messageId:
                        type: string
                        format: uuid
                        pattern: >-
                          ^([0-9a-fA-F]{8}-[0-9a-fA-F]{4}-[1-8][0-9a-fA-F]{3}-[89abAB][0-9a-fA-F]{3}-[0-9a-fA-F]{12}|00000000-0000-0000-0000-000000000000|ffffffff-ffff-ffff-ffff-ffffffffffff)$
                      status:
                        type: string
                        enum:
                          - queued
                          - suppressed
                      to:
                        type: string
                      segments:
                        type: integer
                        minimum: -9007199254740991
                        maximum: 9007199254740991
                      encoding:
                        type: string
                      template:
                        type:
                          - string
                          - 'null'
                      templateVersion:
                        anyOf:
                          - type: integer
                            minimum: -9007199254740991
                            maximum: 9007199254740991
                          - type: 'null'
                      templateLocale:
                        type:
                          - string
                          - 'null'
                      sendAfter:
                        anyOf:
                          - type: string
                            format: date-time
                            pattern: >-
                              ^(?:(?:\d\d[2468][048]|\d\d[13579][26]|\d\d0[48]|[02468][048]00|[13579][26]00)-02-29|\d{4}-(?:(?:0[13578]|1[02])-(?:0[1-9]|[12]\d|3[01])|(?:0[469]|11)-(?:0[1-9]|[12]\d|30)|(?:02)-(?:0[1-9]|1\d|2[0-8])))T(?:(?:[01]\d|2[0-3]):[0-5]\d:[0-5]\d(?:\.\d+)?(?:Z|([+-](?:[01]\d|2[0-3]):[0-5]\d)))$
                          - type: 'null'
                      suppressed:
                        type: object
                        properties:
                          reason:
                            type: string
                          detail:
                            type: string
                        required:
                          - reason
                          - detail
                        additionalProperties: {}
                      blocked:
                        type: object
                        properties:
                          reason:
                            type: string
                          fix:
                            type: string
                        required:
                          - reason
                          - fix
                        additionalProperties: {}
                    required:
                      - messageId
                      - status
                      - to
                      - segments
                      - encoding
                      - template
                      - templateVersion
                      - templateLocale
                      - sendAfter
                    additionalProperties: {}
                required:
                  - activityId
                  - result
        '400':
          description: invalid_input or invalid_json
        '401':
          description: unauthenticated
        '403':
          description: forbidden
        '404':
          description: not_found
        '409':
          description: 'conflict: idempotency_mismatch, email_taken, last_key'
        '413':
          description: body_too_large
        '429':
          description: rate_limited
      security:
        - bearer: []
components:
  securitySchemes:
    bearer:
      type: http
      scheme: bearer
      description: >-
        A Lath API key: lath_live_sk… or lath_test_sk… on a server,
        lath_live_pk… or lath_test_pk… in a browser.

````