Как передать аргумент имени файла gitconfig diff textconv?

#git #diff #git-config

#git #diff #git-config

Вопрос:

Документация по textconv at https://git.wiki.kernel.org/index.php/Textconv имеет лаконичную формулировку:

~/.gitconfig необходимо указать команду для выполнения драйвера textconv:

 [diff "<driver_name>"]
    textconv=<command>
  

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

 [diff "pdf"]
    textconv = pdftotext -layout "$1" -
  

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

Есть ли способ обойтись без этих скриптов? Соглашение "$1" or xargs '{}' для аргументов, похоже, не работает.

Ответ №1:

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

 [diff "pdf"]
    textconv = sh -c 'pdftotext -layout -enc UTF-8 "$0" -'
  

(найдено здесь: https://gist.github.com/t-yuki/9348e5d4aa4a75a6acf9 )

Комментарии:

1. Спасибо! Это не идеально, с вызовом вложенной оболочки; но поскольку это работает и помогает мне сэкономить на дополнительных файлах сценариев оболочки, я приму это как новый ответ! хороший

2. Если в Windows Git включен mingw64 pdftotext, он должен быть таким: [diff «pdf»] textconv = sh -c ‘pdftotext -layout -enc UTF-8 «$ 0» -‘

Ответ №2:

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

 temp = prepare_temp_file(r, spec->path, spec);
*arg   = pgm;
*arg   = temp->name;
*arg = NULL;


child.use_shell = 1;
child.argv = argv;
child.out = -1;
if (start_command(amp;child)) {
    remove_tempfile();
    return NULL;
}
  

Два аргумента — это имя самой программы (argv[0], как обычно) и имя временного файла, содержащего биты, извлеченные из того места, где они находятся (на основе spec параметра; перейдите по ссылке выше для получения дополнительной информации).

Спецификация, вероятно, действительно содержит исходное имя пути в большинстве или во всех случаях (а если нет, посмотрите на функцию чуть ниже этой), она просто не копируется в аргументы программы. Код фильтра textconv может, но не использует метод % -expansion, используемый драйверами слияния Git, и если это так (но это не так), он может иметь % -escape, который передает исходное имя файла. Но, конечно, это не так.

(Вы можете создать свой собственный клон Git и поработать над ним, и, возможно, попытаться убедить людей из Git принять ваше изменение как вклад в общедоступный Git …)