4 # dcontrol - Query Debian control files across releases and architectures
5 # Copyright (C) 2009 Christoph Berg <myon@debian.org>
7 # This program is free software; you can redistribute it and/or modify
8 # it under the terms of the GNU General Public License as published by
9 # the Free Software Foundation; either version 2 of the License, or
10 # (at your option) any later version.
12 # This program is distributed in the hope that it will be useful,
13 # but WITHOUT ANY WARRANTY; without even the implied warranty of
14 # MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
15 # GNU General Public License for more details.
17 # You should have received a copy of the GNU General Public License
18 # along with this program; if not, write to the Free Software
19 # Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA
26 # Load the URI::Escape and LWP::UserAgent modules safely
27 my $progname = basename($0,'.pl');
28 eval { require URI::Escape; };
30 if ($@ =~ /^Can\'t locate URI\/Escape\.pm/) {
31 die "$progname: you must have the liburi-perl package installed\nto use this script\n";
33 die "$progname: problem loading the URI::Escape module:\n $@\nHave you installed the liburi-perl package?\n";
37 eval { require LWP::UserAgent; };
39 my $progname = basename $0;
40 if ($@ =~ /^Can\'t locate LWP/) {
41 die "$progname: you must have the libwww-perl package installed\nto use this script\n";
43 die "$progname: problem loading the LWP::UserAgent module:\n $@\nHave you installed the libwww-perl package?\n";
45 import LWP::UserAgent;
50 my $progname = basename($0,'.pl'); # the '.pl' is for when we're debugging
51 my $modified_conf_msg;
55 my $ua = LWP::UserAgent->new(agent => "$progname ###VERSION###");
61 Usage: $progname [-sd] package[modifiers] [...]
63 Query package and source control files for all Debian distributions.
66 -s --show-suite Add headers for distribution the control file is from
67 -d --debug Print URL queried
70 =version Exact version match
71 \@architecture Query this architecture
72 /[archive:][suite][/component]
73 Restrict to archive (debian, debian-backports,
74 debian-security, debian-volatile), suite (always
75 codenames, with the exception of experimental), and/or
76 component (main, updates/main, ...). Use // if the suite
77 name contains slashes.
79 By default, all versions, suites, and architectures are queried.
80 Use \@source for source packages. \@binary returns no source packages.
81 Refer to $dcontrol_url for currently supported values.
83 Default settings modified by devscripts configuration files:
90 This is $progname, from the Debian devscripts package, version ###VERSION###
91 This code is copyright 2009 by Christoph Berg <myon\@debian.org>.
93 This program comes with ABSOLUTELY NO WARRANTY.
94 You are free to redistribute this code under the terms of the
95 GNU General Public License, version 2 or later.
101 unless ($arg =~ /^([\w.+-]+)/) {
102 die "$arg does not start with a valid package name\n";
104 my $url = "$dcontrol_url?package=" . uri_escape($1);
105 if ($arg =~ /=([\w~:.+-]+)/) {
106 $url .= "&version=" . uri_escape($1);
108 if ($arg =~ /@([\w.-]+)/) {
109 $url .= "&architecture=$1";
111 if ($arg =~ m!/([\w-]*):([\w/-]*)//([\w/-]*)!) {
112 $url .= "&archive=$1&suite=$2&component=$3";
113 } elsif ($arg =~ m!/([\w/-]*)//([\w/-]*)!) {
114 $url .= "&suite=$1&component=$2";
115 } elsif ($arg =~ m!/([\w-]*):([\w-]*)/([\w/-]*)!) {
116 $url .= "&archive=$1&suite=$2&component=$3";
117 } elsif ($arg =~ m!/([\w-]*):([\w-]*)!) {
118 $url .= "&archive=$1&suite=$2";
119 } elsif ($arg =~ m!/([\w-]*)/([\w/-]*)!) {
120 $url .= "&suite=$1&component=$2";
121 } elsif ($arg =~ m!/([\w\/-]+)!) {
124 if ($opt->{'show-suite'}) {
125 $url .= "&annotate=yes";
127 print "$url\n" if $opt->{debug};
128 my $response = $ua->get ($url);
129 if ($response->is_success) {
130 print $response->content . "\n";
132 die $response->status_line;
138 if (@ARGV and $ARGV[0] =~ /^--no-?conf$/) {
139 $modified_conf_msg = " (no configuration files read)";
142 my @config_files = ('/etc/devscripts.conf', '~/.devscripts');
144 'DCONTROL_URL' => 'http://qa.debian.org/cgi-bin/dcontrol',
146 my %config_default = %config_vars;
150 foreach my $var (keys %config_vars) {
151 $shell_cmd .= "$var='$config_vars{$var}';\n";
153 $shell_cmd .= 'for file in ' . join(" ",@config_files) . "; do\n";
154 $shell_cmd .= '[ -f $file ] && . $file; done;' . "\n";
156 foreach my $var (keys %config_vars) { $shell_cmd .= "echo \$$var;\n" }
157 my $shell_out = `/bin/bash -c '$shell_cmd'`;
158 @config_vars{keys %config_vars} = split /\n/, $shell_out, -1;
160 foreach my $var (sort keys %config_vars) {
161 if ($config_vars{$var} ne $config_default{$var}) {
162 $modified_conf_msg .= " $var=$config_vars{$var}\n";
165 $modified_conf_msg ||= " (none)\n";
166 chomp $modified_conf_msg;
168 $dcontrol_url = $config_vars{'DCONTROL_URL'};
172 Getopt::Long::Configure('bundling');
174 "d|debug" => \$opt->{'debug'},
175 "s|show-suite" => \$opt->{'show-suite'},
176 "h|help" => \$opt->{'help'},
177 "V|version" => \$opt->{'version'},
179 or die "$progname: unrecognised option. Run $progname --help for more details.\n";
181 if ($opt->{'help'}) { usage(); exit 0; }
182 if ($opt->{'version'}) { version(); exit 0; }
183 if ($opt->{'no-conf'}) {
184 die "$progname: --no-conf is only acceptable as the first command-line option!\n";
193 while (my $arg = shift @ARGV) {
201 dcontrol -- Query package and source control files for all Debian distributions
207 =item B<dcontrol> [I<options>] I<package>[I<modifiers>] [I<...>]
213 B<dcontrol> queries a remote database of Debian binary and source package
214 control files. It can be thought of as an B<apt-cache> webservice that also
215 operates for distributions and architectures different from the local machine.
219 Like B<apt-cache>, packages can be suffixed by modifiers:
227 =item B<@>I<architecture>
229 Query this only architecture. Use B<@source> for source packages,
230 B<@binary> excludes source packages.
232 =item B</>[I<archive>B<:>][I<suite>][B</>I<component>]
234 Restrict to I<archive> (debian, debian-backports, debian-security,
235 debian-volatile), I<suite> (always codenames, with the exception of
236 experimental), and/or I<component> (main, updates/main, ...). Use two slashes
237 (B<//>) to separate suite and component if the suite name contains slashes.
238 (Component can be left empty.)
242 By default, all versions, suites, and architectures are queried. Refer to
243 B<http://qa.debian.org/cgi-bin/dcontrol> for currently supported values.
249 =item B<-s>, B<--show-suites>
251 Add headers showing which distribution the control file is from.
253 =item B<-d>, B<--debug>
257 =item B<-h>, B<--help>
261 =item B<-V>, B<--version>
263 Show version information.
267 =head1 CONFIGURATION VARIABLES
269 The two configuration files F</etc/devscripts.conf> and
270 F<~/.devscripts> are sourced by a shell in that order to set
271 configuration variables. Command line options can be used to override
272 configuration file settings. Environment variable settings are
273 ignored for this purpose. The currently recognised variable is:
279 URL to query. Default is B<http://qa.debian.org/cgi-bin/dcontrol>.
285 This program is Copyright (C) 2009 by Christoph Berg <myon@debian.org>.
287 This program is licensed under the terms of the GPL, either version 2
288 of the License, or (at your option) any later version.