利用rpmbuild打包,需要兩類文件:1、源碼,源碼以tar歸檔進行壓縮的源碼包,以及一些.patch文件,存放於目錄./SOURCES下;2、.spec文件,定義了打包的動作,以及依賴,是打包的最主要類容。
首先介紹SPEC文件:
SPEC文件的一些語法:
.spec中的條件判斷語句有兩種:
1、if結構
引用
%if %{str}
%else
動作
%endif
其中%{str}是條件,0為假,非0為真。
2、?:結構
引用
%{?變量:動作1}動作2
其中{}用於控制范圍,而“?”號和“:”號是分割符,如果要判斷條件是非的情況,可以在“?”號前加“!”號。
此條件與前面的%if有點不同,其只判斷變量是否定義,定義了就為真,否則就為假,即使變量定義為0,也為真,並運行后面的語句。
spec文件的一些定義:
Name: #軟件包的名稱
Version: #軟件包的版本號
Release: #發布的序列
Epoch: #發布的序列
Summary: #摘要
Group: #組描述
License: 發行許可證
Sources[0-n]: #打包的源碼包
Patch0: *.patch #補丁文件
BuildRequires: #打包時依賴的軟件
Requires: #安裝此rpm包時依賴的軟件包
BuildRoot: #安裝此軟件的虛擬根目錄
以上是描述性的元素,其中Epoch:Version:Release表示了rpm包的新舊,優先級依次降低,打出的rpm包也是以${package}-${Version}-${Release}命名。
spec文件主體內容:
spec文件中引用的一些宏變量主要定義在/usr/lib/rpm/macros中
主要有三個階段:
%pre
#預處理階段,解壓縮軟件包
%setup
%setup 不加任何選項,僅將軟件包打開。 %setup -n newdir 將軟件包解壓在newdir目錄。 %setup -c 解壓縮之前先產生目錄。 %setup -b num 將第num個source文件解壓縮。 %setup -T 不使用default的解壓縮操作。 %setup -T -b 0 將第0個源代碼文件解壓縮。 %setup -c -n newdir 指定目錄名稱newdir,並在此目錄產生rpm套件。 %patch 最簡單的補丁方式,自動指定patch level。 %patch0 -p0 打第1個補丁,利用當前相對路徑名稱 %pacth1 -p2 打第2個補丁,忽略補丁文件第一層目錄 %patch 0 使用第0個補丁文件,相當於%patch ?p 0。 %patch -s 不顯示打補丁時的信息。 %patch -T 將所有打補丁時產生的輸出文件刪除。
%build 編譯階段
./configure --prefix=$RPM_BUILD_ROOT/usr
make
or
%configure #可以用rpm –eval '%configure'命令查看該宏
make
在openstack項目中直接是:python setup.py build
%install 將軟件安裝到虛擬根目錄
常用命令:
make DESTDIR=$RPM_BUILD_ROOT install
install [options] src ${RPM_BUILD_ROOT}/${dst} #安裝配置文件至指定目錄,相當於cp
建立連接關系等。
在openstack 項目中:
%{_python2} setup.py install -01 --skip-build --root %{buildroot}
%clean
清理一些臨時文件,或是生產中不需要的文件
%files [name]
文件和目錄的歸檔,rpm包真正包含的內容,$name 與package name對應,一個package生成一個rpm包,名字${name}-¥{version}-${release}.rpm。若沒有name,則即是spec Name項。
files是相對路徑,應用宏或變量表示相對路徑:
如果描述為目錄,表示目錄中除%exclude外的所有文件。
%defattr (-,root,root) 指定包裝文件的屬性,分別是(mode,owner,group),-表示默認值,對文本文件是0644,可執行文件是0755
%changelog 變更日志
一般會把git log記錄輸入,openstack文件中記錄的日志:
git rev-parse --abbrev-ref HEAD >> *.spec
git log --pretty=oneline --abbrev-commit | head -n +1 >> *.spec
#生成patch的命令
diff -Naur path/to/A_Project path/to/B_Project > Project.patch (A是原始項目)
或者利用 git命令:
#new 是有更改的分支,old是沒有更改的分支 git checkout new git format-patch -M old 生成:000-*.patch
git打patch的命令:
git am 000-*.patch
#解析rpm包
rpm -qpl *.rpm #列出rpm包包含的內容
rpm2cpio *.rpm | cpio -div #解壓縮出rpm包
yum-duilddep *.spec 安裝spec文件中的所有編譯依賴軟件,BuidRequires。
rpmbuild --define "_topdir ${dir:-/home/rpmbuild}" -bb *.spec
_topdir指定打包的目錄,rpmbuild/{SURCES,BUILD,BUILDROOT,SPECS,RPMS,SRPMS}。
也可以向spec文件傳入參數,也是利用--define
