Есть ли какой-либо синтаксис или трюк, чтобы создать многострочный макрос файла спецификации rpm?

Задний план.

$ rpmbuild --version
RPM version 4.3.3

Я работаю над файлом спецификаций, который должен обрабатывать список файлов в нескольких сценариях. DRY (не повторяйтесь) заставляет меня определить список один раз как макрос, который расширяется в различные вспомогательные сценарии. Ведение списка - это боль, так как я не видел способа избежать размещения всех файлов в одной строке.

%define LIST \
a \
b 

выдает ошибку

%define LIST a\
b\

тоже выдает ошибку

%define LIST a
%define LIST %LIST b

Сбой из-за ошибки рекурсии


person Chaim Geretz    schedule 02.12.2010    source источник


Ответы (6)


Вы не можете создавать многострочные макросы в файле спецификаций так, как вы можете это сделать в файле ~/.rpmmacros. Как-то глупо.

Я создаю подкаталог SPECS/inc/ со спецификациями, которые действуют как многострочные макросы, используемые всеми пакетами, созданными для моего сайта. Вместо того, чтобы использовать макросы как %foo, вы можете просто сделать %include inc/foo.spec. Вы также можете создавать ярлыки, чтобы избежать синтаксиса включения %global foo %include inc/foo.spec. Тогда он работает так же, как многострочный макрос.

Вот полный пример.

inc/env.spec

%global foo %include inc/foo.spec
%global bar %include inc/bar.spec
#Lots of other common things to all packages

inc/foo.spec

a
b
c
d

И затем в моем файле спецификации пакета, mylib.spec:

%include inc/env.spec

Name: mylib
Version: X.Y
#etc...

%foo
person Matthew Fioravante    schedule 08.05.2014
comment
Это действительно умное решение! Спасибо!! - person Amol; 28.06.2019

Поскольку вы немного подробнее объяснили свою цель, давайте попробуем другой подход. Попробуйте это в своем файле спецификации:

Source1:        flist

%{expand:%global LIST %(cat %{SOURCE1})}

И это в файле Source1 (в данном случае flist):

a \
b \
c 

Я тестировал это с rpm 4.4.6, так как это самая старая версия, доступная мне на данный момент.

person Stan    schedule 28.04.2012
comment
Это не работает на CentOS4, у которого закончился срок службы и древняя версия RPM. К сожалению, это то, с чем ОП и ваш покорный слуга пытаются работать. Хотя, безусловно, это самое близкое к решению. - person chutz; 13.11.2012

В определениях макросов обратная косая черта в конце строки удаляется и используется для указания RPM, что определение макроса продолжается. Символ новой строки НЕ удаляется (в отличие от make-файла). Поэтому, если вы создаете многострочный скрипт, точка с запятой не нужна. Это также означает, что если вы разделяете одну команду, вы должны использовать обратную косую черту 3. Два, чтобы получить обратную косую черту, которую увидит оболочка, и один, чтобы указать rpmbuild продолжать синтаксический анализ макроса. Оболочка удалит обратную косую черту, а также новую строку, и это даст одну команду в две строки. Вау !!

person Bruce K    schedule 14.05.2012
comment
%define MAKE make \\\ name=TODO \\\ help \\\ - person RzR; 23.11.2017

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

%define LIST a\
b\
c

Это определение макроса будет работать. Если вы планируете использовать их как команды, т.е. что-то вроде

%define DOSOMETHING rm file1\
rm file2\
rm file3
...
%build
%DOSOMETHING

так не пойдет. Строки в исполняемых разделах сначала разбиваются на отдельные команды, ЗАТЕМ раскладываются макросы. т.е. определение макроса будет работать, а выполнение его как трех отдельных команд — нет.

Если вы хотите выполнить 3 отдельные команды, проще сделать это так:

%define DOSOMETHING rm file1; rm file2; rm file3
person m1tk4    schedule 04.12.2010
comment
Приведенное выше решение не работает для меня, возможно, оно может работать для других версий rpmbuild. Я получаю сообщение об ошибке: ошибка: строка 31: Неизвестный тег: b\ Отредактировал вопрос, чтобы отразить это. - person Chaim Geretz; 06.12.2010

На вашем месте я бы сохранил список в исходном файле.

Содержание %{_sourcedir}/LIST:

a
b
c
d

В файле спецификации:

%define process_files() \
    for i in %(cat %{_sourcedir}/LIST)
    do \
        echo "process list of files here" \
    done
person djhaskin987    schedule 15.10.2013

Этот пример должен работать:

cat file.spec

%define MAKE make \\\
 status=success \\\
 #EOL

%build
${MAKE}


cat Makefile

status?=fail
default: 
    echo "status=${status}"
person RzR    schedule 22.11.2017