Friday, November 4, 2011

Using MOCK to build packages for RHEL distros

MOCK is a python based powerful package build tool ( I would have called it a system, but it is basically rpmbuild under chroot ). I use it a lot, mainly because the servers I am working on are RHEL and my workstation is Fedora. It is very powerful, because it enables you to build packages in a chroot environment and build them on a RHEL based distro, for any RHEL based distro or architecture, either from source or source RPM. It is no wonder this is what the guys from RHEL are using to build the packages for all distros. First, you must install it.
yum install mock
should do it. Then, you must add your user to the mock group, since mock requires root permissions - for chroot and such.
root@localhost$ usermode -aG mock [your-user] 
Now you are ready to experience the power of MOCK. Its configuration files are in /etc/mock/ (surprise surprise). There is a global confguration file - /etc/mock/site-defaults.cfg , and there are the distro configuration files - like epel-5-i386.cfg, epel-5-x86_64.cfg - each containing the distro specific configurations. The global configuration variables ( /etc/mock/site-defaults.cfg ) cant be overwritten in each of the config files. The options I find most useful are
#This uses the pigz instead of gzip
#Pigz is way faster on multi-core systems (uses parallel processing) with zipping/unzipping
#You should yum install it if it is not already installed

config_opts['plugin_conf']['root_cache_opts']['compress_program'] = "pigz"

# bind mount plugin is enabled by default but has no configured directories to mount
#It is used to bind mount a directory in your direcotry tree to MOCK's chroot
#They are specified in ("root_dir","chroot_dir") tuples, using python "append" list method ( For PythonProgrammers: extend, insert and other list methods should also work)

config_opts['plugin_conf']['bind_mount_enable'] = True
config_opts['plugin_conf']['bind_mount_opts']['dirs'].append(('/opt/intel', '/opt/intel' ))

#This should mount /var/lib/mock/ in your ramdisk, but for some reason, 
#this does not work for men, so a workaround is presented*

#config_opts['plugin_conf']['tmpfs_enable'] = True
#config_opts['plugin_conf']['tmpfs_opts']['required_ram_mb'] = 16384
#config_opts['plugin_conf']['tmpfs_opts']['max_fs_size'] = '8192m'
*Workaround for TMPFS Add this to /etc/fstab
mock_root                       /var/lib/mock/          tmpfs   uid=0,gid=395,mode=02775  0 0 # Gid should be the GID of the MOCK group
And
mount -a
Using mock is fairly simple:

Build SRPM

mock -r epel-5-x86_64 --buildsrpm --sources="build_source.tar.bz" --spec "build_spec.spec" --resultdir="$HOME/mock/output/" --no-cleanup-after
-r - specifies the build distro and architecture
--buildsrpms - tells mock it should build SOURCE RPM
--spec - the spec file mock should use when building the script
--resultdir - where the output and logs of mock execution will be put
--no-cleanup-after - tells mock it should not delete its chroot when finished (good for debbugging)

Build RPM from SRPM

mock -r epel-5-x86_64 --no-clean --rebuild "/home/[user]/mock/output/*.src.rpms" --resultdir="$HOME/mock/output/" --no-cleanup-after
--noclean - tells mock not to clean up the chroot env before building ( clean means *delete* and *rebuild*)

Install package to chroot from outside chroot

This is the only way since the chroot does not have its own YUM. If you want to
mock -r  epel-5-x86_64 --install compat-libstdc++-33.x86_64 man --resultdir="$HOME/mock/output/"
--install - this will install packages specified inside MOCK chroot

Copy files inside chroot

mock -r  epel-5-x86_64 --copyin /tmp/stuff --resultdir="$HOME/mock/output/"
--copyin - copies files inside the MOCK chroot, use this only when mount bind is not possible

Initialize chroot without building anything

mock -r  epel-5-x86_64 --init --resultdir="$HOME/mock/output/"

Clean/Remove chroot

mock -r  epel-5-x86_64 --clean --resultdir="$HOME/mock/output/"

Open a shell in the chroot

mock -r  epel-5-x86_64 --shell --resultdir="$HOME/mock/output/"
NB! Without --resultdir all mock commands fail

No comments:

Post a Comment