File Coverage

blib/lib/Net/Discident.pm
Criterion Covered Total %
statement 55 65 84.6
branch 7 14 50.0
condition 6 11 54.5
subroutine 13 15 86.6
pod 4 6 66.6
total 85 111 76.5


line stmt bran cond sub pod time code
1             package Net::Discident;
2              
3 2     2   16228 use Modern::Perl;
  2         11974  
  2         12  
4 2     2   242 use Digest::MD5 qw( md5_hex );
  2         3  
  2         90  
5 2     2   19 use File::Find;
  2         13  
  2         107  
6 2     2   1692 use File::stat;
  2         312831  
  2         14  
7 2     2   1886 use HTTP::Lite;
  2         24818  
  2         73  
8 2     2   1273 use JSON;
  2         19704  
  2         17  
9              
10 2     2   2213 use version;
  2         4852  
  2         13  
11             our $VERSION = qv( 1.0.1 );
12              
13 2     2   170 use constant BASE_URI => 'http://discident.com/v1';
  2         4  
  2         1284  
14              
15              
16              
17             sub new {
18 2     2 0 360 my $class = shift;
19 2         4 my $path = shift;
20            
21 2         5 my $self = {};
22 2         6 bless $self, $class;
23            
24 2         9 $self->fingerprint( $path );
25            
26 2         6 return $self;
27             }
28              
29             sub fingerprint {
30 3     3 1 11 my $self = shift;
31 3         6 my $path = shift;
32 3         6 my $fingerprint = shift;
33            
34 3 50 66     23 return $self->ident()
35             if !defined $fingerprint && !defined $path;
36            
37 1 50       4 $fingerprint = $self->fingerprint_files( $path )
38             if !defined $fingerprint;
39            
40             # discident fingerprints are uppercase and hyphenated hex md5s
41 1         13 my $md5 = uc md5_hex( $fingerprint );
42 1         19 $md5 =~ s{(.{8})(.{4})(.{4})(.{4})(.*)}{$1-$2-$3-$4-$5};
43            
44 1         5 $self->{'ident'} = $md5;
45            
46 1         5 return $md5;
47             }
48             sub ident {
49 5     5 1 5760 my $self = shift;
50 5         12 my $ident = shift;
51            
52 5 100       21 $self->{'ident'} = $ident
53             if defined $ident;
54            
55 5         34 return $self->{'ident'};
56             }
57             sub query {
58 3     3 1 2809 my $self = shift;
59 3   66     18 my $ident = shift // $self->ident();
60 3   50     21 my $raw = shift // 0;
61            
62 3         11 my $uri = $self->query_url( $ident );
63 3         31 my $http = HTTP::Lite->new();
64 3 50       210 my $code = $http->request( $uri )
65             or die "Unable to fetch ident: $!";
66            
67 3 50       911542 die "Unable to fetch ident: HTTP $code"
68             unless 200 == $code;
69            
70 3 50       18 return $http->body()
71             if $raw;
72            
73 3         20 return from_json $http->body()
74             }
75             sub query_url {
76 3     3 1 7 my $self = shift;
77 3   33     14 my $ident = shift // $self->ident();
78            
79 3         20 return sprintf "%s/%s/", BASE_URI, $ident;
80             }
81              
82             sub fingerprint_files {
83 0     0 0   my $self = shift;
84 0           my $path = shift;
85            
86 0           my $long_fingerprint;
87            
88             my $stat_file = sub {
89 0 0   0     return if -d $_;
90              
91 0           my $stat = stat $_;
92 0           substr $_, 0, length( $path ), '';
93            
94 0           $long_fingerprint .= sprintf(
95             ":%s:%lld",
96             $_,
97             $stat->size,
98             );
99 0           };
100            
101 0           find(
102             {
103             wanted => $stat_file,
104             no_chdir => 1,
105             },
106             $path,
107             );
108            
109 0           return $long_fingerprint;
110             }
111              
112             1;
113              
114             __END__