Drupal. Применение файлов patch для устранения ошибок.

Небольшая памятка по применению файлов *.patch для исправления ошибок в Друпале. Чисто чтоб самому не забыть.

Обычно какие-то исправления получаешь с новой версией модуля. Но случается разработчики не вносят исправления в официальный релиз сразу или вообще. Или исправления делаются не разработчиком. В этом случае нужные исправления можно получить в виде файла с именем kakoe-to-tam-imia.patch

Команда patch

Файл представляет из себя результат работы unix-команды diff, которая вычисляет разницу между двумя файлами. Разница записывается в простой текстовый файл,который может быть трех несколько разных форматов, но для друпал рекомендуется так называемый унифицированный.

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

patch < file.patch

либо запуск его из папки где он создавался командой (сама программа patch при этом запускается из корня дерева Drupal):
patch -p0 < path/file.patch

Разработчики Drupal рекомендуют создавать патчи только в корне дерева Drupal, но кто бы их слушал. Определить, в каком каталоге создали патч можно открыв его в простом текстовом редакторе. Если в строке начинающейся с трех минусов вы видите знакомое sites/all/modules/.., значит все в порядке - кладите его в корень сайта и отдавайте рекомендуемую команду. Если только имя файла, значит надо класть патч в папку того модуля файл которого исправляется. Можно встретить и соломоново решение - патч содержит кусок пути от корня пакета до файла во внутренней папке. Например первый попавшийся мне патч на модуль image_attach содержал такую строчку.

--- contrib/image_attach/image_attach.module

Т.е. был сделан в папке модуля image для его субмодуля image_attach.

Дополнительной сложностью для веб-мастеров, работающих под Windows будет то, что команды diff и patch в этой ОС отсутствуют. Если у вас нет доступа к командной строке сервера, то придется обзаводиться Windows-версией команды patch.
Одним из вариантов может быть UnxUtils. Как его использовать, я писал на страничке Утилиты Unix (Linux) для Windows - UnxUtils. Вам понадобится только один файл patch.exe скопировать в системную папку Windows и можете использовать все вышеописанное.

Если после применения заплатки появились какие-то проблемы в работе движка, то можно откатиться назад используя команду:

patch -p0 -R < path/file.patch

или
patch -R < file.patch

в зависимости от того, какой командой вы патчили изначально.

Хотя на мой взгляд проще сохранить все файлы исходных кодов модуля, а потом просто вернуть их на место заменив пропатченные файлы. Ведь ошибка может произойти из-за некорректной работы программы patch, в этом случае шансы на удачный откат так же становятся зыбкими.

Ручное редактирование файлов с кодом.

А если у вас нет желания или возможности ставить Unix-утилиты, или patch-файл невелик по объему его можно применить вручную. Контекстный формат патчей достаточно прост и нагляден.

После заголовка с именами файлов, патч состоит из контекстных блоков. Заголовок каждого блока начинается с @@ и заканчивается на @@. Первой цифрой после "двойной собаки" идет номер строки исходного файла, где начинается данный блок. В конце также может быть указано имя функции, к которой относится данный блок. Далее идут строки контекста исходного файла, строки добавляемые и строки удаляемые.

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

Строки начинающиеся со знака "минус" (-) требуется удалить из исходного файла.

Строки начинающиеся со знака "плюс" (+), соответственно добавить. Только не забывайте скопировав добавляемое в файл удалить с первых позиций все плюсы.

Все очень просто, но нудно и требует некоторой внимательности.

Примечания

Некоторые ошибки

Иногда происходит зацикливание выполнения команды patch, остановить которое можно только нажав Ctrl+C. Вывод при этом выглядит так:
File to patch:
Skip this patch? [y]
Skipping patch.
missing header for unified diff at line 620 of patch
can't find file to patch at input line 620
Perhaps you should have used the -p or --strip option?

И так далее увеличивая число в четвертой строке до бесконечности.

Связана эта ошибка с различиями символов конца строк в Unix (откуда эти патчи обычно родом ) и Windows (где мы их имеем несчастье применять). Чтобы избавится от этой проблемы требуется открыть файл в текстовом редакторе и пересохранить его выставив переводы строк в формате Windows. После этого повторить команду patch.

Другая ошибка

patching file `filename.ext'
Assertion failed: hunk, file patch.c, line 321

abnormal program termination

Диагноз тот же: Unix-окончания строк. Перед выполнением команды надо пересохранить файл патча в Windows-формате.

Справка по опциям команды patch

Usage: patch [OPTION]... [ORIGFILE [PATCHFILE]]

Input options:

-p NUM --strip=NUM Strip NUM leading components from file names.
-F LINES --fuzz LINES Set the fuzz factor to LINES for inexact matching.
-l --ignore-whitespace Ignore white space changes between patch and input.

-c --context Interpret the patch as a context difference.
-e --ed Interpret the patch as an ed script.
-n --normal Interpret the patch as a normal difference.
-u --unified Interpret the patch as a unified difference.

-N --forward Ignore patches that appear to be reversed or already applied.
-R --reverse Assume patches were created with old and new files swapped.

-i PATCHFILE --input=PATCHFILE Read patch from PATCHFILE instead of stdin.

Output options:

-o FILE --output=FILE Output patched files to FILE.
-r FILE --reject-file=FILE Output rejects to FILE.

-D NAME --ifdef=NAME Make merged if-then-else output using NAME.
-E --remove-empty-files Remove output files that are empty after patching.

-Z --set-utc Set times of patched files, assuming diff uses UTC (GMT).
-T --set-time Likewise, assuming local time.

Backup and version control options:

-b --backup Back up the original contents of each file.
--backup-if-mismatch Back up if the patch does not match exactly.
--no-backup-if-mismatch Back up mismatches only if otherwise requested.

-V STYLE --version-control=STYLE Use STYLE version control.
STYLE is either 'simple', 'numbered', or 'existing'.
-B PREFIX --prefix=PREFIX Prepend PREFIX to backup file names.
-Y PREFIX --basename-prefix=PREFIX Prepend PREFIX to backup file basenames.
-z SUFFIX --suffix=SUFFIX Append SUFFIX to backup file names.

-g NUM --get=NUM Get files from RCS or SCCS if positive; ask if negative.

Miscellaneous options:

-t --batch Ask no questions; skip bad-Prereq patches; assume reversed.
-f --force Like -t, but ignore bad-Prereq patches, and assume unreversed.
-s --quiet --silent Work silently unless an error occurs.
--verbose Output extra information about the work being done.
--dry-run Do not actually change any files; just print what would happen.

-d DIR --directory=DIR Change the working directory to DIR first.
--binary Read and write data in binary mode.

-v --version Output version info.
--help Output this help.

Report bugs to .

Источники на сайте Drupal:
http://drupal.org/patch/create
http://drupal.org/patch/apply
http://drupal.org/patch/apply

Спасибо за

Спасибо за статью.

Не за что.

Не за что. Заходите ещё.

Добавлю что поиск

Добавлю что поиск оптимального решения привел к использованию Eclipse. Кроме отличного CVS клиента там имеется и удобная патчилка :)

Ручное редактирование файлов

Ручное редактирование файлов с кодом не понятно. У меня есть файл image_gallery.patch и image_gallery.module. В image_gallery.patch есть следующая строка
@@ -78,6 +78,12 @@ function image_gallery_admin_settings()
Что значат -78,6 +78,12?

Далее идет код:

 '#size' => 3,
     '#description' => t('Sets the number of images to be displayed in a gallery page.'),
   );
+  $form['gallery']['image_gallery_hide_empty_galleries'] = array(
+    '#type' => 'checkbox',
+    '#title' => t('Hide empty galleries'),
+    '#default_value' => variable_get('image_gallery_hide_empty_galleries', 0),
+    '#description' => t('When enabled, empty galleries will not be displayed.'),
+  );
   $form['gallery']['image_gallery_node_info'] = array(
     '#type' => 'checkbox',
     '#title' => t('Display node info'),

Что требуется заменить в файле image.module? C 78 строки?

То ли я не по-русски пишу, толи у вас кодировка не та?

Вроде внятно всё пояснил:

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

 '#size' => 3,
     '#description' => t('Sets the number of images to be displayed in a gallery page.'),
   );

Это контекст от которого вам надо начинать.
   $form['gallery']['image_gallery_node_info'] = array(
     '#type' => 'checkbox',
     '#title' => t('Display node info'),

Это контекст, который в исходном файле идёт сразу после первого фрагмента. Его тоже не надо трогать.

Я не разбирался досконально с форматом файлов diff, всего лишь преследовал практические цели, но простая наблюдатетельность позволила мне заметить, что первая цифра после @@ означает номер строки исходного файла. Дальнейшее думаю нагуглите сами, если вам интересно.

Строки начинающиеся со знака "минус" (-) требуется удалить из исходного файла.

В вашем случае их нет.

Строки начинающиеся со знака "плюс" (+), соответственно добавить. Только не забывайте скопировав добавляемое в файл удалить с первых позиций все плюсы.

+  $form['gallery']['image_gallery_hide_empty_galleries'] = array(
+    '#type' => 'checkbox',
+    '#title' => t('Hide empty galleries'),
+    '#default_value' => variable_get('image_gallery_hide_empty_galleries', 0),
+    '#description' => t('When enabled, empty galleries will not be displayed.'),
+  );

Ставим это между приведёнными выше двумя кусками и убираем плюсы. Что непонятного?

^(

Пипец... я уже 3 часа гуглю и нигде! не могу толком найти обьяснения одному вопросу:
@@ -78,6 +78,12 @@
то, что -78 - это строка, которую надо удалить легко догадаться и я давно догадался;
то, что +78 - это строка, которую надо записать - тоже;
НО ЧТО ЗНАЧАТ ЦИФРЫ ПОСЛЕ ЗАПЕТЫХ: 6 И 12, КОТОРЫЕ ИДУТ ПОСЛЕ 78 ????
Мозги плавятся, голова болит - нигде об этом не написано. Может, Вы объясните???

что то не могу понять что тут

что то не могу понять что тут пишется

Описание работы с

Описание работы с parch-файлами