Документация для разработчиков

Обработка входящих писем

Приём почты на адреса DashaMail, разбор писем и передача их в вашу систему по webhook.

Раздел позволяет принимать входящие письма — ответы на рассылки, обращения в поддержку, машинные уведомления — и обрабатывать их автоматически. DashaMail принимает письмо, разбирает его на части (тема, текст, вложения) и выполняет действия того маршрута, чьи условия совпали.

Как это работает

  1. Домен. У аккаунта есть служебный поддомен, который создаётся автоматически при первом обращении к списку доменов. Можно подключить и свой — тогда потребуется прописать MX-запись.
  2. Маршруты. Каждый маршрут — это условия отбора писем и список действий. Письмо проверяется маршрутами по возрастанию priority.
  3. Действия. Отправить письмо на ваш webhook, сохранить его для последующей выгрузки, переслать на другой адрес или прервать обработку.

Условия отбора

Условия задаются либо структурой filter, либо текстовым выражением expression — но не обоими сразу. Маршрут без условий принимает все письма.

{
  "combinator": "and",
  "conditions": [
    { "field": "recipient", "op": "matches", "value": "^support@" },
    { "field": "header", "name": "X-Priority", "op": "equals", "value": "1" }
  ]
}
КлючЗначения
combinatorand или or
fieldrecipient — адрес получателя, from — адрес автора, sender — конверт отправителя, header — произвольный заголовок (требует name)
opmatches — регулярное выражение, equals — точное совпадение, contains — вхождение подстроки
valueНепустая строка. Для matches проверяется корректность шаблона при сохранении

Действия

actions — массив от одного до пяти элементов. Каждый элемент обязан иметь type.

ТипПараметрыЧто делает
webhook url — обязателен, должен начинаться с http:// или https://, не длиннее 2048 символов.
attachmentsoff (по умолчанию), url — ссылки на файлы, inline — файлы в base64
Отправляет разобранное письмо POST-запросом на ваш адрес
store ttl_days — срок хранения от 1 до 30 дней.
notify_url — адрес уведомления о поступлении
Сохраняет письмо, чтобы забрать его позже через список писем
forward email — адрес получателя Пересылает письмо. Доступно только на платном тарифе и требует подтверждённого домена отправки; списывает баланс как транзакционное письмо. Пересылка на inbound-домен DashaMail запрещена
stop Прерывает обработку: следующие маршруты не проверяются

Подпись webhook

У каждого маршрута есть signing_key — им подписываются исходящие webhook-запросы. Проверяйте подпись на своей стороне, чтобы отличать запросы DashaMail от посторонних. Ключ можно перевыпустить, если он скомпрометирован.

Права субаккаунта на этот раздел задаются отдельно. При уровне доступа «только чтение» изменяющие запросы вернут code: 2, при полном запрете недоступен весь раздел.

Домены приёма #

GET /router/domains

Список доменов, на которые аккаунт принимает почту.

При первом обращении служебный поддомен аккаунта создаётся автоматически — отдельный запрос для этого не нужен.

curl -X GET 'https://api.dashamail.com/v2/router/domains' \
  -H 'Authorization: Bearer YOUR_API_KEY'
<?php
$ch = curl_init('https://api.dashamail.com/v2/router/domains');
curl_setopt_array($ch, [
    CURLOPT_RETURNTRANSFER => true,
    CURLOPT_CUSTOMREQUEST  => 'GET',
    CURLOPT_HTTPHEADER     => [
        'Authorization: Bearer YOUR_API_KEY',
    ],
]);

$response = json_decode(curl_exec($ch), true);
$status   = curl_getinfo($ch, CURLINFO_HTTP_CODE);
curl_close($ch);

if ($status >= 400) {
    throw new RuntimeException($response['error']['message']);
}
print_r($response['response']['data']);
import requests

response = requests.get(
    'https://api.dashamail.com/v2/router/domains',
    headers={'Authorization': 'Bearer YOUR_API_KEY'},
)

response.raise_for_status()
print(response.json()['response']['data'])
const response = await fetch('https://api.dashamail.com/v2/router/domains', {
  method: 'GET',
  headers: {
    'Authorization': 'Bearer YOUR_API_KEY',
  },
});

const payload = await response.json();
if (!response.ok) throw new Error(payload.error.message);
console.log(payload.response.data);
Ответ HTTP 200
{
  "response": {
    "msg": {
      "err_code": 0,
      "text": "OK",
      "type": "message"
    },
    "data": [
      {
        "id": 41,
        "domain": "u128341.in.dashamail.com",
        "is_default": true,
        "verified": 1,
        "created_at": "2026-04-01 12:00:00"
      }
    ]
  }
}

Подключить свой домен #

POST /router/domains

Добавляет ваш поддомен для приёма писем. После добавления пропишите MX-запись из инструкции и запустите проверку.

Параметры тела запроса

ПараметрТипОписание
domain обязательныйstringПоддомен для приёма почты, например mail.example.ru.

Возможные ошибки

HTTPcodeКогда возникает
422 3 Домен не задан или некорректен
401 2 Недостаточно прав
curl -X POST 'https://api.dashamail.com/v2/router/domains' \
  -H 'Authorization: Bearer YOUR_API_KEY' \
  -H 'Content-Type: application/json' \
  -d '{
  "domain": "mail.example.ru"
}'
<?php
$ch = curl_init('https://api.dashamail.com/v2/router/domains');
curl_setopt_array($ch, [
    CURLOPT_RETURNTRANSFER => true,
    CURLOPT_CUSTOMREQUEST  => 'POST',
    CURLOPT_HTTPHEADER     => [
        'Authorization: Bearer YOUR_API_KEY',
        'Content-Type: application/json',
    ],
    CURLOPT_POSTFIELDS     => json_encode([
            'domain' => 'mail.example.ru',
        ], JSON_UNESCAPED_UNICODE),
]);

$response = json_decode(curl_exec($ch), true);
$status   = curl_getinfo($ch, CURLINFO_HTTP_CODE);
curl_close($ch);

if ($status >= 400) {
    throw new RuntimeException($response['error']['message']);
}
print_r($response['response']['data']);
import requests

response = requests.post(
    'https://api.dashamail.com/v2/router/domains',
    headers={'Authorization': 'Bearer YOUR_API_KEY'},
    json={
        'domain': 'mail.example.ru',
    },
)

response.raise_for_status()
print(response.json()['response']['data'])
const response = await fetch('https://api.dashamail.com/v2/router/domains', {
  method: 'POST',
  headers: {
    'Authorization': 'Bearer YOUR_API_KEY',
    'Content-Type': 'application/json',
  },
  body: JSON.stringify({
  "domain": "mail.example.ru"
}),
});

const payload = await response.json();
if (!response.ok) throw new Error(payload.error.message);
console.log(payload.response.data);
Ответ HTTP 201
{
  "response": {
    "msg": {
      "err_code": 0,
      "text": "OK",
      "type": "message"
    },
    "data": {
      "id": 42,
      "domain": "mail.example.ru",
      "verified": 0
    }
  }
}

Проверить MX-запись #

POST /router/domains/{domain_id}/verify

Проверяет, что MX-запись домена указывает на серверы DashaMail. До успешной проверки письма на этот домен не принимаются.

Параметры пути

ПараметрТипОписание
domain_id обязательныйintegerИдентификатор домена.

Возможные ошибки

HTTPcodeКогда возникает
404 4 Домена с таким идентификатором нет
422 3 MX-запись не найдена или указывает не на DashaMail
curl -X POST 'https://api.dashamail.com/v2/router/domains/42/verify' \
  -H 'Authorization: Bearer YOUR_API_KEY'
<?php
$ch = curl_init('https://api.dashamail.com/v2/router/domains/42/verify');
curl_setopt_array($ch, [
    CURLOPT_RETURNTRANSFER => true,
    CURLOPT_CUSTOMREQUEST  => 'POST',
    CURLOPT_HTTPHEADER     => [
        'Authorization: Bearer YOUR_API_KEY',
    ],
]);

$response = json_decode(curl_exec($ch), true);
$status   = curl_getinfo($ch, CURLINFO_HTTP_CODE);
curl_close($ch);

if ($status >= 400) {
    throw new RuntimeException($response['error']['message']);
}
print_r($response['response']['data']);
import requests

response = requests.post(
    'https://api.dashamail.com/v2/router/domains/42/verify',
    headers={'Authorization': 'Bearer YOUR_API_KEY'},
)

response.raise_for_status()
print(response.json()['response']['data'])
const response = await fetch('https://api.dashamail.com/v2/router/domains/42/verify', {
  method: 'POST',
  headers: {
    'Authorization': 'Bearer YOUR_API_KEY',
  },
});

const payload = await response.json();
if (!response.ok) throw new Error(payload.error.message);
console.log(payload.response.data);
Ответ HTTP 200
{
  "response": {
    "msg": {
      "err_code": 0,
      "text": "OK",
      "type": "message"
    },
    "data": {
      "id": 42,
      "domain": "mail.example.ru",
      "verified": 1
    }
  }
}

Удалить домен приёма #

DELETE /router/domains/{domain_id}

Отключает приём почты на домен. Служебный домен аккаунта удалить нельзя.

Параметры пути

ПараметрТипОписание
domain_id обязательныйintegerИдентификатор домена.

Возможные ошибки

HTTPcodeКогда возникает
404 4 Домена с таким идентификатором нет
401 2 Недостаточно прав
curl -X DELETE 'https://api.dashamail.com/v2/router/domains/42' \
  -H 'Authorization: Bearer YOUR_API_KEY'
<?php
$ch = curl_init('https://api.dashamail.com/v2/router/domains/42');
curl_setopt_array($ch, [
    CURLOPT_RETURNTRANSFER => true,
    CURLOPT_CUSTOMREQUEST  => 'DELETE',
    CURLOPT_HTTPHEADER     => [
        'Authorization: Bearer YOUR_API_KEY',
    ],
]);

$response = json_decode(curl_exec($ch), true);
$status   = curl_getinfo($ch, CURLINFO_HTTP_CODE);
curl_close($ch);

if ($status >= 400) {
    throw new RuntimeException($response['error']['message']);
}
print_r($response['response']['data']);
import requests

response = requests.delete(
    'https://api.dashamail.com/v2/router/domains/42',
    headers={'Authorization': 'Bearer YOUR_API_KEY'},
)

response.raise_for_status()
print(response.json()['response']['data'])
const response = await fetch('https://api.dashamail.com/v2/router/domains/42', {
  method: 'DELETE',
  headers: {
    'Authorization': 'Bearer YOUR_API_KEY',
  },
});

const payload = await response.json();
if (!response.ok) throw new Error(payload.error.message);
console.log(payload.response.data);
Ответ HTTP 204
(тело ответа пустое)

Что прописать в DNS #

GET /router/domains/mx

Возвращает MX-запись, которую нужно добавить у регистратора, чтобы почта на ваш домен приходила в DashaMail.

curl -X GET 'https://api.dashamail.com/v2/router/domains/mx' \
  -H 'Authorization: Bearer YOUR_API_KEY'
<?php
$ch = curl_init('https://api.dashamail.com/v2/router/domains/mx');
curl_setopt_array($ch, [
    CURLOPT_RETURNTRANSFER => true,
    CURLOPT_CUSTOMREQUEST  => 'GET',
    CURLOPT_HTTPHEADER     => [
        'Authorization: Bearer YOUR_API_KEY',
    ],
]);

$response = json_decode(curl_exec($ch), true);
$status   = curl_getinfo($ch, CURLINFO_HTTP_CODE);
curl_close($ch);

if ($status >= 400) {
    throw new RuntimeException($response['error']['message']);
}
print_r($response['response']['data']);
import requests

response = requests.get(
    'https://api.dashamail.com/v2/router/domains/mx',
    headers={'Authorization': 'Bearer YOUR_API_KEY'},
)

response.raise_for_status()
print(response.json()['response']['data'])
const response = await fetch('https://api.dashamail.com/v2/router/domains/mx', {
  method: 'GET',
  headers: {
    'Authorization': 'Bearer YOUR_API_KEY',
  },
});

const payload = await response.json();
if (!response.ok) throw new Error(payload.error.message);
console.log(payload.response.data);
Ответ HTTP 200
{
  "response": {
    "msg": {
      "err_code": 0,
      "text": "OK",
      "type": "message"
    },
    "data": {
      "mx_target": "in.dashamail.com",
      "priority": 10,
      "example": "mail.example.ru. IN MX 10 in.dashamail.com."
    }
  }
}

Список маршрутов #

GET /router/routes

Все маршруты аккаунта в порядке применения — по возрастанию priority.

Что возвращается

match_count и last_matched_at показывают, срабатывал ли маршрут — полезно при отладке условий. Поле expression — текстовая запись того же условия, что и filter.

curl -X GET 'https://api.dashamail.com/v2/router/routes' \
  -H 'Authorization: Bearer YOUR_API_KEY'
<?php
$ch = curl_init('https://api.dashamail.com/v2/router/routes');
curl_setopt_array($ch, [
    CURLOPT_RETURNTRANSFER => true,
    CURLOPT_CUSTOMREQUEST  => 'GET',
    CURLOPT_HTTPHEADER     => [
        'Authorization: Bearer YOUR_API_KEY',
    ],
]);

$response = json_decode(curl_exec($ch), true);
$status   = curl_getinfo($ch, CURLINFO_HTTP_CODE);
curl_close($ch);

if ($status >= 400) {
    throw new RuntimeException($response['error']['message']);
}
print_r($response['response']['data']);
import requests

response = requests.get(
    'https://api.dashamail.com/v2/router/routes',
    headers={'Authorization': 'Bearer YOUR_API_KEY'},
)

response.raise_for_status()
print(response.json()['response']['data'])
const response = await fetch('https://api.dashamail.com/v2/router/routes', {
  method: 'GET',
  headers: {
    'Authorization': 'Bearer YOUR_API_KEY',
  },
});

const payload = await response.json();
if (!response.ok) throw new Error(payload.error.message);
console.log(payload.response.data);
Ответ HTTP 200
{
  "response": {
    "msg": {
      "err_code": 0,
      "text": "OK",
      "type": "message"
    },
    "data": [
      {
        "id": 7,
        "priority": 0,
        "description": "Обращения в поддержку",
        "filter": {
          "combinator": "and",
          "conditions": [
            {
              "field": "recipient",
              "op": "matches",
              "value": "^support@"
            }
          ]
        },
        "expression": "recipient matches \"^support@\"",
        "actions": [
          {
            "type": "webhook",
            "url": "https://example.ru/inbound",
            "attachments": "url"
          }
        ],
        "signing_key": "whsec_8f2c…",
        "is_active": true,
        "match_count": 412,
        "last_matched_at": "2026-04-12 09:41:02",
        "created_at": "2026-04-01 12:04:00",
        "updated_at": "2026-04-10 15:22:31"
      }
    ]
  }
}

Один маршрут #

GET /router/routes/{route_id}

Возвращает маршрут целиком, включая ключ подписи.

Параметры пути

ПараметрТипОписание
route_id обязательныйintegerИдентификатор маршрута.

Возможные ошибки

HTTPcodeКогда возникает
404 4 Маршрута с таким идентификатором нет
curl -X GET 'https://api.dashamail.com/v2/router/routes/7' \
  -H 'Authorization: Bearer YOUR_API_KEY'
<?php
$ch = curl_init('https://api.dashamail.com/v2/router/routes/7');
curl_setopt_array($ch, [
    CURLOPT_RETURNTRANSFER => true,
    CURLOPT_CUSTOMREQUEST  => 'GET',
    CURLOPT_HTTPHEADER     => [
        'Authorization: Bearer YOUR_API_KEY',
    ],
]);

$response = json_decode(curl_exec($ch), true);
$status   = curl_getinfo($ch, CURLINFO_HTTP_CODE);
curl_close($ch);

if ($status >= 400) {
    throw new RuntimeException($response['error']['message']);
}
print_r($response['response']['data']);
import requests

response = requests.get(
    'https://api.dashamail.com/v2/router/routes/7',
    headers={'Authorization': 'Bearer YOUR_API_KEY'},
)

response.raise_for_status()
print(response.json()['response']['data'])
const response = await fetch('https://api.dashamail.com/v2/router/routes/7', {
  method: 'GET',
  headers: {
    'Authorization': 'Bearer YOUR_API_KEY',
  },
});

const payload = await response.json();
if (!response.ok) throw new Error(payload.error.message);
console.log(payload.response.data);
Ответ HTTP 200
{
  "response": {
    "msg": {
      "err_code": 0,
      "text": "OK",
      "type": "message"
    },
    "data": {
      "id": 7,
      "priority": 0,
      "description": "Обращения в поддержку",
      "filter": {
        "combinator": "and",
        "conditions": [
          {
            "field": "recipient",
            "op": "matches",
            "value": "^support@"
          }
        ]
      },
      "actions": [
        {
          "type": "webhook",
          "url": "https://example.ru/inbound"
        }
      ],
      "signing_key": "whsec_8f2c…",
      "is_active": true
    }
  }
}

Создать маршрут #

POST /router/routes

Создаёт правило обработки входящих писем. Без явного priority маршрут встаёт в конец очереди.

Ключ подписи signing_key генерируется автоматически и возвращается в ответе — сохраните его, чтобы проверять подлинность webhook-запросов.

Параметры тела запроса

ПараметрТипОписание
actions обязательныйJSON-строкаДействия маршрута — от одного до пяти. См. описание действий.
filterJSON-строкаУсловия отбора писем. Несовместим с expression. Без условий маршрут принимает все письма.
expressionstringУсловия отбора текстом. Несовместим с filter.
descriptionstringОписание маршрута, не длиннее 255 символов.
is_activeфлагпо умолчанию: 1Активен ли маршрут.
priorityintegerПорядок применения. Меньше — раньше.

Возможные ошибки

HTTPcodeКогда возникает
422 3 Некорректная структура filter или actions, заданы оба способа задания условий, либо действие forward недоступно на текущем тарифе
401 2 Недостаточно прав
curl -X POST 'https://api.dashamail.com/v2/router/routes' \
  -H 'Authorization: Bearer YOUR_API_KEY' \
  -H 'Content-Type: application/json' \
  -d '{
  "description": "Обращения в поддержку",
  "filter": "{\"combinator\":\"and\",\"conditions\":[{\"field\":\"recipient\",\"op\":\"matches\",\"value\":\"^support@\"}]}",
  "actions": "[{\"type\":\"webhook\",\"url\":\"https://example.ru/inbound\",\"attachments\":\"url\"},{\"type\":\"stop\"}]"
}'
<?php
$ch = curl_init('https://api.dashamail.com/v2/router/routes');
curl_setopt_array($ch, [
    CURLOPT_RETURNTRANSFER => true,
    CURLOPT_CUSTOMREQUEST  => 'POST',
    CURLOPT_HTTPHEADER     => [
        'Authorization: Bearer YOUR_API_KEY',
        'Content-Type: application/json',
    ],
    CURLOPT_POSTFIELDS     => json_encode([
            'description' => 'Обращения в поддержку',
            'filter' => '{"combinator":"and","conditions":[{"field":"recipient","op":"matches","value":"^support@"}]}',
            'actions' => '[{"type":"webhook","url":"https://example.ru/inbound","attachments":"url"},{"type":"stop"}]',
        ], JSON_UNESCAPED_UNICODE),
]);

$response = json_decode(curl_exec($ch), true);
$status   = curl_getinfo($ch, CURLINFO_HTTP_CODE);
curl_close($ch);

if ($status >= 400) {
    throw new RuntimeException($response['error']['message']);
}
print_r($response['response']['data']);
import requests

response = requests.post(
    'https://api.dashamail.com/v2/router/routes',
    headers={'Authorization': 'Bearer YOUR_API_KEY'},
    json={
        'description': 'Обращения в поддержку',
        'filter': '{"combinator":"and","conditions":[{"field":"recipient","op":"matches","value":"^support@"}]}',
        'actions': '[{"type":"webhook","url":"https://example.ru/inbound","attachments":"url"},{"type":"stop"}]',
    },
)

response.raise_for_status()
print(response.json()['response']['data'])
const response = await fetch('https://api.dashamail.com/v2/router/routes', {
  method: 'POST',
  headers: {
    'Authorization': 'Bearer YOUR_API_KEY',
    'Content-Type': 'application/json',
  },
  body: JSON.stringify({
  "description": "Обращения в поддержку",
  "filter": "{\"combinator\":\"and\",\"conditions\":[{\"field\":\"recipient\",\"op\":\"matches\",\"value\":\"^support@\"}]}",
  "actions": "[{\"type\":\"webhook\",\"url\":\"https://example.ru/inbound\",\"attachments\":\"url\"},{\"type\":\"stop\"}]"
}),
});

const payload = await response.json();
if (!response.ok) throw new Error(payload.error.message);
console.log(payload.response.data);
Ответ HTTP 201
{
  "response": {
    "msg": {
      "err_code": 0,
      "text": "OK",
      "type": "message"
    },
    "data": {
      "id": 7,
      "priority": 0,
      "description": "Обращения в поддержку",
      "signing_key": "whsec_8f2c…",
      "is_active": true,
      "match_count": 0
    }
  }
}

Изменить маршрут #

PUT /router/routes/{route_id}

Меняет отдельные поля маршрута. Передавайте только то, что нужно изменить — незаданные поля сохраняют прежние значения.

Параметры пути

ПараметрТипОписание
route_id обязательныйintegerИдентификатор маршрута.

Параметры тела запроса

ПараметрТипОписание
descriptionstringНовое описание.
filterJSON-строкаНовые условия отбора.
expressionstringНовые условия текстом.
actionsJSON-строкаНовый набор действий. Заменяет прежний целиком.
is_activeфлагВключить или выключить маршрут.
priorityintegerНовый порядок применения.

Возможные ошибки

HTTPcodeКогда возникает
404 4 Маршрута с таким идентификатором нет
422 3 Некорректные условия или действия
401 2 Недостаточно прав
curl -X PUT 'https://api.dashamail.com/v2/router/routes/7' \
  -H 'Authorization: Bearer YOUR_API_KEY' \
  -H 'Content-Type: application/json' \
  -d '{
  "is_active": 0
}'
<?php
$ch = curl_init('https://api.dashamail.com/v2/router/routes/7');
curl_setopt_array($ch, [
    CURLOPT_RETURNTRANSFER => true,
    CURLOPT_CUSTOMREQUEST  => 'PUT',
    CURLOPT_HTTPHEADER     => [
        'Authorization: Bearer YOUR_API_KEY',
        'Content-Type: application/json',
    ],
    CURLOPT_POSTFIELDS     => json_encode([
            'is_active' => 0,
        ], JSON_UNESCAPED_UNICODE),
]);

$response = json_decode(curl_exec($ch), true);
$status   = curl_getinfo($ch, CURLINFO_HTTP_CODE);
curl_close($ch);

if ($status >= 400) {
    throw new RuntimeException($response['error']['message']);
}
print_r($response['response']['data']);
import requests

response = requests.put(
    'https://api.dashamail.com/v2/router/routes/7',
    headers={'Authorization': 'Bearer YOUR_API_KEY'},
    json={
        'is_active': 0,
    },
)

response.raise_for_status()
print(response.json()['response']['data'])
const response = await fetch('https://api.dashamail.com/v2/router/routes/7', {
  method: 'PUT',
  headers: {
    'Authorization': 'Bearer YOUR_API_KEY',
    'Content-Type': 'application/json',
  },
  body: JSON.stringify({
  "is_active": 0
}),
});

const payload = await response.json();
if (!response.ok) throw new Error(payload.error.message);
console.log(payload.response.data);
Ответ HTTP 200
{
  "response": {
    "msg": {
      "err_code": 0,
      "text": "OK",
      "type": "message"
    },
    "data": {
      "id": 7,
      "description": "Обращения в поддержку",
      "is_active": false
    }
  }
}

Удалить маршрут #

DELETE /router/routes/{route_id}

Удаляет маршрут. Уже сохранённые им письма остаются доступными до истечения их срока хранения.

Параметры пути

ПараметрТипОписание
route_id обязательныйintegerИдентификатор маршрута.

Возможные ошибки

HTTPcodeКогда возникает
404 4 Маршрута с таким идентификатором нет
401 2 Недостаточно прав
curl -X DELETE 'https://api.dashamail.com/v2/router/routes/7' \
  -H 'Authorization: Bearer YOUR_API_KEY'
<?php
$ch = curl_init('https://api.dashamail.com/v2/router/routes/7');
curl_setopt_array($ch, [
    CURLOPT_RETURNTRANSFER => true,
    CURLOPT_CUSTOMREQUEST  => 'DELETE',
    CURLOPT_HTTPHEADER     => [
        'Authorization: Bearer YOUR_API_KEY',
    ],
]);

$response = json_decode(curl_exec($ch), true);
$status   = curl_getinfo($ch, CURLINFO_HTTP_CODE);
curl_close($ch);

if ($status >= 400) {
    throw new RuntimeException($response['error']['message']);
}
print_r($response['response']['data']);
import requests

response = requests.delete(
    'https://api.dashamail.com/v2/router/routes/7',
    headers={'Authorization': 'Bearer YOUR_API_KEY'},
)

response.raise_for_status()
print(response.json()['response']['data'])
const response = await fetch('https://api.dashamail.com/v2/router/routes/7', {
  method: 'DELETE',
  headers: {
    'Authorization': 'Bearer YOUR_API_KEY',
  },
});

const payload = await response.json();
if (!response.ok) throw new Error(payload.error.message);
console.log(payload.response.data);
Ответ HTTP 204
(тело ответа пустое)

Перевыпустить ключ подписи #

POST /router/routes/{route_id}/rekey

Генерирует новый signing_key. Старый перестаёт действовать немедленно — обновите его в своём обработчике сразу после вызова.

Параметры пути

ПараметрТипОписание
route_id обязательныйintegerИдентификатор маршрута.

Возможные ошибки

HTTPcodeКогда возникает
404 4 Маршрута с таким идентификатором нет
401 2 Недостаточно прав
curl -X POST 'https://api.dashamail.com/v2/router/routes/7/rekey' \
  -H 'Authorization: Bearer YOUR_API_KEY'
<?php
$ch = curl_init('https://api.dashamail.com/v2/router/routes/7/rekey');
curl_setopt_array($ch, [
    CURLOPT_RETURNTRANSFER => true,
    CURLOPT_CUSTOMREQUEST  => 'POST',
    CURLOPT_HTTPHEADER     => [
        'Authorization: Bearer YOUR_API_KEY',
    ],
]);

$response = json_decode(curl_exec($ch), true);
$status   = curl_getinfo($ch, CURLINFO_HTTP_CODE);
curl_close($ch);

if ($status >= 400) {
    throw new RuntimeException($response['error']['message']);
}
print_r($response['response']['data']);
import requests

response = requests.post(
    'https://api.dashamail.com/v2/router/routes/7/rekey',
    headers={'Authorization': 'Bearer YOUR_API_KEY'},
)

response.raise_for_status()
print(response.json()['response']['data'])
const response = await fetch('https://api.dashamail.com/v2/router/routes/7/rekey', {
  method: 'POST',
  headers: {
    'Authorization': 'Bearer YOUR_API_KEY',
  },
});

const payload = await response.json();
if (!response.ok) throw new Error(payload.error.message);
console.log(payload.response.data);
Ответ HTTP 200
{
  "response": {
    "msg": {
      "err_code": 0,
      "text": "OK",
      "type": "message"
    },
    "data": {
      "id": 7,
      "signing_key": "whsec_1d9b…"
    }
  }
}

Изменить порядок маршрутов #

POST /router/routes/reorder

Задаёт новый порядок применения маршрутов одним запросом. Передайте идентификаторы в нужной последовательности.

Параметры тела запроса

ПараметрТипОписание
order обязательныйJSON-строкаМассив идентификаторов маршрутов в порядке применения.

Возможные ошибки

HTTPcodeКогда возникает
422 3 Не передан order или он не является массивом
401 2 Недостаточно прав
curl -X POST 'https://api.dashamail.com/v2/router/routes/reorder' \
  -H 'Authorization: Bearer YOUR_API_KEY' \
  -H 'Content-Type: application/json' \
  -d '{
  "order": "[9,7,12]"
}'
<?php
$ch = curl_init('https://api.dashamail.com/v2/router/routes/reorder');
curl_setopt_array($ch, [
    CURLOPT_RETURNTRANSFER => true,
    CURLOPT_CUSTOMREQUEST  => 'POST',
    CURLOPT_HTTPHEADER     => [
        'Authorization: Bearer YOUR_API_KEY',
        'Content-Type: application/json',
    ],
    CURLOPT_POSTFIELDS     => json_encode([
            'order' => '[9,7,12]',
        ], JSON_UNESCAPED_UNICODE),
]);

$response = json_decode(curl_exec($ch), true);
$status   = curl_getinfo($ch, CURLINFO_HTTP_CODE);
curl_close($ch);

if ($status >= 400) {
    throw new RuntimeException($response['error']['message']);
}
print_r($response['response']['data']);
import requests

response = requests.post(
    'https://api.dashamail.com/v2/router/routes/reorder',
    headers={'Authorization': 'Bearer YOUR_API_KEY'},
    json={
        'order': '[9,7,12]',
    },
)

response.raise_for_status()
print(response.json()['response']['data'])
const response = await fetch('https://api.dashamail.com/v2/router/routes/reorder', {
  method: 'POST',
  headers: {
    'Authorization': 'Bearer YOUR_API_KEY',
    'Content-Type': 'application/json',
  },
  body: JSON.stringify({
  "order": "[9,7,12]"
}),
});

const payload = await response.json();
if (!response.ok) throw new Error(payload.error.message);
console.log(payload.response.data);
Ответ HTTP 200
{
  "response": {
    "msg": {
      "err_code": 0,
      "text": "OK",
      "type": "message"
    },
    "data": true
  }
}

Сохранённые письма #

GET /router/messages

Письма, сохранённые действием store. Тело письма в список не входит — забирайте его поштучно.

Параметры строки запроса

ПараметрТипОписание
route_idintegerТолько письма указанного маршрута.
recipientstringФильтр по адресу получателя.
sincedatetimeПисьма, полученные не раньше.
untildatetimeПисьма, полученные не позже.
limitintegerРазмер страницы.
offsetintegerСмещение.

Возможные ошибки

HTTPcodeКогда возникает
404 4 Писем по фильтру нет
curl -X GET 'https://api.dashamail.com/v2/router/messages?route_id=7&limit=2' \
  -H 'Authorization: Bearer YOUR_API_KEY'
<?php
$ch = curl_init('https://api.dashamail.com/v2/router/messages?route_id=7&limit=2');
curl_setopt_array($ch, [
    CURLOPT_RETURNTRANSFER => true,
    CURLOPT_CUSTOMREQUEST  => 'GET',
    CURLOPT_HTTPHEADER     => [
        'Authorization: Bearer YOUR_API_KEY',
    ],
]);

$response = json_decode(curl_exec($ch), true);
$status   = curl_getinfo($ch, CURLINFO_HTTP_CODE);
curl_close($ch);

if ($status >= 400) {
    throw new RuntimeException($response['error']['message']);
}
print_r($response['response']['data']);
import requests

response = requests.get(
    'https://api.dashamail.com/v2/router/messages?route_id=7&limit=2',
    headers={'Authorization': 'Bearer YOUR_API_KEY'},
)

response.raise_for_status()
print(response.json()['response']['data'])
const response = await fetch('https://api.dashamail.com/v2/router/messages?route_id=7&limit=2', {
  method: 'GET',
  headers: {
    'Authorization': 'Bearer YOUR_API_KEY',
  },
});

const payload = await response.json();
if (!response.ok) throw new Error(payload.error.message);
console.log(payload.response.data);
Ответ HTTP 200
{
  "response": {
    "msg": {
      "err_code": 0,
      "text": "OK",
      "type": "message"
    },
    "data": [
      {
        "id": 90211,
        "route_id": 7,
        "recipient": "support@mail.example.ru",
        "from_email": "ivan@example.com",
        "subject": "Не приходит счёт",
        "attachments_count": 1,
        "raw_size": 48213,
        "created_at": "2026-04-12 09:41:02",
        "expires_at": "2026-04-19 09:41:02",
        "retrieved_at": null
      }
    ]
  }
}

Одно письмо #

GET /router/messages/{message_id}

Возвращает разобранное письмо: заголовки, текстовую и HTML-версии, перечень вложений.

Параметры пути

ПараметрТипОписание
message_id обязательныйintegerИдентификатор письма.

Возможные ошибки

HTTPcodeКогда возникает
404 4 Письма с таким идентификатором нет или срок хранения истёк
curl -X GET 'https://api.dashamail.com/v2/router/messages/90211' \
  -H 'Authorization: Bearer YOUR_API_KEY'
<?php
$ch = curl_init('https://api.dashamail.com/v2/router/messages/90211');
curl_setopt_array($ch, [
    CURLOPT_RETURNTRANSFER => true,
    CURLOPT_CUSTOMREQUEST  => 'GET',
    CURLOPT_HTTPHEADER     => [
        'Authorization: Bearer YOUR_API_KEY',
    ],
]);

$response = json_decode(curl_exec($ch), true);
$status   = curl_getinfo($ch, CURLINFO_HTTP_CODE);
curl_close($ch);

if ($status >= 400) {
    throw new RuntimeException($response['error']['message']);
}
print_r($response['response']['data']);
import requests

response = requests.get(
    'https://api.dashamail.com/v2/router/messages/90211',
    headers={'Authorization': 'Bearer YOUR_API_KEY'},
)

response.raise_for_status()
print(response.json()['response']['data'])
const response = await fetch('https://api.dashamail.com/v2/router/messages/90211', {
  method: 'GET',
  headers: {
    'Authorization': 'Bearer YOUR_API_KEY',
  },
});

const payload = await response.json();
if (!response.ok) throw new Error(payload.error.message);
console.log(payload.response.data);
Ответ HTTP 200
{
  "response": {
    "msg": {
      "err_code": 0,
      "text": "OK",
      "type": "message"
    },
    "data": {
      "id": 90211,
      "route_id": 7,
      "recipient": "support@mail.example.ru",
      "sender": "ivan@example.com",
      "from_email": "ivan@example.com",
      "message_id_header": "<CAF…@mail.example.com>",
      "subject": "Не приходит счёт",
      "body_text": "Здравствуйте! Счёт по заказу 1024 так и не пришёл.",
      "body_html": "<p>Здравствуйте! Счёт по заказу 1024 так и не пришёл.</p>",
      "attachments_count": 1,
      "raw_size": 48213,
      "created_at": "2026-04-12 09:41:02",
      "expires_at": "2026-04-19 09:41:02"
    }
  }
}

Удалить письмо #

DELETE /router/messages/{message_id}

Удаляет сохранённое письмо вместе с вложениями, не дожидаясь истечения срока хранения.

Параметры пути

ПараметрТипОписание
message_id обязательныйintegerИдентификатор письма.

Возможные ошибки

HTTPcodeКогда возникает
404 4 Письма с таким идентификатором нет
401 2 Недостаточно прав
curl -X DELETE 'https://api.dashamail.com/v2/router/messages/90211' \
  -H 'Authorization: Bearer YOUR_API_KEY'
<?php
$ch = curl_init('https://api.dashamail.com/v2/router/messages/90211');
curl_setopt_array($ch, [
    CURLOPT_RETURNTRANSFER => true,
    CURLOPT_CUSTOMREQUEST  => 'DELETE',
    CURLOPT_HTTPHEADER     => [
        'Authorization: Bearer YOUR_API_KEY',
    ],
]);

$response = json_decode(curl_exec($ch), true);
$status   = curl_getinfo($ch, CURLINFO_HTTP_CODE);
curl_close($ch);

if ($status >= 400) {
    throw new RuntimeException($response['error']['message']);
}
print_r($response['response']['data']);
import requests

response = requests.delete(
    'https://api.dashamail.com/v2/router/messages/90211',
    headers={'Authorization': 'Bearer YOUR_API_KEY'},
)

response.raise_for_status()
print(response.json()['response']['data'])
const response = await fetch('https://api.dashamail.com/v2/router/messages/90211', {
  method: 'DELETE',
  headers: {
    'Authorization': 'Bearer YOUR_API_KEY',
  },
});

const payload = await response.json();
if (!response.ok) throw new Error(payload.error.message);
console.log(payload.response.data);
Ответ HTTP 204
(тело ответа пустое)

Вложение письма #

GET /router/messages/{message_id}/attachments/{attachment_id}

Возвращает вложение письма — имя файла, MIME-тип и содержимое.

Параметры пути

ПараметрТипОписание
message_id обязательныйintegerИдентификатор письма.
attachment_id обязательныйintegerИдентификатор вложения.

Возможные ошибки

HTTPcodeКогда возникает
400 400 Не указан идентификатор вложения
404 9 Вложение не найдено
curl -X GET 'https://api.dashamail.com/v2/router/messages/90211/attachments/1' \
  -H 'Authorization: Bearer YOUR_API_KEY'
<?php
$ch = curl_init('https://api.dashamail.com/v2/router/messages/90211/attachments/1');
curl_setopt_array($ch, [
    CURLOPT_RETURNTRANSFER => true,
    CURLOPT_CUSTOMREQUEST  => 'GET',
    CURLOPT_HTTPHEADER     => [
        'Authorization: Bearer YOUR_API_KEY',
    ],
]);

$response = json_decode(curl_exec($ch), true);
$status   = curl_getinfo($ch, CURLINFO_HTTP_CODE);
curl_close($ch);

if ($status >= 400) {
    throw new RuntimeException($response['error']['message']);
}
print_r($response['response']['data']);
import requests

response = requests.get(
    'https://api.dashamail.com/v2/router/messages/90211/attachments/1',
    headers={'Authorization': 'Bearer YOUR_API_KEY'},
)

response.raise_for_status()
print(response.json()['response']['data'])
const response = await fetch('https://api.dashamail.com/v2/router/messages/90211/attachments/1', {
  method: 'GET',
  headers: {
    'Authorization': 'Bearer YOUR_API_KEY',
  },
});

const payload = await response.json();
if (!response.ok) throw new Error(payload.error.message);
console.log(payload.response.data);
Ответ HTTP 200
{
  "response": {
    "msg": {
      "err_code": 0,
      "text": "OK",
      "type": "message"
    },
    "data": {
      "id": 1,
      "message_id": 90211,
      "filename": "order-1024.pdf",
      "mime_type": "application/pdf",
      "size": 44120,
      "body": "JVBERi0xLjQKJcfs…"
    }
  }
}

Журнал доставок webhook #

GET /router/deliveries

Попытки доставки писем на ваши webhook-адреса и адреса пересылки. Первое место, куда стоит смотреть, если письма до вашей системы не доходят.

Параметры строки запроса

ПараметрТипОписание
route_idintegerТолько доставки указанного маршрута.
statusstringФильтр по результату доставки.
recipientstringФильтр по адресу получателя исходного письма.
sincedatetimeНе раньше указанного момента.
untildatetimeНе позже указанного момента.
limitintegerРазмер страницы.
offsetintegerСмещение.

Возможные ошибки

HTTPcodeКогда возникает
404 4 Доставок по фильтру нет
curl -X GET 'https://api.dashamail.com/v2/router/deliveries?status=failed&limit=2' \
  -H 'Authorization: Bearer YOUR_API_KEY'
<?php
$ch = curl_init('https://api.dashamail.com/v2/router/deliveries?status=failed&limit=2');
curl_setopt_array($ch, [
    CURLOPT_RETURNTRANSFER => true,
    CURLOPT_CUSTOMREQUEST  => 'GET',
    CURLOPT_HTTPHEADER     => [
        'Authorization: Bearer YOUR_API_KEY',
    ],
]);

$response = json_decode(curl_exec($ch), true);
$status   = curl_getinfo($ch, CURLINFO_HTTP_CODE);
curl_close($ch);

if ($status >= 400) {
    throw new RuntimeException($response['error']['message']);
}
print_r($response['response']['data']);
import requests

response = requests.get(
    'https://api.dashamail.com/v2/router/deliveries?status=failed&limit=2',
    headers={'Authorization': 'Bearer YOUR_API_KEY'},
)

response.raise_for_status()
print(response.json()['response']['data'])
const response = await fetch('https://api.dashamail.com/v2/router/deliveries?status=failed&limit=2', {
  method: 'GET',
  headers: {
    'Authorization': 'Bearer YOUR_API_KEY',
  },
});

const payload = await response.json();
if (!response.ok) throw new Error(payload.error.message);
console.log(payload.response.data);
Ответ HTTP 200
{
  "response": {
    "msg": {
      "err_code": 0,
      "text": "OK",
      "type": "message"
    },
    "data": [
      {
        "id": 55120,
        "route_id": 7,
        "message_id": 90211,
        "status": "failed",
        "http_code": 502,
        "attempts": 3,
        "created_at": "2026-04-12 09:41:05"
      }
    ]
  }
}

Одна доставка #

GET /router/deliveries/{delivery_id}

Подробности попытки доставки, включая ответ вашего сервера — по нему видно, почему запрос не прошёл.

Параметры пути

ПараметрТипОписание
delivery_id обязательныйintegerИдентификатор доставки.

Возможные ошибки

HTTPcodeКогда возникает
404 4 Доставки с таким идентификатором нет
curl -X GET 'https://api.dashamail.com/v2/router/deliveries/55120' \
  -H 'Authorization: Bearer YOUR_API_KEY'
<?php
$ch = curl_init('https://api.dashamail.com/v2/router/deliveries/55120');
curl_setopt_array($ch, [
    CURLOPT_RETURNTRANSFER => true,
    CURLOPT_CUSTOMREQUEST  => 'GET',
    CURLOPT_HTTPHEADER     => [
        'Authorization: Bearer YOUR_API_KEY',
    ],
]);

$response = json_decode(curl_exec($ch), true);
$status   = curl_getinfo($ch, CURLINFO_HTTP_CODE);
curl_close($ch);

if ($status >= 400) {
    throw new RuntimeException($response['error']['message']);
}
print_r($response['response']['data']);
import requests

response = requests.get(
    'https://api.dashamail.com/v2/router/deliveries/55120',
    headers={'Authorization': 'Bearer YOUR_API_KEY'},
)

response.raise_for_status()
print(response.json()['response']['data'])
const response = await fetch('https://api.dashamail.com/v2/router/deliveries/55120', {
  method: 'GET',
  headers: {
    'Authorization': 'Bearer YOUR_API_KEY',
  },
});

const payload = await response.json();
if (!response.ok) throw new Error(payload.error.message);
console.log(payload.response.data);
Ответ HTTP 200
{
  "response": {
    "msg": {
      "err_code": 0,
      "text": "OK",
      "type": "message"
    },
    "data": {
      "id": 55120,
      "route_id": 7,
      "message_id": 90211,
      "status": "failed",
      "http_code": 502,
      "attempts": 3,
      "response_body": "502 Bad Gateway",
      "created_at": "2026-04-12 09:41:05"
    }
  }
}

Настройки обработки #

GET /router/settings

Общие настройки приёма входящей почты.

curl -X GET 'https://api.dashamail.com/v2/router/settings' \
  -H 'Authorization: Bearer YOUR_API_KEY'
<?php
$ch = curl_init('https://api.dashamail.com/v2/router/settings');
curl_setopt_array($ch, [
    CURLOPT_RETURNTRANSFER => true,
    CURLOPT_CUSTOMREQUEST  => 'GET',
    CURLOPT_HTTPHEADER     => [
        'Authorization: Bearer YOUR_API_KEY',
    ],
]);

$response = json_decode(curl_exec($ch), true);
$status   = curl_getinfo($ch, CURLINFO_HTTP_CODE);
curl_close($ch);

if ($status >= 400) {
    throw new RuntimeException($response['error']['message']);
}
print_r($response['response']['data']);
import requests

response = requests.get(
    'https://api.dashamail.com/v2/router/settings',
    headers={'Authorization': 'Bearer YOUR_API_KEY'},
)

response.raise_for_status()
print(response.json()['response']['data'])
const response = await fetch('https://api.dashamail.com/v2/router/settings', {
  method: 'GET',
  headers: {
    'Authorization': 'Bearer YOUR_API_KEY',
  },
});

const payload = await response.json();
if (!response.ok) throw new Error(payload.error.message);
console.log(payload.response.data);
Ответ HTTP 200
{
  "response": {
    "msg": {
      "err_code": 0,
      "text": "OK",
      "type": "message"
    },
    "data": {
      "pass_autoreply": 0,
      "pass_list_mail": 0
    }
  }
}

Изменить настройки #

PUT /router/settings

Задаёт, пропускать ли служебную почту к вашим маршрутам. По умолчанию автоответы и рассылочные письма отфильтровываются: это защищает от петель, когда ваш обработчик отвечает на автоответ, а тот отвечает снова.

Параметры тела запроса

ПараметрТипОписание
pass_autoreplyфлагпо умолчанию: 0Пропускать автоответы («в отпуске», «получено»).
pass_list_mailфлагпо умолчанию: 0Пропускать письма с заголовками рассылок (List-Id и подобными).

Возможные ошибки

HTTPcodeКогда возникает
401 2 Недостаточно прав
curl -X PUT 'https://api.dashamail.com/v2/router/settings' \
  -H 'Authorization: Bearer YOUR_API_KEY' \
  -H 'Content-Type: application/json' \
  -d '{
  "pass_autoreply": 1,
  "pass_list_mail": 0
}'
<?php
$ch = curl_init('https://api.dashamail.com/v2/router/settings');
curl_setopt_array($ch, [
    CURLOPT_RETURNTRANSFER => true,
    CURLOPT_CUSTOMREQUEST  => 'PUT',
    CURLOPT_HTTPHEADER     => [
        'Authorization: Bearer YOUR_API_KEY',
        'Content-Type: application/json',
    ],
    CURLOPT_POSTFIELDS     => json_encode([
            'pass_autoreply' => 1,
            'pass_list_mail' => 0,
        ], JSON_UNESCAPED_UNICODE),
]);

$response = json_decode(curl_exec($ch), true);
$status   = curl_getinfo($ch, CURLINFO_HTTP_CODE);
curl_close($ch);

if ($status >= 400) {
    throw new RuntimeException($response['error']['message']);
}
print_r($response['response']['data']);
import requests

response = requests.put(
    'https://api.dashamail.com/v2/router/settings',
    headers={'Authorization': 'Bearer YOUR_API_KEY'},
    json={
        'pass_autoreply': 1,
        'pass_list_mail': 0,
    },
)

response.raise_for_status()
print(response.json()['response']['data'])
const response = await fetch('https://api.dashamail.com/v2/router/settings', {
  method: 'PUT',
  headers: {
    'Authorization': 'Bearer YOUR_API_KEY',
    'Content-Type': 'application/json',
  },
  body: JSON.stringify({
  "pass_autoreply": 1,
  "pass_list_mail": 0
}),
});

const payload = await response.json();
if (!response.ok) throw new Error(payload.error.message);
console.log(payload.response.data);
Ответ HTTP 200
{
  "response": {
    "msg": {
      "err_code": 0,
      "text": "OK",
      "type": "message"
    },
    "data": {
      "pass_autoreply": 1,
      "pass_list_mail": 0
    }
  }
}

DashaMail хранит и защищает ваши данные на территории Российской Федерации

Подробнее...