This guide describes the procedures that the Debian Perl Group contributors use to maintain packages in the Git repositories on git.debian.org.
It covers how to upload an initial package, how to update packages, how to build them, how to upgrade them, and how to get the source for all packages with mr(1).
The guide is a work in progress. Different people tend to do things in different ways. If your way diverges, you may want to document it here so that others can benefit. Please send any comments or ideas to <debian-perl@lists.debian.org>.
For a more general guide to Git, see the Git User's Manual at http://www.kernel.org/pub/software/scm/git/docs/user-manual.html.
If you just want to work on an individual package maintained by the Debian Perl Group, you need the following packages installed (the versions in squeeze work fine for this case):
Each package has its own Git repository. If you are working with multiple packages maintained by the Debian Perl Group, then you will probably want to use mr(1) to manage the multiple Git repos involved. For this workflow, you'll need the following packages installed:
The version in squeeze has buggy command_bidi_pipe method
for the post_update feature
meta.git repository
Check out meta.git repository with
$ git clone ssh://git.debian.org/git/pkg-perl/meta.git
This contains the following useful scripts:
alioth-git-repo
Creates a new repo in /git/pkg-perl/packages on alioth. This is the preferred
method. See below for more detail.
compare-hashes
Filters out unnecessary pulls. Uses a couple of non-core Perl modules and complains if those aren't present.
Used in .mrconfig.
pkg-perl-post-receive
Called by the post-receive hooks of the git repos; runs KGB (IRC notifications), updates the PET database, and sends mails to the commit list.
remove-repository
Deletes a repository from alioth. Should be run from a shell on vasks. See
Removing packages for more detail.
setup-repository
Sets up a remote repository. Should be run from a shell on vasks. This is
normally done for you by alioth-git-repo. See here for more detail.
split-json-info
Used in .mrconfig.
When called with --pkg-perl options, dh-make-perl populates
a Git repository with master, upstream and pristine-tar
branches, and sets up an origin remote pointing to Alioth.
$ dh-make-perl [option] --pkg-perl --cpan Foo
git-import-dsc imports the source of a package into the Git
repository. It operates on the .dsc file and the associated source files.
Example of starting a new package from scratch:
$ dh-make-perl [option...] --pkg-perl --cpan Foo
...
$ mkdir libfoo-perl
$ cd libfoo-perl
$ git init
$ git-import-dsc --pristine-tar ../libfoo-perl_1.23-1.dsc
If the package is already in Debian and you want to add a bit of history to the
repository, repeat the last command for all .dsc files you have, in
incremental version order. Alternatively you could use git-import-dscs.
Note that dh-make-perl(1) has many options to make your life easier.
Attention: git-import-dsc(1) adds a debian/$version tag. This one should not
be pushed for new packages (but deleted, and later created after the first upload).
An alternative for a new package, as described in http://www.eyrie.org/~eagle/notes/debian/git.html ("Importing a package" -> "If you're instead starting from scratch ..."), is to create a new empty repository and then use git-import-orig(1) and dh-make-perl(1).
If your package does not have a .dsc file you can use (running from the new empty repository):
$ git-import-orig --pristine-tar ../libfoo-perl_1.23.orig.tar.gz
This can be done with plain git-clone(1), but using gbp-clone(1) sets up tracking branches for upstream source and pristine-tar(1) data:
$ gbp-clone --all --pristine-tar ssh://git.debian.org/git/pkg-perl/packages/libfoo-perl.git
Add the following to your ~/.mrconfig, creating it if needed:
[src/pkg-perl/git]
chain = true
checkout = git clone ssh://git.debian.org/git/pkg-perl/meta.git git
Notes:
You then need to explicitly trust ~/src/pkg-perl/git/.mrconfig, by
adding it to ~/.mrtrust, otherwise the chain feature will be
disabled for security reasons.
Now run mr up to clone the meta repository, which contains another
.mrconfig with some features and some helper scripts.
A second invocation of mr up clones all the repositories listed
in meta's .mrconfig, i.e. all pkg-perl git repositories in
/git/pkg-perl/packages on git.debian.org.
For the adventurous:
mr --trust-all bootstrap http://anonscm.debian.org/gitweb/?p=pkg-perl/meta.git;a=blob_plain;f=.mrconfig;hb=HEAD
does mostly the same, except that the authenticity and integrity of the initial .mrconfig are not checked in any way.
Upstream sources are kept (in plain, uncompressed form) in the upstream
branch. The data needed to regenerate original source tarballs from
the upstream branch are kept with the help of the pristine-tar(1) tool
in the pristine-tar branch. Upstream sources are merged with Debian-specific changes
in the master branch, which is the usual place to work in.
From this point on, work on the package normally. Some prefer to update debian/changelog with each commit, others leave this to the git-dch(1) tool at package release time. In case you use git-dch(1) for the changelog entries, don't forget to use it when you stop working on the package.
There are several ways to do this. Please read this section. The pkg-perl
repositories use some infrastructure that is set-up by the below methods.
Non-pkg-perl methods such as gbp-create-remote-repo will not set up this
infrastructure.
The first time:
$ meta/alioth-git-repo
This connects via SSH to alioth, runs setup-repository there with the right arguments, then pushes the local repository over there.
From then on, just use git push --all && git push --tags as usual or use
mr(1) for committing, which also pushes the changes to the original repository
on Alioth, mimicking the subversion commit behaviour at the expense of the
ability to make amends, squashes and splits of commits (you still have to push
any non-active branches or tags via git push). -- Note that the mr(1)'s feature
to push-on-commit is turned off if you use our .mrconfig from the meta
repository as described above.
Before pushing to git.debian.org for the first time, an empty repository needs
to be created there. To do this, use the setup-repository script available
in the /git/pkg-perl directory. Run it similarly to:
$ ssh git.debian.org
$ cd /git/pkg-perl
$ ./setup-repository libfoo-perl 'Packaging of FOO in Debian'
This creates an empty, bare, shared Git repository and setup some hooks.
Now, on your local machine add the Alioth repository as a remote:
$ git remote add origin ssh://git.debian.org/git/pkg-perl/packages/libfoo-perl.git
Then push to it:
$ git push --all --set-upstream
$ git push --tags
The --set-upstream option helps future use of git pull.
Use your favourite way of building the Debian package. If the source tarball is not in ../, check it out from the pristine-tar info (not needed if you use git-buildpackage(1) with the settings mentioned in Tips & tricks below):
$ pristine-tar checkout ../libfoo-bar-perl_1.23_orig.tar.gz
(or ../../scripts/pristine-orig, which figures out the package name and
version from debian/changelog.)
This requires that you have the pristine-tar current (e.g. via git fetch
or gbp-pull(1)).
After uploading, tag the release. The easiest way is to use debcommit(1)
$ debcommit -a -r
Push the result afterwards:
$ git push
$ git push --tags
First make sure that the local repository is up to date, for example using gbp-pull(1).
If the Debian package has a debian/watch file you can use the uscan(1) tool to check for the latest upstream release and download it.
Attention:
cd /usr/share/pyshared/gbp/deb patch <<END
--- uscan.py-orig 2012-12-13 09:09:13.250558008 +0100
+++ uscan.py 2012-12-16 22:22:05.774558001 +0100
@@ -101,6 +101,12 @@
except KeyError as e:
raise UscanError("Couldn't find '%s' in uscan output" %
e.args[0])
+ # perl repack support #635920
+ for row in out.split("\n"):
+ m = re.match(r"\*\*\* ([^\s]+) ready", row)
+ if m:
+ source = "%s" % m.group(1)
+ break
self._tarball = source
def _parse_uptodate(self, out):
END
git-import-orig(1), when used with its --uscan option, acts as
a frontend for uscan:
$ git-import-orig --uscan --pristine-tar
Basically, this command downloads the latest tarball and imports it
into the Git repository: the new sources are imported into the
upstream branch, tarball data is put into the pristine-tar
branch, the upstream release is tagged and finally that tag is merged
into the master branch.
$ uscan
This downloads the latest tarball in ../ and symlink it to the proper
.orig.tar.gz (you can use the --rename options of uscan to directly
rename the tarball without symlinking). If the watch file is not present
you have to download the tarball manually.
Then import the new upstream release in the git repository:
$ git fetch origin upstream:upstream pristine-tar:pristine-tar $ git-import-orig --pristine-tar ../libfoo-bar-perl_2.00_orig.tar.gz
Create a new debian/changelog stanza about the new upstream release:
$ dch -v2.00 'New upstream release'
Can be automated by the following configuration in ~/.gbp.conf:
[git-import-orig] # run hook after the import: postimport = git-dch -N%(version)s -S -a --debian-branch=$GBP_BRANCH
Commit the changes so far:
$ debcommit -a -m'new upstream release 2.00'
Don't forget to share your work when ready:
$ git push --all $ git push --tags
quilt(1) does a fine job managing patches, especially if using the 3.0
(quilt) source format. See http://pkg-perl.alioth.debian.org/howto/quilt.html
for a guide. gbp-pq(1) can be used for treating the patches as a series of
commits. See
https://honk.sigxcpu.org/piki/development/debian_packages_in_git/
From time to time, there is a need to work in a branch for a stable update or a security fix. Things are simple:
First create a branch from the tag that represents the version currently in the archive:
$ git checkout -b squeeze debian/2.40-5
If the squeeze branch already exists, check it out and merge the version
currently in the archive:
$ git checkout squeeze
$ git merge debian/2.40-5
From this point on, work normally in the squeeze branch, build, tag and
push.
For changes across many repos. - Just do them and
$ mr commit
from within the top directory of the repositories.
Our global ~/.mrconfig redefines mr commit to not push to the repositories. Therefore, after commiting:
$ ssh vasks.debian.org touch /home/groups/pkg-perl/KGB-notifications-disabled
mr push
$ ssh vasks.debian.org rm /home/groups/pkg-perl/KGB-notifications-disabled
This has to be done by hand until we have a way to disable them dynamically on mass commits.
This is true for any VCS, but it won't hurt saying it again: please include only
one change in each commit. git-gui(1)'s and git add -p's ability to stage
single lines (or hunks) is a huge help if you have done several unrelated changes
in the sources.
Some prefer to update debian/changelog with each commit, while others prefer to do that only at release time by using git-dch(1). There is no policy yet about which method to recommend, so please state your preference and reasoning by replying to http://lists.debian.org/msgid-search/20110801153235.GD8289@PC-Ale.fastwebnet.it.
When there is need to remove a package from the group you can either remove it completely (if added without never beeing released) or move it to attic. It can be done by using remove-repository on vasks.
One of the annoying things about git-buildpackage is that when you check out
a package using the git+ssh protocol, it asks your password pretty often
when building, about 25 times. This tends to get annoying by the second time you
have to type in your password. To avoid this, upload your public SSH key in
the alioth account area (https://alioth.debian.org/account/editsshkeys.php).
Note that even if ssh-copy-id(1) seems to work, this is only temporary since the authorized_keys file is re-generated from the Alioth account info every now and then.
To avoid typing even the public key passphrase you may want to run SSH agent
(see ssh-agent(1), included in the openssh-client package).
The URLs used above for git commands assume that your username on
git.debian.org is the same as your local username. If this is not the case,
you can put user@ in front of git.debian.org in all of the URLs, but this
is ugly (can it cause problems with git-buildpackage ? ).
You can solve this problem with your local ssh configuration, however.
Edit ~/.ssh/config (creating it if you don't already have it) and add a
stanza for git.debian.org like:
Host git.debian.org
User <user>
replacing <user> with your username on git.debian.org. This tells ssh
to use that username by default when connecting to git.debian.org unless
another is specified, and lets you use git with the default URLs.
git-buildpackage(1) has a configuration file which can save some typing on
each command. The pristine-tar option is particularly handy.
An example of configuration file:
[DEFAULT] pristine-tar = True sign-tags = True
This may be stored for example in ~/.gbp.conf (per user configuration), in debian/gbp.conf (per branch configuration) or in .git/gbp.conf (per repository configuration).
If using the 3.0 (quilt) source format may also be handy to add the .pc
directory to the .gitignore file. To do this globally, you may use the
following:
git config --global --add core.excludesfile ~/.gitignore echo '/.pc/' >> ~/.gitignore
(If you have a Git repository in your home, you probably want to use something else than ~/.gitignore for the global excludes file).
Git is detached. This is very good, when you happen to work mainly offline or on the road. The problem is not to forget to publish your work at some point in time :)
Various shell hooks that change the prompt may be of help.
Copyright (c) 2010-2012 by the individual authors and contributors noted above. All rights reserved. This document is free software; you may redistribute it and/or modify it under the same terms as Perl itself
Perl is distributed under your choice of the GNU General Public License version 1 or later or the Artistic License. On Debian systems, the complete text of the GNU General Public License version 1 can be found in `/usr/share/common-licenses/GPL-1' and the Artistic License in `/usr/share/common-licenses/Artistic'.