|
Заблокировать выполнение процедуры на сервере одновременно двумя пользователями | ☑ | ||
---|---|---|---|---|
0
D_Sergeevich
09.07.13
✎
13:22
|
День добрый.
Есть обработка которая получает файл через веб сервис, метод получения вызывается в процедуре на сервере. Как заблокировать эту процедуру на время ее выполнения. т.е. чтобы пользователь не мог ее вызвать когда она отрабатывает для другого пользователя. &НаКлиенте Процедура Сформировать(Команда) data_start = Строка(Формат(Объект.НачалоПериода,"ДФ=dd.MM.yyyy")); data_end = Строка(Формат(Объект.КонецПериода,"ДФ=dd.MM.yyyy")); acc_source = Строка(Объект.Счет); name_source = "Данные - выписка"; //Проверка заполнения полей Если data_start = '00010101' ИЛИ data_end = '00010101' ИЛИ acc_source = "" Тогда Предупреждение("Пожалуйста заполните все поля!"); Иначе ПодключениеКВебСервису(data_start, data_end, acc_source, name_source) КонецЕсли; КонецПроцедуры //Подключени к веб сервису и вызов методов &НаСервере Процедура ПодключениеКВебСервису(data_start, data_end, acc_source, name_source) WSОпределение = Новый WSОпределения("C:/Service.wsdl"); WSПрокси = Новый WSПрокси(WSОпределение,"http://tempuri.org/","Service1","Service1"); WSПрокси.Пользователь = "*****"; WSПрокси.Пароль = "*****"; Данные = WSПрокси.GetDataWcf(name_source, acc_source, data_start, data_end); ДвоичныеДанные = WSПрокси.getFile(0); ДвоичныеДанные.Записать("C:\\test.xml"); КонецПроцедуры |
|||
1
Поросенок Петр
09.07.13
✎
13:25
|
А что случается если не "заблокировать" ?
|
|||
2
D_Sergeevich
09.07.13
✎
13:28
|
(1) Зависает соединение с веб сервисом. Получение файла идет около 30 сек. и на это время нужно блокировать выполнение другим пользователям.
|
|||
3
Maxus43
09.07.13
✎
13:29
|
ну взведи константу например, "Нелья". и проверяй... потом сбросишь
|
|||
4
Поросенок Петр
09.07.13
✎
13:31
|
Могу ошибаться, надо копать в сторону Таймаут.
Новый WSПрокси(<Определение>, <URIПространстваИменСервиса>, <ИмяСервиса>, <ИмяТочкиПодключения>, ***<Таймаут>***) |
|||
5
D_Sergeevich
09.07.13
✎
13:36
|
(4) Новый WSПрокси(<Определение>, <URIПространстваИменСервиса>, <ИмяСервиса>, <ИмяТочкиПодключения>) Тут нету таймаута.
(3)Ну вот я как раз так и думал, завел константу типа булево "Блокировка", но не соображу где ее устанавливать и где проверять |
|||
6
Fragster
гуру
09.07.13
✎
13:37
|
установка исключительной блокировки на константу
|
|||
7
Fragster
гуру
09.07.13
✎
13:37
|
см, как сделана синхронизация в v8: Многопоточный тест производительности 1с
|
|||
8
Maxus43
09.07.13
✎
13:39
|
(5) тут
&НаСервере Процедура ПодключениеКВебСервису(data_start, data_end, acc_source, name_source) сначала проверять, если Истина то возврат, иначе устанавливай и выполняй дальше. в конце процедуры снимай |
|||
9
Maxus43
09.07.13
✎
13:40
|
ну и предусмотреть что свалится с ошибкой может, а константу надо таки сбросить всё равно
|
|||
10
D_Sergeevich
09.07.13
✎
13:45
|
(9) ага, благодарю!
А как проверить свалилась она с ошибкой или нет, чтоб в случае чего сбросить константу |
|||
11
Maxus43
09.07.13
✎
13:46
|
вобще для этого используют ПОПЫТКА ИСКЛЮЧЕНИЕ, я хз тока ошибку вебсервиса поймёт ли
|
|||
12
Fragster
гуру
09.07.13
✎
13:46
|
не надо менять значение константы, надо выставить на нее исключительную блокировку - тогда другой сеанс не сможет выставить на нее свою блокировку, пока первый не снимет свою. профит!
|
|||
13
Maxus43
09.07.13
✎
13:47
|
(12) ты там вот в (7) найдёш сходу "см, как сделана синхронизация" если первый раз туда попадёшь?)
|
|||
14
Maxus43
09.07.13
✎
13:48
|
(12) игра блокировками или значением - разница принципиальная какая кстати?
|
|||
15
Fragster
гуру
09.07.13
✎
13:51
|
(13) глобальный поиск "Синхронизация" :)
(14) при отвале не надо думать, что rphost упадет и константа останется не в том состоянии. |
|||
16
Очкарик
09.07.13
✎
13:51
|
(0) Установи исключительную блокировку на Объект в момент работы процедуры
|
|||
17
Maxus43
09.07.13
✎
13:55
|
(15) согласен, понадёжней будет
|
|||
18
vde69
09.07.13
✎
13:59
|
заведи справочник, один элемент - это твоя процедура, далее запрос "для изменения"
|
|||
19
Fragster
гуру
09.07.13
✎
14:03
|
(18) кстати да, если режим управления блокировками - автоматический - то ДЛЯ ИЗМЕНЕНИЯ вместо БлокировкаДанных надо использовать...
|
|||
20
D_Sergeevich
09.07.13
✎
14:04
|
Всем спасибо буду пробовать. Окончательный результат выложу, думаю многим пригодится
(19) режим блокировки в конфе у меня управляемый |
|||
21
D_Sergeevich
09.07.13
✎
14:59
|
Нашел тот кусок кода из сылки
|
|||
22
D_Sergeevich
09.07.13
✎
15:00
|
Но почему то оно не блокирует и второй пользователь тоже может ставить Заблокировать()
Блокировка = Новый БлокировкаДанных; ЭлементБлокировки = Блокировка.Добавить("Константа.Синхронизация"); ЭлементБлокировки.Режим = РежимБлокировкиДанных.Разделяемый; Блокировка.Заблокировать(); |
|||
23
Fragster
гуру
09.07.13
✎
15:06
|
Исключительный
|
|||
24
D_Sergeevich
09.07.13
✎
15:13
|
(23) Блокировка = Новый БлокировкаДанных;
ЭлементБлокировки = Блокировка.Добавить("Константа.Блокировка"); ЭлементБлокировки.Режим = РежимБлокировкиДанных.Исключительный; Блокировка.Заблокировать(); Тоже самое ( |
|||
25
D_Sergeevich
09.07.13
✎
15:19
|
Правильно я делаю?
&НаСервере Процедура ПодключениеКВебСервису(data_start, data_end, acc_source, name_source) Блокировка = Новый БлокировкаДанных; ЭлементБлокировки = Блокировка.Добавить("Константа.Блокировка"); ЭлементБлокировки.Режим = РежимБлокировкиДанных.Исключительный; Блокировка.Заблокировать(); WSОпределение = Новый WSОпределения("C:/Service.wsdl"); WSПрокси = Новый WSПрокси(WSОпределение,"http://tempuri.org/","Service1","Service1"); WSПрокси.Пользователь = "***"; WSПрокси.Пароль = "***"; Данные = WSПрокси.GetDataWcf(name_source, acc_source, data_start, data_end); ДвоичныеДанные = WSПрокси.getFile(0); ДвоичныеДанные.Записать("C:\\test.xml_enc"); КонецПроцедуры |
|||
26
kosts
09.07.13
✎
15:19
|
Попробуй справочник заблокировать
|
|||
27
D_Sergeevich
09.07.13
✎
15:33
|
А когда снимается блокировка? когда будит выход из процедуры?
|
|||
28
Fragster
гуру
09.07.13
✎
15:42
|
(24) транзакцию-то добавь
|
|||
29
D_Sergeevich
09.07.13
✎
16:46
|
(28) При попытки вызвать метод вторым пользователем возникает Ошибка (Конфликт блокировок при выполнении транзакции. Превышено максимальное время ожидания предоставления блокировки)
&НаСервере Процедура ПодключениеКВебСервису(data_start, data_end, acc_source, name_source) НачатьТранзакцию(РежимУправленияБлокировкойДанных.Управляемый); Блокировка = Новый БлокировкаДанных; ЭлементБлокировки = Блокировка.Добавить("Константа.Блокировка"); ЭлементБлокировки.Режим = РежимБлокировкиДанных.Исключительный; Блокировка.Заблокировать(); WSОпределение = Новый WSОпределения("C:/Service.wsdl"); WSПрокси = Новый WSПрокси(WSОпределение,"http://tempuri.org/","Service1","Service1"); WSПрокси.Пользователь = "***"; WSПрокси.Пароль = "***"; Данные = WSПрокси.GetDataWcf(name_source, acc_source, data_start, data_end); ДвоичныеДанные = WSПрокси.getFile(0); ДвоичныеДанные.Записать("C:\\test.xml_enc"); ЗафиксироватьТранзакцию(); КонецПроцедуры |
|||
30
Fragster
гуру
09.07.13
✎
16:51
|
(29) так и задумано - чтобы твой второй не ждал бесконечно. если надо бесконечно - то можно (а) сииииильно увеличить время ожидания блокировки, например с помощью УстановитьВремяОжиданияБлокировкиДанных() (б) пытаться установить блокировку в попытке в цикле (там надо вместе с НачатьТранзакцию(), если что)
|
|||
31
D_Sergeevich
09.07.13
✎
16:56
|
(30) А нельзя сделать так чтобы выводилось предупреждение? типа (В данный момент идет получение данных для такого то пользователя, попробуйте повторить попытку через ~30 сек.)
|
|||
32
Fragster
гуру
09.07.13
✎
17:06
|
(31) кто я такой, чтобы запрещать так сделать?
|
|||
33
D_Sergeevich
09.07.13
✎
17:18
|
(32) )) Ну вообще то я имел введу как так сделать?
|
|||
34
Fragster
гуру
09.07.13
✎
17:23
|
Попытка ... исключение Сообщение/возврат ошибки КонецПопытки
|
Форум | Правила | Описание | Объявления | Секции | Поиск | Книга знаний | Вики-миста |