При работе с базами данных 1С, размещенными на MSSQL, часто возникает необходимость уменьшить объем хранимых данных, удалив устаревшие записи или информацию по неактуальным организациям. На первый взгляд, это может показаться простой задачей, решаемой прямым SQL-запросом DELETE. Однако, база данных 1С — это сложная, взаимосвязанная структура, и простое удаление записей без учета ее специфики может привести к необратимым потерям данных, нарушению целостности и некорректной работе системы.
В этой статье мы подробно рассмотрим, почему традиционная "обрезка" базы средствами SQL является крайне рискованной, и какой подход, называемый "свёрткой", является правильным. Мы проанализируем гибридные методы, сочетающие работу в 1С и прямые SQL-запросы, а также обсудим необходимые меры предосторожности.
Прежде чем пытаться обрезать или свернуть базу данных 1С, крайне важно понять, как платформа хранит данные в MSSQL. В отличие от стандартных баз данных, где имена таблиц и полей часто интуитивно понятны, 1С использует специфическую систему именования, которая напрямую не соответствует названиям объектов конфигурации (документов, справочников, регистров).
Например, названия таблиц в SQL обычно начинаются с префиксов:
_Document для документов._AccRg для регистров бухгалтерии._Reg для регистров накопления и сведений._Reference для справочников.Поля, отвечающие за дату документа, часто называются _Date_Time или _Period (для записей регистров). Статус документа может храниться в полях типа _Fld<число> или _Posted, где _Posted обычно указывает на проведение документа (1 - проведен, 0 - не проведен).
Мы не можем просто угадывать эти названия. Для получения точных соответствий между объектами 1С и таблицами/полями SQL мы можем использовать следующие инструменты:
ПолучитьСтруктуруХраненияИнформационнойБазы() может помочь разработчикам получить эти данные программно. Существуют также обработки из "Инструментов разработчика", которые визуализируют эту структуру. Однако, эти средства доступны из среды 1С, а не напрямую из SQL._Date_Time очевидно является датой). Но такой метод не дает полного понимания логики взаимосвязей.Для безопасной и эффективной работы с базой мы настоятельно рекомендуем изучить соответствие объектов 1С и физических таблиц SQL перед выполнением любых операций по удалению данных.
Первоначальный подход, предложенный автором, – это попытка "обрезать" базу, удалив данные до определенной даты (01.2020) и по одной организации, используя прямые SQL-запросы. Этот подход, если он не учитывает специфику 1С, является крайне рискованным и почти всегда приводит к катастрофическим последствиям.
Суть проблемы:
1scrdoc). Простое удаление может привести к появлению ссылок на несуществующие объекты (<Объект не найден>), что нарушит целостность данных и стабильность работы системы.Таким образом, то, что автор называет "обрезкой", в профессиональной среде 1С называется свёрткой базы данных. Цель свёртки — уменьшение объема базы при сохранении полной функциональности и целостности данных, что достигается заменой старых документов на консолидированные начальные остатки.
Самым безопасным и рекомендуемым способом является свёртка базы данных средствами самой платформы 1С:Предприятие. Многие типовые конфигурации имеют встроенные обработки для свёртки или архивации данных, которые корректно формируют начальные остатки и удаляют старые данные. Однако, когда штатные средства по каким-то причинам не подходят (например, из-за их отсутствия, сложности или низкой производительности на очень больших базах), можно применить гибридный подход.
Этот подход сочетает использование функционала 1С для формирования корректных начальных остатков и прямые SQL-запросы для массового удаления устаревших движений и документов. Давайте разберем его по шагам.
Перед тем как писать SQL-запросы, мы должны точно знать, какие таблицы и поля соответствуют документам, регистрам и организациям в нашей конфигурации 1С. Для этого мы можем:
ПолучитьСтруктуруХраненияИнформационнойБазы() в 1С для получения детальной карты объектов 1С и их физического представления в SQL.Это самый важный шаг. В копии базы, используя средства 1С, мы формируем документы ввода начальных остатков на заданную дату обрезки (в нашем случае 01.01.2020). Мы должны убедиться, что эти документы корректно отражают все необходимые остатки по регистрам бухгалтерского учета, регистрам накопления, регистрам сведений, а также по кадровым данным и другим критически важным областям. Это обеспечит правильные данные после удаления старых записей.
Если нам нужно удалить одну из организаций, мы можем сформировать остатки для остальных шести организаций, а данные по седьмой организации, которую нужно убрать, в остатки не включать.
После успешного формирования и проведения документов ввода начальных остатков, мы можем приступить к удалению старых движений регистров в SQL. Это делается в несколько этапов, начиная с регистров бухгалтерии и регистров накопления.
Важно: Для очень больших таблиц регистров операция DELETE может быть очень медленной. В некоторых случаях, если нам нужно полностью очистить данные до определенной даты, может быть быстрее использовать подход с INSERT ... SELECT в новую таблицу, затем DROP старой и RENAME новой. Однако, это требует более глубокого понимания всех индексов и связей.
Пример SQL-кода для удаления движений регистра бухгалтерии (например, _AccRg5565, где _Period — это поле даты):
USE [НазваниеВашейБазы];
DELETE _AccRg5565
FROM _AccRg5565
WHERE _Period < '40180101'; -- '40180101' соответствует 01.01.2018 в формате 1С даты (число дней от 0001.01.01), для 01.01.2020 будет другое значение.
-- Более надежно использовать прямое преобразование: WHERE CONVERT(DATETIME, _Period) < '2020-01-01';
Для регистров накопления или сведений мы поступаем аналогично, используя соответствующее поле даты (обычно _Period или _Date_Time).
Если таблица итогов регистра (например, для _AccRg5565 это может быть _AccRg5565_VT) очень большая, для ее полной очистки может быть быстрее использовать команду TRUNCATE TABLE, а затем пересчитать итоги в 1С.
USE [НазваниеВашейБазы];
TRUNCATE TABLE _AccRg5565_VT; -- Удаляет все записи из таблицы итогов, что может быть быстрее, чем DELETE.
После удаления движений регистров мы обязательно должны запустить полный пересчет итогов в 1С (обычно через "Тестирование и исправление" или регламентное задание) для всех затронутых регистров.
После того как мы уверены в корректности остатков и движений регистров (после пересчета итогов), мы можем выполнить удаление самих документов, которые предшествуют дате обрезки. Также мы удаляем документы, относящиеся к той организации, которую мы хотим исключить.
Пример SQL-кода для удаления документов (например, _Document120, где _Date_Time — поле даты):
USE [НазваниеВашейБазы];
DELETE _Document120
FROM _Document120
WHERE _Date_Time < '2020-01-01 00:00:00.000'; -- Пример удаления документов до 01.01.2020
Если документы являются "непроведенными" (как в случае автора), то это упрощает задачу, поскольку они не формируют движений по регистрам. Однако, даже такие документы могут иметь ссылки на другие объекты или участвовать в сложной логике системы. Мы должны быть уверены, что удаление этих документов не нарушит логику работы других системных процессов или более поздних документов, которые могут ссылаться на них.
Для удаления документов, относящихся к конкретной организации, нам нужно знать поле, по которому идет связь с организацией (часто это _Fld<число>, хранящее ссылку на справочник организаций). Пример:
USE [НазваниеВашейБазы];
DELETE D
FROM _Document<НомерДокумента> D
WHERE D._Fld<НомерПоляОрганизации> = (SELECT R._ID FROM _Reference<НомерСправочникаОрганизаций> R WHERE R._Description = 'НазваниеУдаляемойОрганизации');
Это примерный запрос, реальные названия полей и таблиц нужно получить из структуры базы.
После удаления документов и движений мы столкнемся с так называемыми "битыми ссылками" (<Объект не найден>) на удаленные документы или на удаленную организацию. В 1С есть штатные механизмы для очистки таких ссылок (например, "Поиск и удаление дублей", "Тестирование и исправление"). Мы запускаем их, чтобы привести базу в порядок.
Также может потребоваться ручная или программная очистка справочников от элементов, которые больше не используются и ссылались на удаленные данные. Например, контрагенты, связанные только с удаленной организацией или старыми документами.
После массового удаления данных в SQL необходимо выполнить операции обслуживания для уменьшения физического размера файлов базы данных и логов транзакций.
.ldf) может сильно разрастись после операций DELETE. Мы можем сжать его, сделав сначала резервную копию лога, а затем выполнив команду DBCC SHRINKFILE..mdf) также может быть сжат, но к этой операции мы подходим с осторожностью, так как частое сжатие может привести к фрагментации.Примеры команд:
USE [НазваниеВашейБазы];
DBCC SHRINKFILE ('НазваниеЛогФайлаБазы_log', 100); -- Сжать лог-файл до 100 МБ.
DBCC SHRINKDATABASE ('НазваниеВашейБазы', 10); -- Сжать базу данных, освобождая 10% свободного места.
Мы повторяем эти операции несколько раз, если база все еще занимает большой объем. После всех операций рекомендуется провести полную реиндексацию.
Помимо описанного гибридного метода, мы можем рассмотреть и другие подходы:
Крайне важно понимать, что прямое изменение данных в базе 1С через SQL, без использования механизмов платформы, запрещено лицензионным соглашением 1С. В случае возникновения проблем, компания 1С может отказать в официальной поддержке и консультациях, ссылаясь на нарушение лицензионных условий.
Основные риски, которые мы принимаем на себя при прямом SQL-доступе:
Поэтому мы всегда подходим к таким операциям с максимальной осторожностью, имея полное понимание последствий и готовые планы по восстановлению. Наличие актуальных бэкапов и тестовых сред является нашим главным страховым полисом.