File: //usr/share/duck/lib/checks/upstream_metadata.pm
# duck - check for upstream metadata files
# Copyright (C) 2016 Simon Kainz <skainz@debian.org>
#
# This program is free software; you can redistribute it and/or modify
# it under the terms of the GNU General Public License as published by
# he Free Software Foundation; either version 2 of the License, or
# (at your option) any later version.
#
# This program is distributed in the hope that it will be useful,
# but WITHOUT ANY WARRANTY; without even the implied warranty of
# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
# GNU General Public License for more details.
#
# On Debian GNU/Linux systems, the complete text of the GNU General
# Public License can be found in `/usr/share/common-licenses/GPL-2'.
#
# You should have received a copy of the GNU General Public License
# along with this program. If not, you can find it on the World Wide
# Web at https://www.gnu.org/copyleft/gpl.html, or write to the Free
# Software Foundation, Inc., 51 Franklin St, Fifth Floor, Boston,
# MA 02110-1301, USA.
package DUCK::upstream_metadata;
use strict;
use warnings;
use autodie;
use Data::Dumper;
use Parse::DebControl qw(parse_file);
use YAML::XS qw(Load);
use Regexp::Common qw /URI Email::Address/;
#use Mail::Address;
my @upstream_filenames=("debian/upstream",
"debian/upstream-metadata.yaml",
"debian/upstream/metadata");
my $extract_hash;
my @extract=("Homepage",
"Repository",
"Repository-Browse",
"Screenshots",
"Bug-Submit",
"Bug-Database",
"Changelog",
"Donation",
"FAQ",
"Gallery",
"Other-References",
"Webservice",
"Reference",
"URL",
"Eprint");
sub proc($;$;$;$;$);
sub guess_type($);
my %options=(
"u:" => " -u file\tspecify path to upstream metadata file",
"U" => " -U\t\tskip processing of upstream metadata file");
sub opts()
{
return keys %options;
}
sub desc()
{
my $r;
foreach (sort keys %options)
{
$r.=$options{$_}."\n";
}
return $r;
}
sub run()
{
my $upstream_filename;
my ($sname,$params,$entries_ref)=@_;
my %opt=%$params;
# my @entries=@$entries_ref;
my @yaml_urls;
foreach my $a (@extract)
{
$extract_hash->{$a}=1;
}
#print Dumper @extract;
#print Dumper $extract_hash;
if ($opt{u})
{
if (! -r $opt{u})
{
print STDERR "Unable to open user-specified upstream metadata file: ".$opt{u}."\n";
exit(2);
}
@upstream_filenames=($opt{u});
}
#Processing upstream metadata file
if (!$opt{U})
{
# extend list of urls by urls from upstream metadata
foreach (@upstream_filenames)
{
@yaml_urls=();
if ( -f $_)
{
$upstream_filename=$_;
open my $fh,"<",$_;
my @raw=<$fh>;
my $raw_string=join("",@raw);
close($fh);
my $hashref;
eval { Load($raw_string);}; if (!$@)
{
$hashref=Load($raw_string);
# print Dumper $hashref;
foreach my $k (keys %{$hashref})
{
proc("",\@yaml_urls,$k,$hashref->{$k});
}
}
}
foreach my $yaml_url(@yaml_urls)
{
# try to be smart: git:// and svn:// based urls must not be handled
# by curl.
my $keyname=_guess_type(@$yaml_url[1]);
if (!$keyname) {$keyname="URL";}
@$yaml_url[1] =~ s/^\s*//;
# print "ff\n";
# push (@$entries_ref, [$upstream_filename.": ".@$yaml_url[2],$keyname,@$yaml_url[1] ]);
push (@$entries_ref, [$upstream_filename.": ".@$yaml_url[2],$keyname,@$yaml_url[1],0,
{filename => $upstream_filename,
# linenumber => $linenum,
checkmethod =>$keyname,
url=>@$yaml_url[1],
certainty=>"wild-guess"}
]);
}
}
}
return;
}
sub proc($;$;$;$;$)
{
my ($sp,$ref,$key,$r,$p)=@_;
my $t=ref($r);
# print "$key\n";
if ($t eq "HASH")
{
# print "\thash\n";
my %a=%{$r};
# print Dumper keys %a;
foreach my $e (keys %a)
{
# print "\t:$e\n";
proc($sp,$ref,$e,$a{$e},$key);
}
}
if ($t eq "ARRAY")
{
# print "\array\n";
my @a=@{$r};
foreach my $e (@a)
{
proc($sp,$ref,$key,$e,$key);
}
}
if ($t eq "")
{
# print "\t end point\n";
# print Dumper $extract_hash;
if ($extract_hash->{$key})
{
# print "adding key $key to data\n";
my @data=($sp,$r,$key);
push(@{$ref},\@data);
}
}
}
sub _guess_type($)
{
my ($url)=@_;
return "Vcs-Git" if ($url =~/^\s*git:\/\//);
return "Vcs-Svn" if ($url =~/^\s*svn:\/\//);
return "URL" if ($url =~/$RE{URI}{HTTP}{-scheme =>"https?"}/);
return "URL" if ($url =~/$RE{URI}{FTP}/);
return undef;
}
1;