Использование предложения "ДЛЯ ИЗМЕНЕНИЯ" в языке запросов

Предложение ДЛЯ ИЗМЕНЕНИЯ позволяет заблаговременно заблокировать некоторые данные (которые могут читаться транзакцией другого соединения) уже при считывании, чтобы исключить взаимные блокировки при записи. ДЛЯ ИЗМЕНЕНИЯ дает возможность указать в запросе таблицы, считываемые данные которых предполагается изменять. В этом случае другое соединение будет ожидать освобождения этих данных уже в момент считывания внутри транзакции, т.е. не сможет прочесть заблокированные данные до тех пор, пока не будет завершена транзакция, наложившая блокировку. Блокировка от изменения данных считываемых в транзакции выполняется независимо от предложения ДЛЯ ИЗМЕНЕНИЯ. Это значит, что если внутри какой-либо транзакции считаны некоторые данные, то из другого соединения эти данные не могут быть изменены до тех пор, пока блокировка не будет снята. Если запрос выполняется вне транзакции, то в нем могут быть считаны и заблокированные данные.

Блокировки устанавливаются в момент выполнения запроса, сбрасываются же при окончании транзакции. В случае если запрос выполняется вне транзакции предложение ДЛЯ ИЗМЕНЕНИЯ игнорируется.

В случае если после предложения ДЛЯ ИЗМЕНЕНИЯ отсутствуют имена таблиц, блокироваться будут считанные данные из всех таблиц, задействованных в запросе. В случае указания конкретных таблиц будут блокироваться только данные из перечисленных таблиц. Для блокировки можно указывать только таблицы верхнего уровня (т.е. не табличные части), участвующие в запросе. Должны приводиться именно имена таблиц, а не их псевдонимы, определенные в запросе. В случае указания виртуальной таблицы будут блокированы данные из всех таблиц, задействованных в виртуальной таблице. При указании виртуальной таблицы следует записывать ее имя без параметров.

Пример использования предложения ДЛЯ ИЗМЕНЕНИЯ можно посмотреть в типовой конфигурации "Управление торговлей" в модуле документа РеализацияТоваров, в функции СформироватьЗапросПоШапке(Режим), которая вызывается из обработчика проведения документа. В этой функции, в случае оперативного проведения выполняется запрос, в котором накладывается блокировка на регистр остатков:

Копировать в буфер обмена
ВЫБРАТЬ 
   Док.Дата, 
   Док.Ссылка, 
   Док.ВидОперации, 
   Док.Организация, 
   Док.ОтражатьВРегламентированномУчете, 
   Док.ОтражатьВУправленческомУчете, 
   Док.ПодразделениеКомпании, 
   Док.Контрагент, 
   Док.ДоговорВзаиморасчетов,
   Док.СкладКомпании, 
   Док.Сделка,
   Док.Сделка.ВидОперации КАК ВидЗаказаПокупателя,
   Док.КурсДокумента, 
   Док.КратностьДокумента, 
   Док.ВалютаДокумента, 
   Док.СуммаДокумента, 
   Док.КурсВзаиморасчетов,
   Док.КратностьВзаиморасчетов,
   Док.СкладКомпании.Розничный КАК СкладКомпанииРозничный,
   Док.ДоговорВзаиморасчетов.ВалютаВзаиморасчетов КАК ВалютаВзаиморасчетов,
   Док.ДоговорВзаиморасчетов.ВедениеВзаиморасчетов КАК ВедениеВзаиморасчетов,
   Док.ДоговорВзаиморасчетов.КонтролироватьЧислоДнейЗадолженности 
       КАК КонтролироватьЧислоДнейЗадолженности,
   Док.ДоговорВзаиморасчетов.ДопустимоеЧислоДнейЗадолженности 
       КАК ДопустимоеЧислоДнейЗадолженности,
   Док.ДоговорВзаиморасчетов.КонтролироватьСуммуЗадолженности 
       КАК КонтролироватьСуммуЗадолженности,
   Док.ДоговорВзаиморасчетов.ДопустимаяСуммаЗадолженности 
       КАК ДопустимаяСуммаЗадолженности,
   Док.ДоговорВзаиморасчетов.ПроцентПредоплаты КАК ПроцентПредоплаты,
   Док.УчитыватьНДС,
   Док.УчитыватьНП,
   Док.СуммаВключаетНДС,
   Док.СуммаВключаетНП,
   Константы.ВалютаУправленческогоУчетаКомпании КАК ВалютаУправленческогоУчета,
   КурсыВалютСрезПоследних.Курс КАК КурсВалютыУпрУчета,
   КурсыВалютСрезПоследних.Кратность КАК КратностьВалютыУпрУчета,
   ВзаиморасчетыПоДоговору.СуммаВалОстаток КАК СуммаВалОстатокПоДоговору,
   ВзаиморасчетыПоСделке.СуммаВалОстаток КАК СуммаВалОстатокПоСделке,
   ПерваяСделка.ДатаПервойСделки,
   СуммыЗаказов.СуммаЗаказаОборот,
   СуммыЗаказов.СуммаОплатыОборот
ИЗ 
   Документ.РеализацияТоваров Док,
   Константы 
      ЛЕВОЕ СОЕДИНЕНИЕ РегистрСведений.КурсыВалют.СрезПоследних(&ДатаДокумента,) 
            КАК КурсыВалютСрезПоследних
      ПО Константы.ВалютаУправленческогоУчетаКомпании = КурсыВалютСрезПоследних.Валюта
 
ЛЕВОЕ СОЕДИНЕНИЕ // Для контроля суммы задолженности по договору 
                 // (ведение взаиморасчетов - любое) и числа дней задолженности по договору 
                 // (ведение взаиморасчетов - по расчетным документам)
   РегистрНакопления.КонтрагентыВзаиморасчетыКомпании.Остатки(, 
             ДоговорВзаиморасчетов = &ДоговорВзаиморасчетов) 
      КАК ВзаиморасчетыПоДоговору
   ПО Истина
 
ЛЕВОЕ СОЕДИНЕНИЕ 
   (ВЫБРАТЬ // Выбирает даты самых ранних сделок по договорам, указанным в т.ч. 
        МИНИМУМ(Сделка.Дата) КАК ДатаПервойСделки,
        ДоговорВзаиморасчетов
    ИЗ РегистрНакопления.КонтрагентыВзаиморасчетыКомпании.Остатки(, 
         ДоговорВзаиморасчетов = &ДоговорВзаиморасчетов)
    ГДЕ СуммаВалОстаток > 0 // Дебиторская задолженность больше 0
        И ДоговорВзаиморасчетов.ВедениеВзаиморасчетов = &ПоРасчетнымДокументам
        И ДоговорВзаиморасчетов.КонтролироватьЧислоДнейЗадолженности
    СГРУППИРОВАТЬ ПО ДоговорВзаиморасчетов) КАК ПерваяСделка
   ПО Истина
 
ЛЕВОЕ СОЕДИНЕНИЕ // Для контроля суммы задолженности по расчетному документу 
                 //(ведение взаиморасчетов - по расчетным документам)
   РегистрНакопления.КонтрагентыВзаиморасчетыКомпании.Остатки(,
   ДоговорВзаиморасчетов = &ДоговорВзаиморасчетов
   И Сделка = &Сделка
   ) КАК ВзаиморасчетыПоСделке
   ПО Истина
 
ЛЕВОЕ СОЕДИНЕНИЕ 
   РегистрНакопления.СуммыЗаказов.Обороты(,,, Заказ = &Сделка) КАК СуммыЗаказов
   ПО Истина
ГДЕ 
   Док.Ссылка = &ДокументСсылка
ДЛЯ ИЗМЕНЕНИЯ РегистрНакопления.КонтрагентыВзаиморасчетыКомпании.Остатки 
                           // Блокирующие чтение таблицы остатков регистра для разрешения 
                           // коллизий многопользовательской работы