How to set up an APT repository?
Just set up a simple but signed repository on a webserver. Because most other tutorials are somewhat dated or cumbersome, I'll try to replicate the procedure here. The initial configuration takes a bit of effort, but the simple build script keeps it easy to manage. And you can just drop in new *.deb
files, then update, or let a cron job handle that.
Generate some signing keys
First you need to create a gpg
signing key for packages and your repository. Make it a (4) RSA signing key, no password, and give it a unique $KEYNAME
when asked for. (Further examples assume "dpkg1
" as keyname.)
gpg --gen-key
gpg -a --export-secret-key dpkg1 > secret.gpg
gpg -a --export dpkg1 > public.gpg
I said no password, because your webserver has no builtin monkey to type it in repeatedly. And the signed packages and repository are only meant to satisfy the update-managers complaints about that. Just upload both keys to the new /apt/
repository directory on your webserver, but delete the secret.gpg
key after initialization.
Update CGI script
This is the simple update shell/CGI script for it:
#!/bin/sh
echo Status: 200 Okay
echo Content-Type: text/plain
echo
echo Rebuilding APT repository:
{
#-- settings
export GNUPGHOME=/var/www/usr12345/files
export KEYNAME=dpkg1
#-- one-time setup
if [ ! -e "$GNUPGHOME/secring.gpg" ] ; then
gpg --import -v -v ./secret.gpg
gpg --import -v -v ./public.gpg
gpg --list-keys
fi
#-- symlink .deb files from adjacent sub-directories
find .. -name '*.deb' -exec ln -s '{}' . \;
#-- build Packages file
apt-ftparchive packages . > Packages
bzip2 -kf Packages
#-- signed Release file
apt-ftparchive release . > Release
gpg --yes -abs -u $KEYNAME -o Release.gpg Release
} 2>&1
The three gpg
lines only need to be executed once, to initialize the GPG setup in some directory $GNUPGHOME
(above the document root). Delete only the secret.gpg
after success.
One unique feature of this small shell script is that it accepts any *.deb
files that you drop in, but also searches recursively (starting from one level up) for others, and symlinks them in. (Needs .htaccess Options FollowSymLinks
eventually.)
You can either execute this script manually as CGI or per cron-job. But hide it, or better yet move it out of the document root.
Because it's a "trivial" apt repository it needs the following apt-sources.list
entry:
deb http://example.org/deb/ ./ # Simple signed repo
That's suitable for single-architecture repositories, and if you don't expect hundreds of packages.
Package signing
Signing your individual packages is also trivial, once you've set up your gpg keys:
dpkg-sig -k dpkg1 -s builder *.deb
(This should be done on the workstation where packages are built, not on the repository webserver.)
Unsigned repository
If you don't need signed packages, then you could slash the update script down to just:
dpkg-scanpackages . > Packages
bzip2 -kf Packages
Which can still be used by average users, but needs a custom flag for apt.sources
:
deb [trusted=yes] http://apt.example.org/deb/ ./
But please don't use the trusted=yes
flag habitually for everything, or if you're not actually sure about the package origin.
For usability
For end users, just drop a HEADER.html
into the repository directory. Apaches mod_auto_index
will prepend that note:
<h1>http://example.org/apt/</h1>
<dl>
<dt>Add this repository to /etc/apt/sources.list as:
<dd><kbd>deb http://example.org/apt/ ./ # example repo</kbd>
<dt>Import verification key with:
<dd><kbd>wget -q http://http://example.org/apt/public.gpg -O- | sudo apt-key add -</kbd>
</dl>
Alternatives
There are a few tools to automate repository management these days. And there are even repository online hosters and package build services (gemfury, packagecloud, bintray etc.)
A rather convenient alternative is prm. It's a Ruby script, which builds complex APT and YUM repos. (But let's just hope RPM finally dies out sometime soon..) - It's best installed per
gem install prm
.And I've also written a small script to automate this similarly: http://apt.include-once.org/apt-phparchive - Please not that it's not overly robust and written in PHP (for once, this is coincidental), and was originally meant for DEB, and RPM-over-APT and Phar bundles.
Since this is closely related to the original question, there are also tools to build Debian packages more easily. Somewhat outdated: EPM. Much more contempoary: FPM. And my personal fork thereof: XPM (more lazy approach for packaging scripting language apps.)
Setting up a trivial repository is very easy using dpkg-scanpackages. This page explains how to set up a trivial repo, and this one explains how to use it (scroll down to example 4).
Yes. You can do this. You just need to organize the files in the right way and create the index files. If you put the directory structure inside the document root of your web server the packages can just be accessed via the web server.
Here is a detailed description how the files need to be organized and how the index files are created.
You can also use a tool called reprepro if you are willing to install that one package. This will make the administration a little more convenient.