При работе с базами данных 1С:Предприятия 7.7, особенно в случаях подготовки копий баз для филиалов или очистки старых данных, часто возникает задача массового удаления документов. Стандартные методы могут работать крайне медленно, что толкает разработчиков на использование прямых SQL-запросов. Однако прямое удаление из SQL-таблиц в 1С 7.7 таит в себе множество подводных камней, связанных с нарушением ссылочной целостности и логики учета. Рассмотрим подробно, как устроена структура хранения документов и какие методы позволяют выполнить удаление максимально эффективно и безопасно.
Для того чтобы понять, почему простой запрос DELETE FROM _1SJourn не сработает, проанализируем, в каких таблицах распределены данные одного документа. В 1С 7.7 документ — это не одна запись, а целый комплекс связанных данных:
IDDoc.DH123). Здесь лежат реквизиты шапки.RA*, которые напрямую влияют на остатки в RG*.Важно понимать: если вы удалите запись только из _1SJourn, данные в DH, DT и регистрах останутся «сиротами». Это приведет к катастрофическим ошибкам при пересчете итогов или попытке тестирования и исправления базы.
Попытка автора темы использовать простой DELETE с соединением через JOIN в одном запросе синтаксически неверна для SQL Server в том виде, в котором она была представлена. Рассмотрим, как мог бы выглядеть алгоритм прямого удаления, если всё же принято решение идти по этому пути.
Проанализируем необходимые действия:
IDDoc удаляемых документов.DH и DT, относящихся к удаляемым видам документов.RA*)._1SCrdoc._1SJourn.Однако, как справедливо заметили участники обсуждения, такой подход требует идеального знания структуры конкретной конфигурации. Малейшая ошибка (например, забытая таблица последовательностей _1SStx) приведет к неработоспособности базы в будущем.
Выясним причину, почему штатное удаление ТекущийДокумент().Удалить(1) работает медленно. Основное время тратится на:
Мы можем значительно ускорить этот процесс, используя «хитрости», предложенные опытными разработчиками в теме. Разберем этот алгоритм по шагам:
Шаг 1: Отключение фиксации транзакций и журнала регистрации
Работа в транзакции позволяет SQL серверу не сбрасывать данные на диск после каждого удаленного документа, а делать это порциями. Также рекомендуется временно отключить регистрацию событий в Конфигураторе (Журнал регистрации), так как запись текстовых логов при массовых операциях создает огромную нагрузку на дисковую подсистему.
Шаг 2: Перенос точки актуальности (ТА) назад
Это самый эффективный прием для ускорения удаления проведенных документов. В 1С 7.7 при удалении проведенного документа система пытается пересчитать итоги от даты документа до ТА. Если мы установим ТА на самую раннюю возможную дату (например, на начало 1980 года), то пересчета фактически не будет, так как нет документов «после» этой точки.
Пример кода для реализации ускоренного удаления:
// 1. Устанавливаем монопольный режим для скорости
// 2. Переносим ТА в глубокое прошлое
Сервис = СоздатьОбъект("Сервис"); // Если используется компонента 1С++ или штатно через установку ТА
УстановитьТАна(НачДата);
// 3. Начинаем транзакцию
ОчиститьДанные = СоздатьОбъект("Документ");
ВыбранныеДокументы = СоздатьОбъект("ТаблицаЗначений");
// Предположим, список IDDoc уже получен запросом или выборкой
НачатьТранзакцию();
Сч = 0;
Док.ВыбратьДокументы(ДатаНач, ДатаКон);
Пока Док.ПолучитьДокумент() = 1 Цикл
// Проверяем условия (например, по складу)
Если Док.Склад <> НужныйСклад Тогда
Док.Удалить(1); // 1 - удаление без корзины (сразу)
Сч = Сч + 1;
КонецЕсли;
// Фиксируем транзакцию каждые 1000 документов, чтобы не переполнить лог SQL
Если Сч % 1000 = 0 Тогда
ЗафиксироватьТранзакцию();
НачатьТранзакцию();
КонецЕсли;
КонецЦикла;
ЗафиксироватьТранзакцию();
Проанализируем ситуацию: стоит ли использовать прямой SQL? Если ваша задача — удалить 90% данных из огромной базы для создания «пустышки», то штатный метод даже с переносом ТА может занять часы. В этом случае программисты иногда используют TRUNCATE TABLE для полной очистки таблиц движений и журналов, но это требует последующего восстановления структуры через «Тестирование и исправление».
Для выборочного удаления (например, по конкретному складу, как у автора темы) штатный метод Удалить(1) внутри транзакции с предварительным переносом ТА назад является золотым стандартом. Он гарантирует:
_1SCrdoc и проводки).Рассмотренная тема подтверждает: лезть «лапками» в SQL-таблицы 1С 7.7 без крайней необходимости не стоит. Использование штатных методов платформы в сочетании с инженерными приемами (управление точкой актуальности и транзакциями) позволяет добиться высокой скорости работы при сохранении полной целостности базы данных. Если же вы решите использовать SQL, помните о необходимости очистки всех связанных таблиц: от _1SJourn до _1SCrdoc и таблиц проводок.