Как перенести строки табличной части из одного документа в другой
Содержание
Чаще всего табличную часть копируют так: открывают старый документ, вручную набирают те же товары в новом и тратят на это час. Хотя в управляемых формах 1С 8.3 строки выделяются мышью и переносятся через буфер обмена за несколько секунд. А если строк сотни или перенос нужен регулярно, его стоит отдать коду.
Ниже способы по нарастанию сложности: от интерфейса до временных таблиц. Начните с самого простого. Программный перенос нужен, когда руками слишком долго или операцию повторяют каждый день.
Что нужно проверить перед копированием
Перенос строк работает, когда у источника и приёмника совпадает состав колонок. Если документ «Поступление товаров» копируется в «Реализацию», часть колонок не совпадёт, и значения потеряются.
Проверьте до начала:
- 📌 Тип объекта. Копирование внутри одного вида документов проходит без потерь. Между разными видами переносятся только одноимённые колонки.
- 📌 Состав колонок. Откройте обе табличные части и сравните: номенклатура, количество, цена, сумма, ставка НДС.
- 📌 Пересчёт. Цены, суммы и НДС после вставки нередко нужно пересчитать, в зависимости от настроек документа.
- 📌 Куда вставляем. В пустую табличную часть или в уже заполненную: от этого зависит, заменятся ли строки или добавятся.
Если нужен весь документ целиком с шапкой и строками, не копируйте строки. В списке документов выделите нужный и нажмите F9 (или команду «Скопировать» в меню «Еще»). Это быстрее и точнее.
Копирование через буфер обмена: способ для пользователя
В управляемых формах (обычное приложение 8.3 с интерфейсом «Такси») строки таблицы выделяются и копируются как в обычной таблице.
- Откройте документ-источник и щёлкните по первой нужной строке табличной части.
- Зажмите
Shiftи щёлкните по последней строке, либоCtrlи отмечайте строки по одной. - Нажмите
Ctrl+C. - Откройте документ-приёмник, поставьте курсор в табличную часть.
- Нажмите
Ctrl+V.
Строки добавятся к существующим. Если в буфере данные из Excel, вставка тоже работает: колонки сопоставляются по порядку, поэтому расположите их в таком же порядке, как в табличной части 1С.
Проверьте результат сразу: пролистайте таблицу и сверьте итоговую сумму с источником. Если значения не подтянулись или встали не в те колонки, перенесите данные другим способом, который описан ниже.
Копирование одной строки
Для дублирования строки внутри того же документа встаньте на неё и нажмите F9. Появится копия под текущей. Удобно для разбивки одной позиции на несколько партий или складов.
Если вставка не сработала
| Симптом | Вероятная причина | Что делать |
|---|---|---|
| Ничего не вставилось | Курсор вне табличной части | Щёлкните в таблицу и повторите |
| Значения встали в чужие колонки | Другой порядок колонок | Переставьте колонки в Excel или переносите программно |
| Пустые ссылки на номенклатуру | Данные из Excel не распознаны как элементы справочника | Загрузите через обработку загрузки данных из табличного документа |
| Не хватает цен и сумм | Они считаются при заполнении | Пересчитайте через кнопку заполнения цен или правку количества |
Перенос между документами разных видов
Для разных видов документов типового переноса «всей табличной части» нет. Здесь два типовых пути.
- ✅ Ввод на основании. Если документы связаны логически (заказ → реализация, поступление → возврат), используйте кнопку «Создать на основании». Табличная часть заполнится по правилам разработчика конфигурации, с нужными пересчётами.
- ✅ Свой перенос через код. Когда типовой связи нет, например, нужно перенести строки из нетипового документа или обработки. Пример в следующем разделе.
Копия документа и перенос строк не должны ломать учёт. Скопированный и проведённый документ создаёт движения заново. Если копию делали «на пробу», удалите её или не проводите.
Программное копирование строк в коде 1С
Самый короткий способ перенести всю таблицу целиком: выгрузить табличную часть в таблицу значений и загрузить в другую.
ДокументОбъект = ДокументСсылка.ПолучитьОбъект();
ТаблицаЗначений = ДокументОбъект.Товары.Выгрузить();
НовыйДокумент = Документы.РеализацияТоваровУслуг.СоздатьДокумент();
НовыйДокумент.Дата = ТекущаяДата();
НовыйДокумент.Товары.Загрузить(ТаблицаЗначений);
НовыйДокумент.Записать();
Метод Загрузить заменяет содержимое табличной части и сопоставляет колонки по именам. Лишние колонки таблицы значений игнорируются, а недостающие остаются пустыми.
Построчный перенос с условием
Когда нужно перенести не все строки или преобразовать данные, перебирайте строки в цикле:
Для Каждого СтрокаИсточника Из ДокументИсточник.Товары Цикл
Если СтрокаИсточника.Количество = 0 Тогда
Продолжить;
КонецЕсли;
СтрокаПриемника = ДокументПриемник.Товары.Добавить();
ЗаполнитьЗначенияСвойств(СтрокаПриемника, СтрокаИсточника);
КонецЦикла;
ЗаполнитьЗначенияСвойств копирует значения свойств с одинаковыми именами. Если нужны только некоторые колонки, перечислите их третьим параметром: "Номенклатура, Количество, Цена".
Копирование выделенных строк из формы
В управляемой форме пользователь выделил строки, и их надо обработать на клиенте. Выделенные строки хранятся как массив идентификаторов:
&НаКлиенте
Процедура СкопироватьВыделенные(Команда)
МассивСтрок = Новый Массив;
Для Каждого Идентификатор Из Элементы.Товары.ВыделенныеСтроки Цикл
Строка = Объект.Товары.НайтиПоИдентификатору(Идентификатор);
МассивСтрок.Добавить(Новый Структура("Номенклатура, Количество",
Строка.Номенклатура, Строка.Количество));
КонецЦикла;
ПеренестиНаСервере(МассивСтрок);
КонецПроцедуры
Дальше на сервере создаёте или открываете документ-приёмник и добавляете строки из массива структур. Так на сервер передаются только нужные поля, а не весь объект формы.
Копирование в обход формы
Для документа, который не открыт на экране, работайте с объектом, а не с данными формы:
- получите объект по ссылке методом
ПолучитьОбъект(); - измените табличную часть;
- вызовите
Записать().
Не пишите документ внутри цикла по строкам: одна запись после всех добавлений заметно быстрее. Это же правило снижает нагрузку на базу, когда пользователи работают одновременно.
Временные таблицы для сложных переносов
Если в процессе нужны группировка, свёртка одинаковых позиций, сравнение с остатками или другие вычисления, удобнее передать табличную часть в запрос. Выгрузите её в таблицу значений и укажите как параметр:
Запрос = Новый Запрос;
Запрос.МенеджерВременныхТаблиц = Новый МенеджерВременныхТаблиц;
Запрос.УстановитьПараметр("Строки", ДокументОбъект.Товары.Выгрузить());
Запрос.Текст =
"ВЫБРАТЬ
| Т.Номенклатура КАК Номенклатура,
| СУММА(Т.Количество) КАК Количество
|ПОМЕСТИТЬ ВТ_Строки
|ИЗ
| &Строки КАК Т
|СГРУППИРОВАТЬ ПО
| Т.Номенклатура";
Запрос.Выполнить();
Во второй запрос с тем же менеджером подключайте ВТ_Строки и соединяйте с остатками, ценами или другими регистрами. Результат выгружайте в таблицу значений (Выгрузить()) и загружайте в табличную часть.
Что даёт такой способ:
- 🔹 одинаковые позиции сворачиваются в одну строку;
- 🔹 цены подтягиваются из регистра сведений одним запросом, а не по запросу на каждую строку;
- 🔹 можно отбросить строки, которых нет в остатках.
Колонки таблицы значений в параметре запроса должны иметь нужные типы. Если колонка создана без типа, в запросе могут возникнуть проблемы со сравнением и соединением. Выгрузка табличной части тип сохраняет, ручная таблица значений требует указания типов при создании колонок.
Ошибки при копировании и как их исправить
Типичные проблемы выглядят так.
- ❌ После загрузки пустые колонки. Имена колонок у источника и приёмника различаются. Сопоставьте вручную построчным переносом:
СтрокаПриемника.Склад = СтрокаИсточника.СкладОтправитель. - ❌ Документ не проводится после копирования. Скопированы строки с номенклатурой, которая запрещена в этом виде документа, или не заполнены обязательные реквизиты шапки. Заполните шапку до записи.
- ❌ Дублируются движения. Копию документа провели, а исходный остался проведённым. Проверьте, нужны ли обе копии.
- ❌ Таблица значений не загружается. Типы колонок несовместимы с типами реквизитов табличной части. Приведите значения явно.
- ❌ Нумерация строк съехала. После
Загрузитьномера строк пересчитываются автоматически. Если нужна своя нумерация, задайте её после загрузки.
Перед массовой операцией оберните запись в Попытка … Исключение, чтобы не потерять данные при сбое:
Попытка
НовыйДокумент.Записать();
Исключение
ЗаписьЖурналаРегистрации("Копирование табличной части",
УровеньЖурналаРегистрации.Ошибка, , ,
ОписаниеОшибки());
ВызватьИсключение;
КонецПопытки;
Если строк много: ускоряем перенос
При больших объёмах время тратится не на копирование, а на лишние обращения к базе. Несколько приёмов.
- Загружайте целиком.
Загрузитьбыстрее построчногоДобавитьв цикле, если не нужна обработка каждой строки. - Не обращайтесь к ссылкам внутри цикла. Реквизит
Строка.Номенклатура.Наименованиев цикле означает запрос к базе на каждой итерации. Получите нужные реквизиты одним запросом заранее. - Записывайте один раз. Одна
Записать()после всех изменений, не после каждой строки. - Работайте на сервере. Клиент-серверные вызовы дорогие. Передайте массив на сервер одним вызовом, как в примере выше.
- Отключите лишние пересчёты. Если документ при добавлении каждой строки пересчитывает суммы, добавьте все строки и пересчитайте один раз.
Для десятков тысяч строк разбейте перенос на пакеты: например, по 500–1000 строк на документ или на транзакцию. Так проще найти ошибочную порцию и не держать долгую транзакцию, которая блокирует других пользователей.
Мини-кейс: перенос спецификации в заказ
Менеджер собрал в одном заказе 40 позиций, и теперь нужен второй заказ с тем же набором для другого покупателя. Вручную это двадцать минут и риск пропустить строку.
Порядок действий:
- В списке заказов выделите исходный и нажмите
F9. Откроется копия с теми же строками. - Замените покупателя и договор в шапке.
- Проверьте цены: у нового покупателя может действовать другое соглашение или вид цены.
- Удалите лишние строки: выделите их с
Ctrlи нажмитеDel. - Запишите документ и убедитесь, что номер и дата новые.
Если нужен не весь заказ, а только часть позиций, откройте оба документа рядом и перенесите нужные строки через Ctrl+C и Ctrl+V. Сорок строк переносятся за полминуты.
Когда копировать строки не нужно
- Документ-приёмник можно создать вводом на основании: так подтянутся связи и проверки.
- Строки нужны только для отчёта. Тогда выгружайте их в табличный документ, а не в другой документ.
- Данные уже есть в регистре. Берите их запросом, а не из старого документа: в документе могла остаться устаревшая цена.
Какой способ выбрать
| Ситуация | Способ |
|---|---|
| Нужен документ целиком | F9 в списке или «Скопировать» |
| Пара десятков строк между документами | Ctrl+C / Ctrl+V |
| Документы связаны по смыслу | Ввод на основании |
| Регулярная операция, одинаковые колонки | Выгрузить + Загрузить |
| Нужны условия и преобразования | Цикл с ЗаполнитьЗначенияСвойств |
| Группировка, остатки, цены | Временная таблица и запрос |
Частые вопросы
Можно ли скопировать табличную часть из Excel в 1С?
Чем Загрузить отличается от Добавить?
Загрузить заменяет всё содержимое табличной части данными таблицы значений. Добавить создаёт одну новую строку в конце.