При разработке нетиповых механизмов учета в 1С часто возникает архитектурная коллизия: документ поступления заполняется в разрезе книги (или любого другого ТМЦ) без указания конкретного получателя, а документ списания (выдачи) обязательно требует указания физического лица. Если попытаться реализовать такой учет на одном регистре накопления остатков с измерениями Книга и ФизЛицо, платформа перестанет корректно закрывать остатки. Проанализируем, почему это происходит и какими способами можно правильно выстроить архитектуру решения.
Платформа «1С:Предприятие» рассчитывает итоги в регистрах накопления остатков по каждой уникальной комбинации значений всех объявленных измерений. Незаполненное измерение (пустая ссылка) и конкретное значение справочника являются абсолютно разными точками многомерной системы координат.
Если документ поступления делает движение «Приход» с измерениями [Книга = "Война и мир", ФизЛицо = ПустаяСсылка], а документ списания делает движение «Расход» с измерениями [Книга = "Война и мир", ФизЛицо = "Петров"], то в регистре образуются две застрявшие записи:
Общий остаток по книге скроется в ноль, но развернутый остаток по измерениям «зависнет». Это приведет к искажению отчетов типа оборотно-сальдовой ведомости и ошибкам при контроле остатков. Для решения задачи разберем несколько проверенных архитектурных подходов.
Наиболее правильным методологическим решением является разделение контура хранения книг и контура учета книг на руках у физических лиц. Создадим два отдельных регистра накопления:
Книга (СправочникСсылка.Книги).Количество (Число).Книга, ФизЛицо.Количество.Разберем логику работы документов при таком подходе:
1. Документ Поступление книг делает движение «Приход» только в первый регистр ОстаткиКнигНаСкладе. Если книга покупалась под конкретного человека, создается запись во второй регистр.
2. Документ Списание (выдача) книг делает два движения одновременно:
ОстаткиКнигНаСкладе (уменьшаем общий запас).КнигиУФизЛиц (увеличиваем долг или числящиеся за человеком книги).При такой схеме регистр остатков на складе всегда закрывается в ноль строго по номенклатуре, а регистр расчетов с физическими лицами ведет точный учет того, у кого какая книга находится на руках.
Если необходимо использовать только один регистр накопления остатков с измерениями Книга и ФизЛицо, потребуется программно скорректировать аналитику в момент списания. Если при проведении списания выясняется, что книга числится на складе без физлица (с пустой ссылкой), документ должен сформировать три записи в регистр:
[Книга, ПустаяСсылка] — списываем свободу из общего фонда.[Книга, ФизЛицо] — зачисляем книгу на конкретного человека.[Книга, ФизЛицо] — списываем выданную книгу с человека.Рассмотрим пример кода в процедуре ОбработкаПроведения документа списания:
Запрос = Новый Запрос;
Запрос.Текст =
"ВЫБРАТЬ
| Остатки.Книга КАК Книга,
| ЕСТЬNULL(Остатки.КоличествоОстаток, 0) КАК ОстатокБезФизЛица
|ИЗ
| РегистрНакопления.ОстаткиКниг.Остатки(&Период, ФизЛицо = ЗНАЧЕНИЕ(Справочник.ФизическиеЛица.ПустаяСсылка)) КАК Остатки
|ГДЕ
| Остатки.Книга = &Книга";
Запрос.УстановитьПараметр("Период", ГраницаВключая);
Запрос.УстановитьПараметр("Книга", СтрокаТЧ.Книга);
РезультатЗапроса = Запрос.Выполнить();
Если НЕ РезультатЗапроса.Пустой() Тогда
// Списываем остаток без физлица и перевешиваем на физлицо
Движение1 = Движения.ОстаткиКниг.ДобавитьРасход();
Движение1.Книга = СтрокаТЧ.Книга;
Движение1.ФизЛицо = Справочники.ФизическиеЛица.ПустаяСсылка();
Движение1.Количество = СтрокаТЧ.Количество;
Движение2 = Движения.ОстаткиКниг.ДобавитьПриход();
Движение2.Книга = СтрокаТЧ.Книга;
Движение2.ФизЛицо = СтрокаТЧ.ФизЛицо;
Движение2.Количество = СтрокаТЧ.Количество;
КонецЕсли;
// Основное списание с физлица
Движение3 = Движения.ОстаткиКниг.ДобавитьРасход();
Движение3.Книга = СтрокаТЧ.Книга;
Движение3.ФизЛицо = СтрокаТЧ.ФизЛицо;
Движение3.Количество = СтрокаТЧ.Количество;
В результате такой операции пустая аналитика полностью закрывается в ноль, а конечный остаток по физлицу также выходит в ноль после выдачи.
Проанализируем еще один способ: исключить ФизЛицо из состава измерений регистра накопления остатков и перенести его в **Реквизиты** регистра.
Плюсы подхода:
Книга, поэтому проблемы с расщеплением аналитики и зависанием итогов не возникают вовсе.Минусы подхода:
.Остатки() станет невозможно, так как виртуальная таблица группирует данные только по измерениям.Выбор конкретного решения зависит от требований к отчетности: