Регистры бухгалтерии. Еще одна таблица оборотов ДТ / КТ
Виртуальная таблица оборотов ДТ / КТ регистра бухгалтерии. Особенности и применение.
- Описание
- Подробнее
Описание
Введение
В предыдущей статье "Регистры бухгалтерии. Виртуальная таблица оборотов" мы рассмотрели работу таблицы оборотов регистра бухгалтерии, коснулись некоторых особенностей ее работы как в части формируемых SQL-запросов платформы, так и в части работы с параметрами этой таблицы. Сегодня мы снова вернемся к оборотам, но в этот раз это будет виртуальная таблица "Обороты Дт/Кт".
Все данные для публикации получены с помощью инструментов:
- Транслятор запросов 1С
- Просмотр и анализ структуры базы данных (отчет на СКД)
- Помощник работы с идентификаторами
Эта таблица используется реже, чем обычная таблица оборотов и далее мы выясним почему. Но некоторые отчеты в типовых конфигурациях ее все же используют:
- Анализ состояния налогового учета по налогу на прибыль
- Анализ состояния налогового учета по УСН
- Валовая прибыль
- Регистры БУ субъектов малого предпринимательства
- И некоторые другие.
Давайте рассмотрим, что эта таблица позволяет сделать и чем она отличается от обычных оборотов. А позже "копнем" как она работает на уровне базы данных.
Первый взгляд
Начнем со сравнения таблиц "Обороты" и "ОборотыДтКт". Если смотреть на доступные поля и параметры, то можно выделить следующие различия:
- В таблице "Обороты" доступны поля оборотов по ДТ и КТ для балансовых ресурсов. Для типового регистра это ресурс "Сумма". Если в таблице оборотов доступны как общая сумма оборотов, так и по ДТ и КТ, то для таблицы "ОборотыДтКт" доступен только общее поле "СуммаОборот".
- Для небалансовых ресурсов отличие заключается в том, что в таблице "Обороты" для них кроме оборотов по ДТ и КТ присутствует общий оборот. В таблице "ОборотДтКт" общего оборота нет.
В остальном, по крайней мере на первый взгляд, виртуальные таблицы схожи: тот же набор параметров виртуальных таблиц и измерений. Все очень похоже.
В таблице "Обороты" параметры виртуальных таблиц делятся не на "Дт / Кт", а на основной счет + его аналитика и корреспондентский счет + его корр. аналитика. Смысл практически тот же самый, но за большим исключением: если в таблице "ОборотыДтКт" отборы устанавливаются именно по счету ДТ и/или по счету КТ, то в обычной таблице оборотов отбор устанавливается без явного указания стороны проводки.
Проще показать на примере. Допустим, у нас есть вот такой запрос.
ВЫБРАТЬ
ХозрасчетныйОборотыДтКт.СчетДт КАК СчетДт,
ХозрасчетныйОборотыДтКт.КоличествоОборотДт КАК КоличествоОборотДт,
ХозрасчетныйОборотыДтКт.СчетКт КАК СчетКт,
ХозрасчетныйОборотыДтКт.КоличествоОборотКт КАК КоличествоОборотКт,
ХозрасчетныйОборотыДтКт.СуммаОборот КАК СуммаОборот
ИЗ
РегистрБухгалтерии.Хозрасчетный.ОборотыДтКт(&НачалоПериода, &КонецПериода, , СчетДт = &Счет, , , , ) КАК ХозрасчетныйОборотыДтКт
Сделав отбор, например, по счету 10.11.1 за 2019 год мы получили такой результат:
СчетДт | КоличествоОборотДт | СчетКт | КоличествоОборотКт | СуммаОборот |
10.11.1 | 1 000 | 10.10 | 1 000 | 1 000 000 |
То есть количественный оборот как по ДТ, так и по КТ равен 1000. Оборот по сумме равен 1000000. Далее сделаем примерно такой же запрос, но к таблице "Обороты" с теми же значениями отборов:
ВЫБРАТЬ
ХозрасчетныйОбороты.Счет КАК Счет,
ХозрасчетныйОбороты.СуммаОборотДт КАК СуммаОборотДт,
ХозрасчетныйОбороты.КоличествоОборотДт КАК КоличествоОборотДт,
ХозрасчетныйОбороты.КорСчет КАК КорСчет,
ХозрасчетныйОбороты.СуммаОборотКт КАК СуммаОборотКт,
ХозрасчетныйОбороты.КоличествоОборотКт КАК КоличествоОборотКт,
ХозрасчетныйОбороты.СуммаОборот КАК СуммаОборот,
ХозрасчетныйОбороты.КоличествоОборот КАК КоличествоОборот
ИЗ
РегистрБухгалтерии.Хозрасчетный.Обороты(&НачалоПериода, &КонецПериода, , Счет = &Счет, , , , ) КАК ХозрасчетныйОбороты
Вот такой результат мы получили:
Счет | СуммаОборотДт | КоличествоОборотДт | КорСчет | СуммаОборотКт | КоличествоОборотКт | СуммаОборот | КоличествоОборот |
10.11.1 | 1 000 000 | 1000 | 10.10 | 200 000 | 50 | 800 000 | 9950 |
10.11.1 | 20.01 | 10 000 | 2000 | -10 000 | -2000 | ||
10.11.1 | 26 | 4 000 | 25 | -4 000 | -25 | ||
10.11.1 | 44.01 | 20 000 | 50 | -20 000 | -50 |
Мы получили обороты с другими корреспондирующими счетами (44.01, 26, 20.01), но сейчас они нас не интересуют. Просто знаем, что таблица "Обороты" позволила их получить. А вот таблица "ОборотыДтКт" их не показала. Почему? Да потому что в проводках эти счета находятся на стороне ДТ, а мы явно указали отбор по ДТ и они в этот отбор не входят. Таблица же оборотов не учитывает явную сторону проводки, а лишь собирает данные по указанному счету как с дебетовой стороны, так и с кредитовой и группирует показатели в общий результат.
Посмотрите на все сделанные корреспонденции счетов за тот же период с участием счета 10.11.1. На стороне дебета он есть только для проводки "ДТ 10.11.1 — КТ 10.10". Именно поэтому только обороты по этой корреспонденции счетов попали в результат, когда отбор по ДТ = "10.11.1" для таблицы "ОборотыДтКт".
СчетДт | СчетКт | ||
44.01 | 10.11.1 | ||
26 | 10.11.1 | ||
10.11.1 | 10.10 | ||
10.10 | 10.11.1 | ||
20.01 | 10.11.1 |
Это важное отличие таблицы "ОборотыДтКт" от обычной таблицы оборотов: мы можем явно указать сторону счета (или другой произвольной аналитики) в проводке для фильтра и оперировать результатами запроса к этой виртуальной таблице точно зная где образовался нужный показатель — по дебету или кредиту.
Если же мы сделаем в обычной таблице оборотов отбор по счету "10.10" (с которым корреспондировал 10.11.1) и оставим результат только для корреспонденции этих двух счетов, то увидим следующее:
Счет | СуммаОборотДт | КоличествоОборотДт | КорСчет | СуммаОборотКт | КоличествоОборотКт | СуммаОборот | КоличествоОборот |
10.10 | 200 000 | 50 | 10.11.1 | 1 000 000 | 1000 | -800 000 | -950 |
То есть, таблица "Обороты" получила данные оборотов по счету "10.10" с корреспондирующим счетом "10.11.1" не смотря на то, что мы указали его в отборе по измерению "Счет" (а не корр. счет) этой виртуальной таблицы. Подробнее о принципе работы виртуальной таблицы "Обороты" Вы можете прочитать в прошлой публикации "Регистры бухгалтерии. Виртуальная таблица оборотов".
Таким образом, для получения оборотов по счету самым эффективным способом является использование виртуальной таблицы "Обороты" без получения данных по кор. счету (об этом мы говорили в предыдущей статье). Если получать корр. аналитику через эту таблицу, то не будут использоваться итоги и запрос может быть тяжелее, чем ожидается. Без корр. аналитики платформа 1С попытается максимально использовать данные таблиц итогов.
Таблица же "ОборотыДтКт" подходит для более специфичных задач, когда необходимо получать обороты с конкретными фильтрами по счету, аналитике или ресурсам с указанием явной стороны проводки — ДТ или КТ. Таблица является самой тяжелой среди всех виртуальных таблиц регистра бухгалтерии, т.к. она никогда не использует рассчитанные итоги, но об этом мы еще поговорим далее. Поэтому если есть возможность использовать обычную таблицу оборотов — делайте именно так. Если нет, то с осторожностью и рациональным подходом, используйте таблицу оборотов ДТ / КТ.
Есть, конечно, еще виртуальные таблицы "Остатки" и "ОстаткиИОбороты", но о них речь пойдет в будущих публикациях. Сейчас лишь отмечу, что в некоторых случаях можно использовать и эти таблицы вместо оборотов по ДТ / КТ, но этот случай выходит за рамки публикации.
Спускаемся глубже
Настало время рассмотреть какие запросы формирует платформа 1С при работе с виртуальной таблицей оборотов ДТ / КТ.
Простой запрос
Начнем с простого примера — получим обороты для счетов со стороны дебета по сумме и количеству. Чисто для эксперимента не будем указывать никаких параметров виртуальной таблицы или других условий.
ВЫБРАТЬ
ХозрасчетныйОборотыДтКт.СчетДт КАК СчетДт,
ХозрасчетныйОборотыДтКт.СуммаОборот КАК СуммаОборот,
ХозрасчетныйОборотыДтКт.КоличествоОборотДт КАК КоличествоОборотДт
ИЗ
РегистрБухгалтерии.Хозрасчетный.ОборотыДтКт(, , , , , , , ) КАК ХозрасчетныйОборотыДтКт
Один небольшой запрос на языке запросов 1С, но большой SQL-запрос на стороне базы данных (на самом деле еще не очень большой).
SELECT
T1.AccountDtRRef, -- СчетДт
T1.Fld790Turnover_, -- СуммаОборотДт
T1.Fld792TurnoverDt_ -- КоличествоОборотДт
FROM (
SELECT
T2._AccountDtRRef AS AccountDtRRef, -- СчетДт
CAST(SUM(T2._Fld790) AS NUMERIC(21, 2)) AS Fld790Turnover_, -- Сумма
CAST(SUM(T2._Fld792Dt) AS NUMERIC(21, 3)) AS Fld792TurnoverDt_ -- КоличествоДт
FROM dbo._AccRg786 T2 -- РегистрБухгалтерии.Хозрасчетный.Основная
WHERE ((T2._Fld774 = @P1)) -- Разделитель данных
AND (T2._Active) = 0x01 -- Активность
GROUP BY T2._AccountDtRRef -- Счет
-- Хотя бы один из ресурсов должен быть НЕ равен 0
HAVING (CAST(SUM(T2._Fld790) AS NUMERIC(21, 2))) <> 0.0
OR (CAST(SUM(T2._Fld792Dt) AS NUMERIC(21, 3))) <> 0.0
) T1
Как обычно платформа получает данные из основной таблицы движений регистра бухгалтерии с отбором по разделителю данных (ох уж эти типовые конфигурации) и только с активными записями. При этом в результат попадают только те данные по счету, которые не равны 0 после группировки результата.
Запрос очень простой и комментарии в тексте говорят сами за себя. Настоящие задачи редко требуют написания запросов без параметров, поэтому усложним пример.
Добавим немного параметров
Совсем немного изменим запрос, добавив отбор по периоду, счету ДТ и виду субконто. Для порядка еще и по организации сделаем отбор.
ВЫБРАТЬ
ХозрасчетныйОборотыДтКт.СчетДт КАК СчетДт,
ХозрасчетныйОборотыДтКт.СубконтоДт1 КАК СубконтоДт1,
ХозрасчетныйОборотыДтКт.СуммаОборот КАК СуммаОборот,
ХозрасчетныйОборотыДтКт.КоличествоОборотДт КАК КоличествоОборотДт
ИЗ
РегистрБухгалтерии.Хозрасчетный.ОборотыДтКт(&НачалоПериода, &КонецПериода, , СчетДт = &СчетДт, &ВидСубконто, , , Организация = &Организация) КАК ХозрасчетныйОборотыДтКт
И снова один маленький запрос на языке запросов 1С, и уже несколько SQL-запросов на стороне базы данных.