昔我往矣

rpm打包过程浅析

2015年08月30日

在解释打包spec文件之前,先说说两种打包常用的方式,以Python为例,CentOS6上默认是Python2.6,但是现在更常用的是Python2.7,为了满足环境要求,好几次在生产环境编译安装Python2.7,烦了之后就想自己打个CentOS6上的rpm包。打包的命令是rpmbuild,先安装rpmbuid:

# yum -y install rpm-build

打包Python的实例

再安装编译Python2.7.10的依赖:

# yum -y install autoconf bzip2-devel db4-devel \
expat-devel gmp-devel libffi-devel libGL-devel \
libX11-devel ncurses-devel openssl-devel \
readline-devel sqlite-devel tcl-devel tix-devel \
tk-devel zlib-devel

下载最新版的Python和我们需要的Spec文件:

# wget https://www.python.org/ftp/python/2.7.10/Python-2.7.10.tgz
# wget https://raw.githubusercontent.com/lihz1990/rpm-specs/master/python2.7.10.spec

方法一:从tarball中编译打包文件

步骤,先解压原来的压缩包,然后把spec文件存放到解压目录下,重新打包再编译!

# tar xvf Python-2.7.10.tgz
# mv python2.7.10.spec Python-2.7.10
# tar czvf Python-2.7.10.tgz Python-2.7.10

完成上面的操作之后,开始打包:

# rpmbuild -tb Python-2.7.10.tgz

如果不出依赖问题,就会顺利完成安装!so easy!

方法二:建立打包目录再打包

# mkdir -p rpmbuild/{BUILD,BUILDROOT,RPMS,SOURCES,SPECS,SRPMS}
# cp Python-2.7.10.tgz rpmbuild/SOURCES
# cp python2.7.10.spec rpmbuild/SPECS

然后开始打包:

# rpmbuild -bb rpmbuild/SPECS/python2.7.10.spec

两种方法的实质其实是一样的,直接从tarball打包也会在当前目录生成rpmbuild/{BUILD,BUILDROOT,RPMS,SOURCES,SPECS,SRPMS}, 只不过是rpmbuild命令帮助创建了这些目录而已。
编译会花一些时间,编译完成之后就可以去寻找你编译好的rpm包了,路径是rpmbuild/RPMS/x86_64/

# ls rpmbuild/RPMS/x86_64/         
python27-2.7.10-2.x86_64.rpm  
python27-debuginfo-2.7.10-2.x86_64.rpm  
python27-devel-2.7.10-2.x86_64.rpm

spec配置文件分析

知道了怎么打包,我们再来看看神奇的spec文件的内容,有些软件会有官方的spec文件,甚至就放在源码tarball里面,还有很多软件并不提供spec文件,又或者我们自己写了软件,要打成rpm包,这就需要学习sepc文件的语法了。我们简单分析下上面的python2.7.10.spec文件!

%define binsuffix 27   
%define pybasever 2.7
%define version 2.7.10
%define name python
%define release 2    #以上define定义变量用

Name: %{name}%{binsuffix} #Name是软件的名字,%{name},{binsuffix}是上面定义的变量
Version: %{version} # 版本,引用上面的变量
Release: %{release} # 软件的释出号,小的bug修复,可以把该值+1
Summary: An interpreted, interactive, object-oriented programming language.  # 一句话概括包信息 
Group: Development/Languages  # 软件所属的组类别,yum grouplist 可以看到所有组
Source0: Python-%{version}.tgz # 源码程序包的名字

License: PSF  # 采用的协议
BuildRoot:  %(mktemp -ud %{_tmppath}/%{name}-%{version}-%{release}-XXXXXX) # 这个是安装或编译时使用的虚拟目录

AutoReq: no # 指示RPM是否自动查找软件所需的共享库,仅当域值为no或0时,RPM不执行find-requires程序,否则均执行该程序。
Provides: python(abi) = %{pybasever} # 指明本软件一些特定的功能,以便其他rpm识别

BuildRequires: autoconf  
BuildRequires: bzip2
BuildRequires: bzip2-devel
BuildRequires: db4-devel 

# expat 2.1.0 added the symbol XML_SetHashSalt without bumping SONAME.  We use
# it (in pyexpat) in order to enable the fix in Python-3.2.3 for CVE-2012-0876:
BuildRequires: expat-devel

BuildRequires: findutils
BuildRequires: gcc-c++
BuildRequires: glibc-devel
BuildRequires: gmp-devel
BuildRequires: libffi-devel
BuildRequires: libGL-devel
BuildRequires: libX11-devel
BuildRequires: make
BuildRequires: ncurses-devel
BuildRequires: openssl-devel
BuildRequires: pkgconfig
BuildRequires: readline-devel
BuildRequires: sqlite-devel


BuildRequires: tar
BuildRequires: tcl-devel
BuildRequires: tix-devel
BuildRequires: tk-devel

BuildRequires: zlib-devel  # 编译时所需要的依赖

%description
Python is an interpreted, interactive, object-oriented programming
language.  It incorporates modules, exceptions, dynamic typing, very high
level dynamic data types, and classes. Python combines remarkable power
with very clear syntax. It has interfaces to many system calls and
libraries, as well as to various window systems, and is extensible in C or
C++. It is also usable as an extension language for applications that need
a programmable interface.  Finally, Python is portable: it runs on many
brands of UNIX, on PCs under Windows, MS-DOS, and OS/2, and on the
Mac.   # 关于本软件的描述

%package devel # 生成子包,子包的名字是上面的Name-devel,devel是这个%package指定的
Summary: The libraries and header files needed for Python extension development. 
Requires: %{name} = %{version}-%{release} 
Group: Development/Libraries   

%description devel
The Python programming language's interpreter can be extended with
dynamically loaded extensions and can be embedded in other programs.
This package contains the header files and libraries needed to do
these types of tasks.

Install python-devel if you want to develop Python extensions.  The
python package will also need to be installed.  You'll probably also
want to install the python-docs package, which contains Python
documentation. # 以上是devel子包的信息,意义一样

%prep # 这个段是预处理段,通常用来执行一些解开源程序包的命令,为下一步的编译安装作准备
%setup -n Python-%{version}  # 把源码包解压并放好 


%build  # 开始构建包
%configure --enable-unicode=ucs4 --enable-shared --prefix=%{_prefix}  # rpm定义的标准宏命令。意思是执行源代码的configure配置
%{__make} %{?_smp_mflags} # make,以及优化参数,__make是内建宏,可以在/usr/lib/rpm/macros中看到


%install   # 安装
%{__rm} -rf $RPM_BUILD_ROOT #删除旧数据
%{__make} install DESTDIR=$RPM_BUILD_ROOT #开始安装
%{__rm} -f $RPM_BUILD_ROOT%{_prefix}/bin/python{,2}
%{__rm} -f $RPM_BUILD_ROOT%{_prefix}/bin/python{,2}-config
%{__rm} -f $RPM_BUILD_ROOT%{_prefix}/bin/2to3
%{__rm} -f $RPM_BUILD_ROOT%{_prefix}/bin/idle
%{__rm} -f $RPM_BUILD_ROOT%{_prefix}/bin/pydoc
%{__rm} -f $RPM_BUILD_ROOT%{_prefix}/bin/smtpd.py
%{__rm} -rf $RPM_BUILD_ROOT%{_libdir}/pkgconfig/ 
%{__ln_s} %{_libdir}/python2.7/config $RPM_BUILD_ROOT%{_prefix}/lib/python2.7/config
%{__ln_s} %{_libdir}/python2.7/lib-dynload $RPM_BUILD_ROOT%{_prefix}/lib/python2.7/lib-dynload  #建立软连接

%clean
%{__rm} -rf $RPM_BUILD_ROOT  #删除安装数据


%files   # 文件段,用于定义软件包所包含的文件,分为三类--说明文档(doc),配置文件(config)及执行程序,还可定义文件存取权限,拥有者及组别。
%defattr(-,root,root,-)  # 定义缺省的权限
%{_prefix}/lib/python2.7/*  # 
%{_libdir}/python2.7/lib-dynload/*
%{_libdir}/libpython2.7.so*
%{_bindir}/python2.7*
%{_prefix}/lib/python2.7/config
%{_libdir}/python2.7/config/Makefile
%{_prefix}/include/python2.7/pyconfig.h  # 这里的_prefix,_libdir,_bindir等都是在/usr/lib/rpm/macros定义好了的

%doc  #告诉rpm,这是文档文件
%{_mandir}/man1/* 

%files devel  # devel子包所包含的文件
%defattr(-,root,root,-)
%{_prefix}/include/python2.7/*
%{_libdir}/python2.7/config/*
%{_prefix}/lib/python2.7/config   #意义同上

%changelog
* Sun Aug 30 2015 lihz1990  <graylc@163.com> - 2.7.10-1  
- Initial RPM release   #变更日志

spec文件还有很多这里没有使用的属性,比如Packager: 可以写上打包人的名字,有兴趣可以详细研究下。/usr/lib/rpm/macros是rpm的宏配置文件,还有~/.macros是用户本地配置文件(可能没有)。祝你们玩的愉快!

参考文档:http://www.rpm.org/max-rpm/

当前暂无评论 »

添加新评论 »