Имя: Пароль:
1C
 
Как обработать ошибку проведения, если активна транзакция?
0 DTX 4th
 
27.10.20
14:28
НачатьТранзакцию();

Для Каждого Об Из Доки Цикл
  Попытка
    Об.Провести();  //вот тут иногда может быть ошибка, которая рушит всю транзакцию
  Исключение
    Об.Записать();
  КонецПопытки;
КонецЦикла;

ЗафиксироватьТранзакцию();

Понимаю, что вопрос поднимался уже не раз. Когда уже придумают удобное решение?
Если только программно проверять документ перед проведение? Это же ужасно, не?
1 vicof
 
27.10.20
14:29
Что значит "обработать"?
2 ДенисЧ
 
27.10.20
14:29
Переписать проведение так, чтобы оно не вызывало исключения
3 vicof
 
27.10.20
14:34
(2) Не сможет. Остатки в минус уйдут)
4 acht
 
27.10.20
14:36
НачатьТранзакцию();
Попытка
    Для Каждого Об Из Доки Цикл
        Об.Записать();
    КонецЦикла;
    ЗафиксироватьТранзакцию();
Исключение
    ОтменитьТранзакцию();
    ВызватьИсключение
КонецПопытки;

НачатьТранзакцию();
Попытка
    Для Каждого Об Из Доки Цикл
        Об.Провести();
    КонецЦикла;
    ЗафиксироватьТранзакцию();
Исключение
    ОтменитьТранзакцию();
    ВызватьИсключение
КонецПопытки;
5 ДенисЧ
 
27.10.20
14:37
(3) А зачем вызывать исключение, если остатка не хватает?
6 vicof
 
27.10.20
14:38
(5) Эмм. Ну типа отказ = истина в обработке проведения будет.
7 d4rkmesa
 
гуру
27.10.20
14:39
8 DTX 4th
 
27.10.20
14:41
(4) Из-за одного документа может не провестись весь хвост массива
Наверн, логично делать запись в транзакции, а проведение уже после. Спасибо за идею
9 ДенисЧ
 
27.10.20
14:48
(6) Эммм. От этого будет исключение? Давно такие новшества?
10 acht
 
27.10.20
14:49
(9) От этого будет исключение, да. Начиная с 8.0
11 rozer76
 
27.10.20
14:50
https://its.1c.ru/db/metod8dev#content:2313:hdoc

Если восстановимая ошибка базы данных произошла в процессе выполнения транзакции, то, вне зависимости от того, было исключение, вызванное этой ошибкой, перехвачено и обработано или нет, транзакция уже не может быть продолжена или зафиксирована. Единственная операция с базой данных, которую можно произвести в такой ситуации - это отмена транзакции.


>>а проведение уже после
как вариант уже без транзакции и писать куда-то для "разбора полетов"
12 fisher
 
27.10.20
14:57
(0) А нафига у тебя вообще в транзакции?
Документы настолько "легкие", что дает эффект ускорения?
(8) А у тебя допустимо пропускать непроведенные? Тогда можно просто если в пачке произошла ошибка, делать откат транзакции и запускать эту пачку повторно на проведение, но уже без транзакции.
13 DTX 4th
 
27.10.20
15:01
(12) >А нафига у тебя вообще в транзакции?
Чтобы этот кусок кода мог выполняться только в одном сеансе одновременно

Транзакция нужна, чтобы блокировку держать (мьютекс)
Ну и откатывать транзакцию с сотней документов из-за одного документа как-то не оч..
14 МихаилМ
 
27.10.20
15:03
а  7.7 поддерживала вложенные транзакции...
15 H A D G E H O G s
 
27.10.20
15:03
Жесть какая

Для Каждого Об Из Доки Цикл
  Попытка
    Об.Провести();  //вот тут иногда может быть ошибка, которая рушит всю транзакцию
  Исключение
ЗафиксироватьТранзакцию();
НачатьТранзацию();
    Об.Записать();
  КонецПопытки;
КонецЦикла;

ЗафиксироватьТранзакцию();
16 H A D G E H O G s
 
27.10.20
15:05
(15) Епстественно, это рушит основопологающий механизмь транзакций, но в свете подарка от 1С "в данной транзакции уже происходили ошибки" как то похер
17 H A D G E H O G s
 
27.10.20
15:06
(9) Добро пожаловать в новый чудный мир.
18 H A D G E H O G s
 
27.10.20
15:06
(12) Да, это дает офигенные ускорения.
19 fisher
 
27.10.20
15:06
(13) Суровые у тебя мьютексы :)
20 ДенисЧ
 
27.10.20
15:07
(13) А не пробовал мутексы по-нормальному делать? А не держать всю базу?
21 H A D G E H O G s
 
27.10.20
15:08
(19) У него вообще сурово. Он как будто откудато вылез и осваивает этот дивный мир. Ну хоть не 15 лет жил и не знал про генерацию исключения при отказе. Уже неплохо.
22 ДенисЧ
 
27.10.20
15:08
(14) А вложенные исключение?
23 fisher
 
27.10.20
15:09
Раз речь за мьютексы, значит ты параллелишь. Верно?
И в чем проблема распараллелить так, чтобы задачи не пересекались?
24 H A D G E H O G s
 
27.10.20
15:10
(20) Ну может надо человеку. Но меня не покидает ощущения велосипедостроительства.

Автор посмотри в сторону
Об.ДополнительныеПараметры.Вставить("ЭтоФлагОтключенияВсехПроверокОтЕвгения",Истина);
25 TormozIT
 
гуру
27.10.20
15:12
26 fisher
 
27.10.20
15:13
(13) > Ну и откатывать транзакцию с сотней документов из-за одного документа как-то не оч.
Если ориентироваться на оптимистический сценарий, то норм. А если это у тебя нормальная ситуация, тогда скорее всего архитектуру поправить надо.
27 МихаилМ
 
27.10.20
15:15
(22) вложенные исключения есть и в 77 и 8
28 ДенисЧ
 
27.10.20
15:15
(27) Мы видим на примере этой темы насколько они "есть"
29 fisher
 
27.10.20
15:19
(14) Да ладно? Что, можно было откатить вложенную транзакцию с успешным завершением внешней?
(28) Вложенные транзакции и исключения СУБД - это козырная карта. Она перебивает :) А так - есть.
30 DTX 4th
 
27.10.20
15:43
(7) Блин, нафига я это читал.. По делу ничего нет

(19) Самые обычные. Из запасных вариантов - только извращаться с регл. заданиями

(20) Какую всю базу? Как лучше мьютекс сделать? Тему я уже создавал
Самый простой способ создать мьютекс?

(23) Нет. Код может выполняться либо регл. заданием, либо по кнопке. Нужно, чтобы эти два сценария не пересеклись

(15) После исключения он даст зафиксировать транзацию?
Выглядит дико, плюс вариант не мой, т.к. не могу транзакцию разрывать

(24) Если так сделать, то это и будет велосипедостроительством
31 TormozIT
 
гуру
27.10.20
15:50
Если скорость не критична, то для проведения каждого документа запускаешь фоновое задание, которое в транзакции проводит документ и всегда откатывает транзакцию и возвращает результат в основной поток. Если фоновому удалось успешно провести, то в основном потоке проводим документ. Понятно что есть ненулевая вероятность получить плавающую ошибку проведения, если в базе работают другие сеансы, но эта вероятность будет значительно ниже чем в других схемах.
32 ДенисЧ
 
27.10.20
15:57
(31) А можно последовательно на каждый запустить пять фоновых... А лучше 10. Для гарантии.
33 fisher
 
27.10.20
16:20
(30) Можно по кнопке запускать фоновое от того же регламентного. Там в регламенте можно настроить, чтобы задания не пересекались. Типа если такое же уже выполняется, то регламент будет ждать. А по кнопке можно проверять - если регламент уже пашет, то так пользователю и говорить.
34 H A D G E H O G s
 
27.10.20
16:22
(30) "Если так сделать, то это и будет велосипедостроительством"
нет. Исключения, даже и обрабатываемые - это жопа. Ты это поймешь, когда будешь что-то отлаживать "по ошибке".
35 H A D G E H O G s
 
27.10.20
16:22
(30) " После исключения он даст зафиксировать транзацию?
Выглядит дико, плюс вариант не мой, т.к. не могу транзакцию разрывать "

Даст
36 fisher
 
27.10.20
16:22
Есть еще примитивнее способ внеочередного запуска регламента по кнопке. Тупо его "передернуть" (деактивировать-активировать).
37 fisher
 
27.10.20
16:25
(35) При ошибке вложенной транзакции зафиксировать внешнюю уже не даст. Об этом и речь. Попытки/исключения не помогут.
38 Rovan
 
гуру
27.10.20
16:47
(0) Записать документы в транзакции,  проводить потом уже без нее
39 DTX 4th
 
27.10.20
17:14
(35) (37) Так даст или нет?)

(38) Я пока на этом в (8) и остановился, но такой вариант не всегда может быть уместен