Как обработать deliver_sm, если одновременно приходят DLR и ответы клиентов

Если в SMPP-сессии одновременно приходят отчёты о доставке (DLR) и ответы клиентов (MO), приложение должно быстро подтвердить каждый `deliver_sm`, определить тип сообщения и передать его в нужную очередь обработки. DLR связывают с исходящей SMS по идентификатору сообщения, а MO направляют в сценарий ответа клиенту. Ниже — порядок обработки, который помогает не перепутать эти события и не задерживать входящие PDU.
Как отличить DLR от ответа клиента?
Шлюз передаёт оба типа событий командой `deliver_sm`. Само название PDU не показывает, что именно пришло: отчёт о доставке или текст от абонента. Приложение должно проверить признаки сообщения, включая `esm_class`, а затем разобрать содержимое PDU.
У DLR обычно есть статус доставки и идентификатор исходного сообщения. Формат текстового отчёта зависит от шлюза, поэтому разбор следует настраивать по спецификации поставщика и проверять на реальных примерах. MO обычно содержит адрес отправителя и текст, который ввёл клиент.
Не определяйте тип события только по тексту тела: формат DLR может различаться. Сохраняйте исходные поля PDU вместе с результатом классификации, чтобы при ошибке разбора можно было проверить сообщение.
В каком порядке обрабатывать входящий deliver_sm?
Принимайте PDU в одном сетевом обработчике, а разбор и бизнес-логику передавайте отдельным задачам. Сначала проверьте обязательные поля и сохраните событие в надёжную очередь. Затем отправьте `deliver_sm_resp` с подходящим статусом. Такой порядок не заставляет шлюз ждать, пока приложение обновит заказ или подготовит ответ клиенту.
- Прочитайте `sequence_number` и поля PDU, затем зафиксируйте событие в очереди или хранилище.
- Определите тип: DLR или MO. Если формат неполный или неизвестный, сохраните событие для разбора и отметьте его как неопределённое.
- Отправьте `deliver_sm_resp`, чтобы подтвердить приём PDU.
- Передайте DLR обработчику статусов, а MO — логике входящих сообщений.
- Запишите результат обработки и причину ошибки, если задача завершилась неудачно.
Сетевой обработчик должен отвечать быстро, а не выполнять длительные операции. Например, отправку ответа клиенту или обновление заказа лучше запускать после подтверждения PDU. Если приложение подтвердит сообщение до сохранения, сбой может привести к потере события; если будет долго ждать бизнес-обработку, шлюз может повторить передачу или разорвать сессию.
Как связать DLR с исходящей SMS и не обработать его повторно?
Сохраняйте идентификатор, который шлюз возвращает для исходящей SMS, и используйте его для поиска записи при поступлении DLR. Учитывайте, что формат идентификатора в отчёте может отличаться от формата в ответе на отправку. Правило нормализации согласуйте с поставщиком и проверьте на нескольких тестовых сообщениях.
Шлюз может повторно доставить событие, если не получил подтверждение или произошёл сбой соединения. Поэтому обработчик должен выдерживать повтор: проверять уникальность события и не запускать одно и то же действие повторно. Для DLR полезно отдельно хранить исходный статус и время приёма, а для MO — отправителя, текст и идентификатор входящего события.
Практический разбор ключей и повторных отчётов приведён в материале о дедупликации входящих DLR в SMPP-шлюзе. Если параллельная обработка увеличивает задержку на соединении, проверьте также метрики здоровья SMPP-сессии.
Что проверить при одновременном потоке DLR и MO?
Создайте два независимых маршрута после первичного приёма. Очередь DLR обновляет статус исходящей SMS, а очередь MO запускает сценарий ответа. Так медленная операция в одном маршруте не блокирует другой. Если порядок событий важен для конкретного номера или диалога, сохраняйте последовательность внутри этой группы, не останавливая обработку всех остальных сообщений.
Проверьте сценарий на тестовой сессии: отправьте SMS, получите DLR, затем передайте MO; после этого повторите одно из событий и убедитесь, что система не выполняет действие дважды. Во время теста фиксируйте время получения PDU, время подтверждения и время завершения обработки. Эти отметки помогут найти задержку между приёмом и бизнес-логикой.
Типичные ошибки
- Приложение считает каждый `deliver_sm` отчётом о доставке и теряет ответы клиентов.
- Обработчик ждёт завершения бизнес-операции и только потом отправляет `deliver_sm_resp`.
- Повторно доставленный DLR запускает повторное уведомление или меняет уже обновлённый статус.
- Приложение не сохраняет исходный PDU и не может разобрать сообщение, формат которого отличается от ожидаемого.
- Один медленный обработчик блокирует приём всех событий в SMPP-сессии.
Начните с журналирования каждого `deliver_sm`, раздельной классификации DLR и MO и сохранения события до подтверждения. Затем проверьте повторную доставку и параллельную нагрузку: после этих тестов будет видно, где нужна настройка очереди или логики SMPP-клиента.


