|
![]() |
#1 |
Administrator
|
"В лоб" нет ответа. Классический аналог задачи - в транзакцию запихнуть отправку на электронную почту письма. При этом на вопрос "откатываем ли транзакцию, если почтовый сервер стал недоступен?" обычно отвечают, что "ну мы же не можем останавливать работу системы из-за того, что где-то какой-то сервер, которым мы не управляем - стал недоступен"
Поэтому ответ здесь зависит от ситуации. Что вероятнее может случиться - ошибка и откат транзакции или ошибка при веб-запросе? Вариант 1. Ошибка и откат транзакции. В этом случае: 1. Делаем проверку на то, что ошибки не будет. Для этого - запускаем на исполнение этот же код, но в конце вызываем ttsabort. Все выборки на обновление делаем с пессимистической блокировкой для гарантии исключения конфликтов совместного обновления. Если код дошёл до конца - то вызываем ttsabort. 2. (Транзакция не открыта). Вызываем веб-запрос. Если вернулась ошибка - не вызываем код с транзакцией. Если ошибки нет - то вызываем код с транзакцией, пессимистическими блокировками и уже делаем ttscommit; Вариант 2. Ошибка при веб-запросе. Здесь надо "на берегу" договориться - останавливаем ли мы работу системы до тех пор, пока веб-запрос не перестанет возвращать ошибки (пример с почтовым сервером) или идем дальше, а с веб-запросом будем разбираться отдельно? Если останавливаем - то тогда отрабатываем по варианту 1. Если не останавливаем, то тогда сначала вызываем код в транзакции и только после его успешной отработки - вызываем веб-запрос. Если веб-запрос выдает ошибки - то эти ошибки логируем и готовим какой-нибудь пакетник по массовой обработки накопившихся ошибок (пример - массовая рассылка почты по тем письмам, которые не были отправлены). Ну собственно - здесь основной вопрос и есть - что делать системе, если по той или иной причине не получается отработать веб-запрос
__________________
Возможно сделать все. Вопрос времени Последний раз редактировалось sukhanchik; 06.06.2022 в 13:23. |
|
![]() |
#2 |
Участник
|
Добрый день.
Транзакцию можно обернуть внутри иного user connection'a. |
|
![]() |
#3 |
Участник
|
X++: // to write your log from inside of another transaction static public void insertExtEventLogInSeparateConnection(RefRecId _lineRecId, str _guid, str _logSource, str _logStr) { ExtEventLog log; UserConnection connection; int ttsLevel = appl.ttsLevel(); //here you can check if you are inside of a transaction str errMsg = strFmt("Cannot add event log '%1:%2:%3'", _guid, _logSource, _logStr); // let's create a separate connection try { connection = new UserConnection(); connection.ttsbegin(); log.setConnection(connection); log.InstructionDocLineRecId = _lineRecId; log.TaskGUID = _guid; log.LogStr = _logStr; log.LogSource = _logSource; log.doInsert(); connection.ttscommit(); } catch { throw error(errMsg); } finally { if(connection) { connection.finalize(); } } }
__________________
Felix nihil admirari |
|
|
Опции темы | Поиск в этой теме |
Опции просмотра | |
|