File Coverage

blib/lib/WWW/RobotRules/AnyDBM_File.pm
Criterion Covered Total %
statement 81 81 100.0
branch 22 26 84.6
condition 4 6 66.6
subroutine 14 15 93.3
pod 2 10 20.0
total 123 138 89.1


line stmt bran cond sub pod time code
1             package WWW::RobotRules::AnyDBM_File;
2 1     1   119690 use strict;
  1         2  
  1         30  
3              
4 1     1   455 use WWW::RobotRules ();
  1         3  
  1         45  
5             our @ISA = qw(WWW::RobotRules);
6             our $VERSION = '6.03';
7              
8 1     1   11 use Carp ();
  1         1  
  1         15  
9 1     1   660 use AnyDBM_File;
  1         4422  
  1         60  
10 1     1   8 use Fcntl qw( O_CREAT O_RDWR );
  1         6  
  1         926  
11              
12             sub new {
13 4     4 1 400916 my ($class, $ua, $file) = @_;
14 4 50       16 Carp::croak('WWW::RobotRules::AnyDBM_File filename required') unless $file;
15              
16 4         12 my $self = bless {}, $class;
17 4         21 $self->{'filename'} = $file;
18 4 50       8 tie %{$self->{'dbm'}}, 'AnyDBM_File', $file, O_CREAT | O_RDWR, 0600
  4         564  
19             or Carp::croak("Can't open $file: $!");
20              
21 4 100       19 if ($ua) {
22 2         10 $self->agent($ua);
23             }
24             else {
25             # Try to obtain name from DBM file
26 2         45 $ua = $self->{'dbm'}{"|ua-name|"};
27 2 100       295 Carp::croak("No agent name specified") unless $ua;
28             }
29              
30 3         12 $self;
31             }
32              
33             sub agent {
34 5     5 1 14 my ($self, $newname) = @_;
35 5         58 my $old = $self->{'dbm'}{"|ua-name|"};
36 5 100       18 if (defined $newname) {
37 2         21 $newname =~ s!/?\s*\d+.\d+\s*$!!; # loose version
38 2 50 66     13 unless ($old && $old eq $newname) {
39              
40             # Old info is now stale. Clear all keys through the tied
41             # interface rather than untie+tie(O_TRUNC), which is a
42             # symlink-follow TOCTOU on the DBM-backing file(s).
43 2         5 %{$self->{'dbm'}} = ();
  2         15  
44 2         197 $self->{'dbm'}{"|ua-name|"} = $newname;
45             }
46             }
47 5         17 $old;
48             }
49              
50             sub no_visits {
51 5     5 0 28 my ($self, $netloc) = @_;
52 5         23 my $t = $self->{'dbm'}{"$netloc|vis"};
53 5 100       19 return 0 unless $t;
54 4         36 (split(/;\s*/, $t))[0];
55             }
56              
57             sub last_visit {
58 2     2 0 4 my ($self, $netloc) = @_;
59 2         14 my $t = $self->{'dbm'}{"$netloc|vis"};
60 2 50       7 return undef unless $t;
61 2         21 (split(/;\s*/, $t))[1];
62             }
63              
64             sub fresh_until {
65 6     6 0 22 my ($self, $netloc, $fresh) = @_;
66 6         60 my $old = $self->{'dbm'}{"$netloc|exp"};
67 6 100       24 if ($old) {
68 3         18 $old =~ s/;.*//; # remove cleartext
69             }
70 6 100       24 if (defined $fresh) {
71 2         68 $fresh .= "; " . localtime($fresh);
72 2         90 $self->{'dbm'}{"$netloc|exp"} = $fresh;
73             }
74 6         25 $old;
75             }
76              
77             sub visit {
78 4     4 0 587 my ($self, $netloc, $time) = @_;
79 4   66     17 $time ||= time;
80              
81 4         4 my $count = 0;
82 4         16 my $old = $self->{'dbm'}{"$netloc|vis"};
83 4 100       11 if ($old) {
84 2         3 my $last;
85 2         12 ($count, $last) = split(/;\s*/, $old);
86 2 100       7 $time = $last if $last > $time;
87             }
88 4         6 $count++;
89 4         173 $self->{'dbm'}{"$netloc|vis"} = "$count; $time; " . localtime($time);
90             }
91              
92             sub push_rules {
93 4     4 0 12 my ($self, $netloc, @rules) = @_;
94 4         6 my $cnt = 1;
95 4         35 $cnt++ while $self->{'dbm'}{"$netloc|r$cnt"};
96              
97 4         20 foreach (@rules) {
98 6         130 $self->{'dbm'}{"$netloc|r$cnt"} = $_;
99 6         24 $cnt++;
100             }
101             }
102              
103             sub clear_rules {
104 4     4 0 632 my ($self, $netloc) = @_;
105 4         6 my $cnt = 1;
106 4         64 while ($self->{'dbm'}{"$netloc|r$cnt"}) {
107 4         66 delete $self->{'dbm'}{"$netloc|r$cnt"};
108 4         18 $cnt++;
109             }
110             }
111              
112             sub rules {
113 4     4 0 12 my ($self, $netloc) = @_;
114 4         9 my @rules = ();
115 4         7 my $cnt = 1;
116 4         7 while (1) {
117 12         68 my $rule = $self->{'dbm'}{"$netloc|r$cnt"};
118 12 100       34 last unless $rule;
119 8         14 push(@rules, $rule);
120 8         14 $cnt++;
121             }
122 4         15 @rules;
123             }
124              
125       0 0   sub dump { }
126              
127             1;
128             __END__