РК_ЗагрузкаОстатков 1.3.1.57: документы ввода и понятные ошибки подключения.

Создание ВводОстатковТоваров по сопоставленным строкам; перехват ошибок на форме;
сообщение про флажок «Активно» при рабочих вызовах Transfer API.

Co-authored-by: Cursor <cursoragent@cursor.com>
This commit is contained in:
mihailkudravcev
2026-08-12 15:00:49 +03:00
parent 95c6315feb
commit 63f453a8b1
8 changed files with 520 additions and 7 deletions
@@ -113,10 +113,236 @@
КонецФункции
// Создание документов ВводОстатковТоваров по сопоставленным строкам (1 документ на склад).
// Себестоимость не заполняется (нет данных в API) — только оперативный учёт количества.
//
// Параметры:
// РежимТест - Булево - только подсчёт без записи
//
// Возвращаемое значение:
// Структура - СозданоДокументов, УдаленоДокументов, СтрокВДокументах, Пропущено, Ошибок, ТекстТега
//
Функция СоздатьДокументыВводаОстатков(РежимТест = Истина) Экспорт
Результат = Новый Структура;
Результат.Вставить("СозданоДокументов", 0);
Результат.Вставить("УдаленоДокументов", 0);
Результат.Вставить("СтрокВДокументах", 0);
Результат.Вставить("Пропущено", 0);
Результат.Вставить("Ошибок", 0);
Результат.Вставить("ТекстТега", "");
Если Не ЗначениеЗаполнено(Организация) Тогда
ВызватьИсключение "Укажите организацию для документов ввода остатков";
КонецЕсли;
Если Не ЗначениеЗаполнено(ДатаДокументовВвода) Тогда
ВызватьИсключение "Укажите дату документов ввода";
КонецЕсли;
ТекстТега = ТегКомментарияДокументов();
Результат.ТекстТега = ТекстТега;
СтрокиПоСкладу = СгруппироватьСопоставленныеСтрокиПоСкладу();
Если СтрокиПоСкладу.Количество() = 0 Тогда
Возврат Результат;
КонецЕсли;
Если ПерезаписатьДокументы И Не РежимТест Тогда
Результат.УдаленоДокументов = УдалитьПрежниеДокументыВолны(ТекстТега);
КонецЕсли;
Для Каждого ЭлементСклада Из СтрокиПоСкладу Цикл
СкладДок = ЭлементСклада.Ключ;
СтрокиСклада = ЭлементСклада.Значение;
Если СтрокиСклада.Количество() = 0 Тогда
Продолжить;
КонецЕсли;
Попытка
Если РежимТест Тогда
Результат.СозданоДокументов = Результат.СозданоДокументов + 1;
Результат.СтрокВДокументах = Результат.СтрокВДокументах + СтрокиСклада.Количество();
Продолжить;
КонецЕсли;
Док = СоздатьДокументПоСкладу(СкладДок, СтрокиСклада, ТекстТега);
Если ЗначениеЗаполнено(Док) Тогда
Результат.СозданоДокументов = Результат.СозданоДокументов + 1;
Результат.СтрокВДокументах = Результат.СтрокВДокументах + Док.Товары.Количество();
Для Каждого СтрТ Из СтрокиСклада Цикл
СтрТ.ДокументВвода = Док.Ссылка;
СтрТ.ЗагруженоВДокумент = Истина;
КонецЦикла;
КонецЕсли;
Исключение
Результат.Ошибок = Результат.Ошибок + 1;
КонецПопытки;
КонецЦикла;
Возврат Результат;
КонецФункции
#КонецОбласти
#Область СлужебныеПроцедурыИФункции
Функция ТегКомментарияДокументов()
Суффикс = Формат(ДатаДокументовВвода, "ДФ=yyyyMMdd");
Если ПустаяСтрока(Суффикс) Тогда
Суффикс = Формат(ДатаОстатков, "ДФ=yyyyMMdd");
КонецЕсли;
Возврат "РК_ПереносОстатков " + Суффикс;
КонецФункции
Функция СгруппироватьСопоставленныеСтрокиПоСкладу()
Группы = Новый Соответствие;
Для Каждого СтрТ Из ВходящиеДанные Цикл
Если Не СтрТ.Сопоставлено Тогда
Продолжить;
КонецЕсли;
Если Не ЗначениеЗаполнено(СтрТ.Склад) Или Не ЗначениеЗаполнено(СтрТ.Номенклатура) Тогда
Продолжить;
КонецЕсли;
Если СтрТ.Количество <= 0 Тогда
Продолжить;
КонецЕсли;
КлючСклада = Строка(СтрТ.Склад.УникальныйИдентификатор());
СтрокиСклада = Группы.Получить(КлючСклада);
Если СтрокиСклада = Неопределено Тогда
СтрокиСклада = Новый Массив;
Группы.Вставить(КлючСклада, СтрокиСклада);
КонецЕсли;
СтрокиСклада.Добавить(СтрТ);
КонецЦикла;
// Переключить ключи на ссылки складов для удобства обхода.
Результат = Новый Соответствие;
Для Каждого СтрТ Из ВходящиеДанные Цикл
Если Не СтрТ.Сопоставлено Или Не ЗначениеЗаполнено(СтрТ.Склад) Тогда
Продолжить;
КонецЕсли;
КлючСклада = Строка(СтрТ.Склад.УникальныйИдентификатор());
СтрокиСклада = Группы.Получить(КлючСклада);
Если СтрокиСклада <> Неопределено И Результат.Получить(СтрТ.Склад) = Неопределено Тогда
Результат.Вставить(СтрТ.Склад, СтрокиСклада);
КонецЕсли;
КонецЦикла;
Возврат Результат;
КонецФункции
Функция УдалитьПрежниеДокументыВолны(ТекстТега)
Удалено = 0;
Запрос = Новый Запрос;
Запрос.Текст =
"ВЫБРАТЬ
| Ввод.Ссылка КАК Ссылка
|ИЗ
| Документ.ВводОстатковТоваров КАК Ввод
|ГДЕ
| НЕ Ввод.ПометкаУдаления
| И НЕ Ввод.Проведен
| И Ввод.Организация = &Организация
| И Ввод.Комментарий ПОДОБНО &Тег
| И Ввод.ХозяйственнаяОперация = ЗНАЧЕНИЕ(Перечисление.ХозяйственныеОперации.ВводОстатковСобственныхТоваров)";
Запрос.УстановитьПараметр("Организация", Организация);
Запрос.УстановитьПараметр("Тег", "%" + ТекстТега + "%");
Выборка = Запрос.Выполнить().Выбрать();
Пока Выборка.Следующий() Цикл
Попытка
ДокОб = Выборка.Ссылка.ПолучитьОбъект();
ДокОб.Удалить();
Удалено = Удалено + 1;
Исключение
КонецПопытки;
КонецЦикла;
Возврат Удалено;
КонецФункции
Функция СоздатьДокументПоСкладу(СкладДок, СтрокиСклада, ТекстТега)
Док = Документы.ВводОстатковТоваров.СоздатьДокумент();
Док.Дата = ДатаДокументовВвода;
Док.Организация = Организация;
Док.Склад = СкладДок;
Док.ХозяйственнаяОперация = Перечисления.ХозяйственныеОперации.ВводОстатковСобственныхТоваров;
Док.Комментарий = ТекстТега + ", склад " + СокрЛП(Строка(СкладДок));
Док.ОтражатьВОперативномУчете = Истина;
Док.ОтражатьСебестоимость = Ложь;
Док.ЦенаВключаетНДС = Ложь;
Попытка
Док.Подразделение = ОбщегоНазначения.ЗначениеРеквизитаОбъекта(СкладДок, "Подразделение");
Исключение
КонецПопытки;
Попытка
Док.Валюта = ЗначениеНастроекПовтИсп.ВалютаРегламентированногоУчетаОрганизации(Организация);
Исключение
Док.Валюта = Константы.ВалютаРегламентированногоУчета.Получить();
КонецПопытки;
Если Не ЗначениеЗаполнено(Док.НалогообложениеНДС) Тогда
Док.НалогообложениеНДС = Перечисления.ТипыНалогообложенияНДС.ПродажаОблагаетсяНДС;
КонецЕсли;
Попытка
ПараметрыНДС = Документы.ВводОстатковТоваров.ИнициализироватьПараметрыВидовДеятельностиНДС(Док);
УчетНДСУП.ЗаполнитьВидДеятельностиНДС(Док.ВидДеятельностиНДС, ПараметрыНДС);
Исключение
КонецПопытки;
Для Каждого СтрТ Из СтрокиСклада Цикл
НовСтр = Док.Товары.Добавить();
НовСтр.Номенклатура = СтрТ.Номенклатура;
НовСтр.Характеристика = СтрТ.Характеристика;
НовСтр.Серия = СтрТ.СерияСсылка;
НовСтр.Количество = СтрТ.Количество;
НовСтр.КоличествоУпаковок = СтрТ.Количество;
НовСтр.Цена = 0;
НовСтр.Сумма = 0;
Попытка
НовСтр.СтавкаНДС = СтрТ.Номенклатура.СтавкаНДС;
Исключение
КонецПопытки;
Если ЗначениеЗаполнено(СтрТ.НомерГТДСсылка) Тогда
НовСтр.НомерГТД = СтрТ.НомерГТДСсылка;
КонецЕсли;
Если ЗначениеЗаполнено(СтрТ.СерияСсылка) Тогда
СтрСер = Док.Серии.Добавить();
СтрСер.Номенклатура = НовСтр.Номенклатура;
СтрСер.Характеристика = НовСтр.Характеристика;
СтрСер.Серия = СтрТ.СерияСсылка;
СтрСер.Количество = НовСтр.Количество;
СтрСер.КоличествоУпаковок = НовСтр.Количество;
КонецЕсли;
КонецЦикла;
Если Док.Товары.Количество() = 0 Тогда
Возврат Документы.ВводОстатковТоваров.ПустаяСсылка();
КонецЕсли;
ОбщегоНазначенияУТ.ЗаполнитьИдентификаторыДокумента(Док, "Товары");
Попытка
ПараметрыУказанияСерий = НоменклатураСервер.ПараметрыУказанияСерий(Док, Документы.ВводОстатковТоваров);
НоменклатураСервер.ЗаполнитьСтатусыУказанияСерий(Док, ПараметрыУказанияСерий);
Исключение
КонецПопытки;
Док.ОбменДанными.Загрузка = Ложь;
Док.Записать(РежимЗаписиДокумента.Запись);
Возврат Док;
КонецФункции
Процедура ЗаполнитьСтрокуВходящихДанныхИзAPI(НовСтр, СтрокаAPI)
НовСтр.НоменклатураИдентификатор = UUIDИзСтроки(ЗначениеСвойства(СтрокаAPI, "nomenclature_guid", ""));