Home > FreeBSD, Technical Miscellany > Enabling mrepo Support for FreeBSD Packages

Enabling mrepo Support for FreeBSD Packages

Enabling mrepo Support for FreeBSD Packages

mrepo is a content management application for Yum/APT RPM Repositories which does not support FreeBSD packages. While this is not necessarily an elegant solution, it’s enough to enable support for FreeBSD packages and can get one started in deploying a more proper implementation.

Enabling preliminary support for FreeBSD packages involves the following procedure. This procedure assumes repos are available via HTTP at the location where content is downloaded from. We also assume a web server is installed and configured to serve mrepo content. Any discussion involving the configuration of these components is beyond the scope of this post.

  1. Apply the patch below to the mrepo.conf and add some FreeBSD repos
  2. Update the local mrepo repositories
  3. Execute `find` symlinking to the updated content
  4. Setup cronjobs to update repos periodically

Applying The Patch

This patch was generated with GNU patch on RHEL6 and should be applied using GNU patch in the following manner to minimize potential issues. It patches the mrepo script, mrepo.conf, and adds three mrepo repositories. The patch:

diff -u usr/bin/mrepo usr/bin/mrepo.new
--- usr/bin/mrepo	2011-07-01 21:16:09.000000000 -0400
+++ usr/bin/mrepo.new	2013-09-26 12:10:22.072081702 -0400
@@ -214,6 +214,7 @@
         self.lftpcleanup = self.getoption('main', 'lftp-cleanup', 'yes') not in disable
         self.lftpexcldebug = self.getoption('main', 'lftp-exclude-debug', 'yes') not in disable
         self.lftpexclsrpm = self.getoption('main', 'lftp-exclude-srpm', 'yes') not in disable
+        self.lftpincltbz = self.getoption('main', 'lftp-include-tbz', 'yes') not in disable
         self.lftpoptions = self.getoption('main', 'lftp-options', '')
         self.lftpcommands = self.getoption('main', 'lftp-commands', '')
         self.lftpmirroroptions = self.getoption('main', 'lftp-mirror-options', '-c -P')
@@ -1282,6 +1283,8 @@
         mirroropts = mirroropts + ' -X \"*.src.rpm\" -X \"/SRPMS/\"'
     if cf.lftpexcldebug:
         mirroropts = mirroropts + ' -X \"*-debuginfo-*.rpm\" -X \"/debug/\"'
+    if cf.lftpincltbz:
+        mirroropts = mirroropts + ' -I \"*.tbz*\"'
     ret = run('%s %s -c \'%s mirror %s %s %s\'' % (cf.cmd['lftp'], opts, cmds, mirroropts, url, path),dryrun=True)
     if ret:
diff -ruN etc/mrepo.conf newetc/mrepo.conf
--- etc/mrepo.conf	2013-09-30 10:57:32.036840555 -0400
+++ newetc/mrepo.conf	2013-09-30 09:08:34.960901787 -0400
@@ -1,4 +1,4 @@
+### Configuration file for mrepo
 ### The [main] section allows to override mrepo's default settings
 ### The mrepo-example.conf gives an overview of all the possible settings
@@ -23,3 +23,5 @@
 hardlink = no
 shareiso = no
 rhnget-download-all = yes
+lftp-include-tbz = yes
diff -ruN etc/mrepo.conf.d/FreeBSD-8-x86_64-dev.conf newetc/mrepo.conf.d/FreeBSD-8-x86_64-dev.conf
--- etc/mrepo.conf.d/FreeBSD-8-x86_64-dev.conf	1969-12-31 19:00:00.000000000 -0500
+++ newetc/mrepo.conf.d/FreeBSD-8-x86_64-dev.conf	2013-09-30 10:59:07.834704096 -0400
@@ -0,0 +1,5 @@
+name = FreeBSD 8.x Packages - Dev Repo
+release = 8
+metadata = yum repomd
+dev-repo = $url_to_the_development_repo
diff -ruN etc/mrepo.conf.d/FreeBSD-8-x86_64-prod.conf newetc/mrepo.conf.d/FreeBSD-8-x86_64-prod.conf
--- etc/mrepo.conf.d/FreeBSD-8-x86_64-prod.conf	1969-12-31 19:00:00.000000000 -0500
+++ newetc/mrepo.conf.d/FreeBSD-8-x86_64-prod.conf	2013-09-30 10:59:18.794803601 -0400
@@ -0,0 +1,5 @@
+name = FreeBSD 8.x Packages - Production Repo
+release = 8
+metadata = yum repomd
+prod-repo = $url_to_the_production_repo
diff -ruN etc/mrepo.conf.d/FreeBSD-8-x86_64-qa.conf newetc/mrepo.conf.d/FreeBSD-8-x86_64-qa.conf
--- etc/mrepo.conf.d/FreeBSD-8-x86_64-qa.conf	1969-12-31 19:00:00.000000000 -0500
+++ newetc/mrepo.conf.d/FreeBSD-8-x86_64-qa.conf	2013-09-30 10:59:28.171888437 -0400
@@ -0,0 +1,5 @@
+name = FreeBSD 8.x Packages - QA Repo
+release = 8
+metadata = yum repomd
+qa-repo = $url_to_the_qa_repo

are applied by executing the following respectively for each patch after the patches have been downloaded:

# cd / && patch < mrepo.patch

Note this patch includes variables that should be replaced by URLs where the repos exist. This URL could be the URL to FreeBSD’s binary package repos, but the size of the repo could cause some issues with this process, especially the step below where the symlinks are generated. My use case involves HTTP repos of home grown FreeBSD packages.

This patch can also be modified to enable support for other file types. For example, tgz and txz files which are supported in FreeBSD’s new pkg framework. which will be default in FreeBSD 10.0-RELEASE. Doing so would enable support for FreeBSD 10 ‘pkg’ files to mrepo as well.

Updating The Repositories

mrepo repositories are updated by executing the patched mrepo script as described here:

# mrepo -ug dev-repo
# mrepo -ug qa-repo
# mrepo -ug prod-repo

These commands update each of the above repos [ included in the patch ] according to srcdir and wwwdir specified in mrepo.conf. Therefore, content downloads to srcdir and wwwdir will be updated in the next step.

Symlink Content

mrepo downloads content from the URLs specified in the mrepo config files located in /etc/mrepo.conf.d/. The FreeBSD-8-x86_64-*.conf repositories in this case. The files are symlinked to from the repo identified by the combination of the value in wwwdir specified in /etc/mrepo.conf and the repo name. This is done by executing the following:

# cd $wwwdir/$repodir && find $srcdir/$repo –type f –name '*tbz' -exec ln –s {} . \;

Where $wwwdir and $srcdir are taken from /etc/mrepo.conf and $repodir is actual directory name of the repo on disk. This step should be executed for each of the repos. Completion of this step means the repos are now available via HTTP.

Configure Cronjobs

It is generally considered a good idea to enable periodic updates of mrepo repos. This can be done in any number of ways, including cronjobs. I choose cronjobs here for simplicity’s sake. Your cronjobs may look similar to the following:

0 0 1 * * mrepo -ug $repo && cd $wwwdir/$repo && find $srcdir/$repo –type f –name ‘*tbz’ -exec ln –s {} . \;

Where $repo is the repo tag specified in it’s config file in /etc/mrepo.conf.d/, $srcdir and $wwwdir are as specified in /etc/mrepo.conf.

Make Content Available Via Cobbler

Some technologists may employ provisioning platforms to distribute OS and package repo contents throughout an environment. I utilize Cobbler in my environments. Therefore, an additional one-time step to create the Cobbler repo is necessary for each repo.

Once the symlinks are created in $wwwdir/$repo, one can add the repo to Cobbler making it available there. This is done by executing:

# cobbler repo add --name="$repo_name" --breed="rsync" --mirror="$wwwdir/$repo"

The new repos will be updated any time a `cobbler reposync` is executed.


This blog is posted for informational purposes only. Extensive testing is recommended prior to implementing changes discussed here.

  1. No comments yet.
  1. No trackbacks yet.

Leave a Reply

Fill in your details below or click an icon to log in:

WordPress.com Logo

You are commenting using your WordPress.com account. Log Out / Change )

Twitter picture

You are commenting using your Twitter account. Log Out / Change )

Facebook photo

You are commenting using your Facebook account. Log Out / Change )

Google+ photo

You are commenting using your Google+ account. Log Out / Change )

Connecting to %s

%d bloggers like this: