gifts2017

Опыт по восстановлению файловой версии базы после неудачной реструктуризации таблиц

Опубликовал Сергей Белов (soaron78) в раздел Администрирование - Системное

В случае если вовремя реструктуризации у вас произошла проблема, а последних резервных копий как на зло нет, не спешите выбрасывать базу данных на мороз, можно попытаться ее восстановить

Вступление

Был летний солнечный день и ничто не предвещало беды, когда зазвонил телефон и сотрудница на другом конце сообщила: "Похоже я убила базу клиента". После допроса с пристрастием выяснилось следующее: на обычном удаленном рабочем столе (RDP) проводилось  обновление конфигурации с реструктуризацией базы, таких обновлений делается по тысячу пятьсот раз на дню. Однако, в этот раз пошло, что-то  не так и база данных рухнула.

Реструктуризация

При повторном запуске программа выдавала сообщение

Незавершенная операция

и после этого вываливалась в Windows. Наличие резервной копии позволило бы восстановить базу в два счета, но человеческая беспечноть сотрудницы, которая не потратила лишних пару минут для ее создания привела к тому, что исправление проблемы заняло около четырех дней, было сделано несколько неправильных шагов, которые не приводили к значимому результату. Ниже я описываю правильный путь.

Восстановление базы


Поиск по интернету привел к страницам с описанием данных проблем без наличия решения, однако вскоре были найдены две важные ссылки, которые явились отправной точной в восстановлении:

Краткое описание формата файлов *.1CD (файловых баз 1Сv8)

Восстанавливаем убитую базу 1C

Шаг №1. Делаем резервную копию испорченной базы 

Коллега awa, упомянул в одном из сообщении, что штатная утилита 1С chdbfl.exe - чуть реже чем всегда бесполезна для исправления подобных проблем. Данная утилита проверяет только физическую целостность таблиц. Восстановление структур необходимых для запуска БД для нее непосильная задача. Более того, в некоторых случаях она портит испорченную базу на столько, что ее невозможно восстановить. В любом случае при запуске данной утилиты всегда делайте резервную копию базы.

 

Шаг №2. Делаем выгрузку конфигурации при помощи утилиты Tool_1CD

Утилита находится здесь: http://infostart.ru/public/19633/

Помимо просмотра списка таблиц, там есть важная для нас функция выгрузки конфигурации. Запускаем утилиту, открываем базу. База открылась без сообщений об ошибок, это хороший знак!

Выгрузка конфигурации

 

Шаг №3. Анализируем структуру файла испорченной базы

Итак, как вам известно CD файл - это по сути хранилище файлов-таблиц. Открываем Hex редактор (например опенсорсный http://en.wikipedia.org/wiki/HxD), переходим по ссылке 0x4000. Тут находится таблица смещений основных таблиц базы данных и конфигурации. 

Лирическое отступление

Все адреса хранятся в абсолютной адресации, что затрудняет исправление в ручном режиме, в случае если испортилась какая-то таблица не первая по списку. С другой стороны это упрощает программистам 1С работу и ускоряет процесс заргузки нужных таблиц в память.


Итак взглянем на таблицу из HEX редактора:

Основная таблица смещений

 

На этой картинке в левой части показан HEX редактор в правой части список таблиц из утилиты Tool_1CD. Их порядок совпадает с тем как они идут в файле CD. Здесь мы видим, что таблица CONFIG начинается с адреса 0x5000 и оканчивается на 0x31F0FFF, где следом начинается таблица CONFIGSAVE по адресу 0x31F1000 (для тех кто никогда не программировал на ассемблере скажу, что в машинных кодах числа пишутся с права на лево - пережиток царского режима). Строго говоря,  0x5000 расположен заголовок таблицы CONFIG, который ссылается еще на один заголовок, а потом уже следует сама таблица (см. описание формата файлов по ссылке выше). Разумно предположить, что если 1С ругается на конфигурацию, стало быть именно эту таблицу нам надо исправить, для этого надо выцепить таблицу CONFIG из сохраненной конфигурации (или если она не сохраняется, взять конфигурацию максимально близкой к испорченной) и подставить ее по адресу 0x5000, но при этом таблица не должна выходить за пределы 0x31F0FFF.

Upd 10/10/2012

Важное замечание awa

1С обращается к таблицам по имени, и ей не важно, какая таблица находится в списке первой, какая второй и т.д. Просто при создании новой базы 1С создает нужные таблицы друг за другом в том порядке, в каком это создание написали программисты 1С. Поэтому всегда и получается, что CONFIG идет первой, CONFIGSAVE второй и т.д. Но если бы первой таблицей была бы какая-нибудь _REFERENCE152, а CONFIG была бы семнадцатой в списке, 1С спокойно бы работала с такой базой.


Шаг №4а. Загружаем в пустую конфигурацию выгруженную конфигурацию (извините за каламбур)

Загрузили. Записали. Смотрим в HEX-редакторе

Структура в другой платформе

Так-с, что-то не то, какая-то новая таблица добавилась. Отсюда вывод: Восстановление нужно делать на том же релизе платформы, что и испорченная база.


Шаг №5б. Загружаем в пустую конфигурацию выгруженную конфигурацию той же самой версии платформы

Смотрим результат:

Рабочая конфигурация

Да-а, результат тоже не очень. Таблица CONFIG заканчивается по адресу 0x10FFF, судя по всему она не реструктуризирована. Ладно попробуем скопировать рабочую таблицу Tool_1CD  в нерабочую базу. Выделяем блок в рабочей базе и копируем с замещением по адресу 0x5000 в испорченную базу:

Выделение блока

Открываем Tool_1CD, открываем испорченную базу, но увы Tool_1CD виснет при попытке посмотреть таблицу CONFIG. После нескольких не правильных шагов, мне пришла идея: а что если 1С структурирует таблицы при загрузке базы? Тогда остается сделать выгрузку и загрузку базы с рабочей конфигурацией.


Шаг №5в. Загружаем в пустую конфигурацию выгруженную конфигурацию той же самой версии платформы, делаем выгрузку и загрузку базы (не конфигурации!).

Посмотрим как сейчас выглядят смещения:

После выгрузки/загрузки

Уже лучше. Теперь CONFIGSAVE расположена по адресу 0x31FC000, что больше чем 0x31F1000. Как же скопировать больший блок таблицы CONFIG в рабочей базе на меньший блок в испорченной базе? Ответ прост: надо удалить метаданные в рабочей конфигурации, не влияющие на ее структуру: общие модули, картинки, отчеты, обработки и т.п. Нам важно запустить испорченную базу, конфигурацию мы потом восстановим.


Шаг 6. Итерация по удалению метаданных конфигурации, не влияющие на ее структуру, выгрузка и загрузка базы.

После нескольких итераций удаления, выгрузки и загрузки базы, я получил следующую картину:

Удаление метаданных

Наконец-то: CONFIGSAVE начинается с 0x313B0000<0x31F1000. Теперь выделяем блок 0x5000-x313AFFF в рабочей базе и в адрес 0x5000 в испорченной базы копируем с замещением

 Копируем блок

Записываем. Открываем 1С. Отклично, все заработало.

 

Upd 10/10/2012

Важное замечание awa

Как правило по смещению 0x4000, содержатся ссылки на файлы описания таблиц. А уже в файлах описания таблиц содержатся ссылки на таблицы записей, индексов и BLOB.  В общем случае, если таблица CONFIG "начинается" с адреса 0x5000, а таблица CONFIGSAVE с адреса 0x31f1000 и нет никакой гарантии, что на промежутке от 0x5000 до 0x31f1000 не содержится ни одного блока, относящегося к любой другой таблице, помимо CONFIG. В большинстве случаев таблица CONFIG не фрагментирована, объясняется это, думаю, тем, что такое расположение файлов одной таблицы друг за другом, так, что вся таблица как бы находится в файле 1CD одним непрерывным куском, образуется в результате применения сжатия базы данных при тестировании и исправлении или при применении утилиты chdbfl.exe.

 

База загрузилась

Осталось только загрузить в базу рабочую конфигурацию, чтобы восстановить рабочую базу. Все, База восстановлена.

P.S. Разумеется данный случай описывает исправление простых поломок, однако даже такой простой случай может ставить в тупик опытных профессионалов, когда не существует типовых способов решения проблемы. Не забывайте делать резерные копии.

См. также

PowerTools от 1 000
Подписаться Добавить вознаграждение

Комментарии

1. Василий Антонов (khaoos) 10.10.12 05:09
Спасибо, полезно, но надеюсь не пригодится :)
DoctorRoza; fomix; +2 Ответить
2. Алексей Роза (DoctorRoza) 10.10.12 10:02
Круто, серьёзная раскопка .. спасибо за информацию! :)
3. Валерий Агеев (awa) 10.10.12 15:54
Похоже, на инфостарте объявлена неделя восстановления и копания во внутренностях баз :)
Плюс за настойчивость и хитрость!
Уже не в первый раз встречаю убеждение, что таблицы лежат в файле 1CD последовательно, строго друг за другом, одним непрерывным куском. В общем случае, это не так совершенно! Во-первых, каждая таблица состоит из нескольких файлов - файл описания таблицы, файл записей, файл индексов и файл записей неограниченно длины. Во-вторых, каждый из этих файлов может быть фрагментирован, т.е. разбросан по всему файлу базы 1CD!
И тем не менее, не первый раз встречаюсь с тем, что людям все-таки удается восстановить базы, исходя из неправильных, вроде бы, предположений!
Объясняется это, думаю, тем, что такое расположение файлов одной таблицы друг за другом, так, что вся таблица как бы находится в файле 1CD одним непрерывным куском, образуется в результате применения сжатия базы данных при тестировании и исправлении или при применении утилиты chdbfl.exe.
Дело в том, что и chdbfl.exe, и сжатие БД при ТиИ делают, по-сути, одно и тоже - они создают новый файл 1CD, копируют всю информацию из старого файла 1CD в новый последовательно, таблица за таблицей, файл за файлом, но при этом пропуская все удаленные записи и блоки, всю ненужную информацию. После этого старый файл удаляется, а новый становится файлом базы 1CD. Таким образом достигается сжатие информации, и заодно происходит дефрагментация файлов таблиц.
Другое дело, что в уже битой базе, в результате порчи служебной информации, chdbfl.exe может безвозвратно "выкинуть" (т.е. просто не скопировать в новый файл базы) огромные куски реальной информации. Именно поэтому, перед использованием chdbfl всегда надо делать бэкап!
4. Сергей Белов (soaron78) 10.10.12 16:05
Очередность таблиц может меняться? Например CONFIG быть не первой в списке?
Правильно ли я понял, что в корневом блоке 0x4000 размещаются ссылки на файл таблиц содержащий данные, индексы и неограниченные строки, а уже в самом файле адреса на эти три таблицы? В таком случае нам можно забить, на фрагментацию, главное при переносе файлов внутрь CD файла не задеть другие файлы.
5. Валерий Агеев (awa) 10.10.12 16:33
(4) Может. 1С обращается к таблицам по имени, и ей не важно, какая таблица находится в списке первой, какая второй и т.д.
Просто при создании новой базы 1С создает нужные таблицы друг за другом в том порядке, в каком это создание написали программисты 1С. Поэтому всегда и получается, что CONFIG идет первой, CONFIGSAVE второй и т.д. Но если бы первой таблицей была бы какая-нибудь _REFERENCE152, а CONFIG была бы семнадцатой в списке, 1С спокойно бы работала с такой базой.
Да, в корневом файле, данные которого, как правило, находятся по смещению 0x4000, содержатся ссылки на файлы описания таблиц. А уже в файлах описания таблиц содержатся ссылки на таблицы записей, индексов и BLOB. Вы правы, что главное не задеть другие файлы при вставке куска из другой базы. Но, в общем случае, если таблица CONFIG "начинается" с адреса 0x5000, а таблица CONFIGSAVE с адреса 0x31f1000, то нет никакой гарантии, что на промежутке от 0x5000 до 0x31f1000 не содержится ни одного блока, относящегося к любой другой таблице, помимо CONFIG. Просто, в силу описанных мною в предыдущем посте причин, часто оказывается, что таких блоков нет, и можно безболезненно перезаписывать весь этот кусок.
6. Сергей Белов (soaron78) 10.10.12 16:52
(5) awa, Можно я добавлю врезку в статью этого сообщения?
7. Валерий Агеев (awa) 10.10.12 16:58
8. Людмила Артемьева (l-Rain) 11.10.12 10:41
Спасибо, очень полезно. Добавлю публикацию в свою копилку.
9. cratos2 (CratosX) 11.10.12 13:08
Спасибо за статью!
для тех кто никогда не программировал на ассемблере скажу, что в машинных кодах числа пишутся с права на лево - пережиток царского режима

Для меня это стало открытием, несмотря на то, что немного копался в HEX-редакторах...
10. f f (fnv) 16.10.12 08:00
Офигеваю от вашей сотрудницы, которая не делает копии... это на автопилоте должно быть...
11. Вавилов Николай Vavilov (1cNike) 25.12.13 18:32
сюр какой-то. ) За статью спасибо
Для написания сообщения необходимо авторизоваться
Прикрепить файл
Дополнительные параметры ответа