File Coverage

blib/lib/Finance/SEC/EdgarData.pm
Criterion Covered Total %
statement 17 77 22.0
branch 0 16 0.0
condition n/a
subroutine 6 14 42.8
pod 0 8 0.0
total 23 115 20.0


line stmt bran cond sub pod time code
1             package Finance::SEC::EdgarData;
2 1     1   67853 use XML::Bare;
  1         15782  
  1         46  
3 1     1   736 use LWP::UserAgent;
  1         54143  
  1         37  
4 1     1   9 use Carp;
  1         2  
  1         54  
5 1     1   7 use strict;
  1         3  
  1         19  
6 1     1   5 use warnings;
  1         1  
  1         22  
7 1     1   11 use v5.10;
  1         4  
8             require Exporter;
9             our @ISA = qw(Exporter);
10             our @EXPORT_OK = qw/
11             set_user_agent
12             get_filing_url
13             get_xbrl_url
14             get_filing_dates
15             get_filing
16             get_rss_url
17             get_rss
18             /;
19             our @EXPORT = qw/
20             set_user_agent
21             get_filing_url
22             get_xbrl_url
23             get_filing_dates
24             get_filing
25             get_rss_url
26             get_rss
27             /;
28             our $VERSION = '0.010021';
29              
30             my $BASE_URL = 'https://www.sec.gov';
31             my $RSS_URL = "$BASE_URL/cgi-bin/browse-edgar?action=getcompany&CIK=%s&type=%s&dateb=&owner=exclude&count=500&output=atom";
32             my $ua = LWP::UserAgent->new;
33             my $agent = "Mozilla/5.0 (X11; Ubuntu; Linux i686; rv:24.0) Gecko/20100101 Firefox/24.0";
34             $ua->agent($ENV{EDGAR_USER_AGENT} || $agent);
35              
36             sub set_user_agent {
37 0     0 0   my $g = shift;
38 0           $ua->agent($g);
39             }
40              
41             sub get_rss_url {
42 0     0 0   my ($sym, $t) = @_;
43 0           my $url = sprintf($RSS_URL, $sym, $t);
44 0           return $url;
45             }
46              
47             sub parse_rss {
48 0     0 0   my $xml = shift;
49 0           my $m = XML::Bare->new(text => $xml);
50 0           my $root = $m->parse();
51 0           return $root;
52             }
53              
54             sub get_rss {
55 0     0 0   my $url = get_rss_url(@_);
56 0           my $res = $ua->get($url);
57 0 0         if (!($res->is_success)) {
58 0           say STDERR $res->content;
59 0           return 0;
60             }
61 0           my $d = $res->content;
62 0           my $rss = parse_rss($d);
63 0           return $rss;
64             }
65              
66             sub get_filing_dates {
67 0     0 0   my $rss = get_rss(@_);
68 0           my @dates = ();
69 0           for my $n (@{$rss->{feed}->{entry}}) {
  0            
70 0           push @dates, $n->{content}->{'filing-date'}->{value};
71             }
72 0           return @dates;
73             }
74              
75             sub get_filing_url {
76 0     0 0   my ($sym, $t, $date) = @_;
77 0           my $rss = get_rss($sym, $t);
78 0           for my $n (@{$rss->{feed}->{entry}}) {
  0            
79 0           my $c = $n->{content};
80 0 0         if ($c->{'filing-date'}->{value} eq $date) {
81 0           return $c->{'filing-href'}->{value};
82             }
83             }
84 0           return 0;
85             }
86              
87             sub get_xbrl_url {
88 0     0 0   my $link = shift;
89 0           my $res = $ua->get($link);
90 0 0         return 0 unless $res->is_success;
91 0           my $d = $res->content;
92 0           my $found = 0;
93 0           while ($d =~ /(.*?)<\/table>/isg) {
94 0 0         if ($1) {
95 0           my $n = "$1";
96 0           my $m = XML::Bare->new(text => $n);
97 0           my $root = $m->parse();
98 0           for my $t (@{$root->{root}->{tr}}) {
  0            
99 0           for (@{$t->{td}}) {
  0            
100 0 0         if ($found) {
101 0           return $BASE_URL . $_->{a}->{href}->{value};
102             }
103 0 0         next unless $_->{value};
104 0 0         if ($_->{value} =~ /XBRL INSTANCE DOCUMENT/) {
105 0           $found = 1;
106             }
107             }
108             }
109             }
110             }
111 0           return 0;
112             }
113              
114             sub get_filing {
115 0     0 0   my ($sym, $t, $date) = @_;
116 0           my $filing_url = get_filing_url($sym, $t, $date);
117 0           my $xbrl_url = get_xbrl_url($filing_url);
118 0           my $res = $ua->get($xbrl_url);
119 0 0         return 0 unless $res->is_success;
120 0           my $d = $res->content;
121 0           my $m = XML::Bare->new(text => $d);
122 0           my $root = $m->parse();
123 0           return $root;
124             }
125              
126             1;
127              
128              
129             __END__