line |
stmt |
bran |
cond |
sub |
pod |
time |
code |
1
|
|
|
|
|
|
|
package WebService::Livedoor::Weather; |
2
|
|
|
|
|
|
|
|
3
|
3
|
|
|
3
|
|
119219
|
use strict; |
|
3
|
|
|
|
|
7
|
|
|
3
|
|
|
|
|
106
|
|
4
|
3
|
|
|
3
|
|
18
|
use warnings; |
|
3
|
|
|
|
|
4
|
|
|
3
|
|
|
|
|
73
|
|
5
|
3
|
|
|
3
|
|
1064
|
use utf8; |
|
3
|
|
|
|
|
17
|
|
|
3
|
|
|
|
|
17
|
|
6
|
3
|
|
|
3
|
|
68
|
use Carp; |
|
3
|
|
|
|
|
4
|
|
|
3
|
|
|
|
|
256
|
|
7
|
3
|
|
|
3
|
|
1844
|
use Encode; |
|
3
|
|
|
|
|
29083
|
|
|
3
|
|
|
|
|
304
|
|
8
|
3
|
|
|
3
|
|
3000
|
use URI::Fetch; |
|
3
|
|
|
|
|
429004
|
|
|
3
|
|
|
|
|
109
|
|
9
|
3
|
|
|
3
|
|
4235
|
use XML::Simple; |
|
0
|
|
|
|
|
|
|
|
0
|
|
|
|
|
|
|
10
|
|
|
|
|
|
|
use JSON 2; |
11
|
|
|
|
|
|
|
our $VERSION = '0.10'; |
12
|
|
|
|
|
|
|
|
13
|
|
|
|
|
|
|
use constant BASE_URI => $ENV{LDWEATHER_BASE_URI} || 'http://weather.livedoor.com'; |
14
|
|
|
|
|
|
|
use constant ENDPOINT_URI => $ENV{LDWEATHER_ENDPOINT_URI} || BASE_URI. '/forecast/webservice/json/v1'; |
15
|
|
|
|
|
|
|
use constant FORECASTMAP_URI => $ENV{LDWEATHER_FORECASTMAP_URI} || BASE_URI. '/forecast/rss/primary_area.xml'; |
16
|
|
|
|
|
|
|
|
17
|
|
|
|
|
|
|
sub new { |
18
|
|
|
|
|
|
|
my ( $class, %args ) = @_; |
19
|
|
|
|
|
|
|
$args{fetch} ||= {}; |
20
|
|
|
|
|
|
|
$args{fetch} = { |
21
|
|
|
|
|
|
|
%{$args{fetch}}, |
22
|
|
|
|
|
|
|
UserAgent => LWP::UserAgent->new( agent => __PACKAGE__.'/'.$VERSION ) |
23
|
|
|
|
|
|
|
}; |
24
|
|
|
|
|
|
|
bless \%args,$class; |
25
|
|
|
|
|
|
|
} |
26
|
|
|
|
|
|
|
|
27
|
|
|
|
|
|
|
sub get { |
28
|
|
|
|
|
|
|
my ($self, $city) = @_; |
29
|
|
|
|
|
|
|
croak('city is required') unless $city; |
30
|
|
|
|
|
|
|
my $cityid = $self->__get_cityid($city); |
31
|
|
|
|
|
|
|
|
32
|
|
|
|
|
|
|
my $res = URI::Fetch->fetch(ENDPOINT_URI. "?city=$cityid", %{$self->{fetch}}); |
33
|
|
|
|
|
|
|
croak("Cannot get weather information : " . URI::Fetch->errstr) unless $res; |
34
|
|
|
|
|
|
|
|
35
|
|
|
|
|
|
|
return $self->__parse_forecast($res->content); |
36
|
|
|
|
|
|
|
} |
37
|
|
|
|
|
|
|
|
38
|
|
|
|
|
|
|
sub __parse_forecast { |
39
|
|
|
|
|
|
|
my ($self, $json) = @_; |
40
|
|
|
|
|
|
|
my $ref; |
41
|
|
|
|
|
|
|
eval{$ref = decode_json($json)}; |
42
|
|
|
|
|
|
|
croak('Oops! failed reading weather information : ' . $@) if $@; |
43
|
|
|
|
|
|
|
|
44
|
|
|
|
|
|
|
### temperature fixing for null case |
45
|
|
|
|
|
|
|
for ( @{$ref->{forecasts}} ) { |
46
|
|
|
|
|
|
|
ref $_->{temperature}{max}{celsius} and $_->{temperature}{max}{celsius} = undef; |
47
|
|
|
|
|
|
|
ref $_->{temperature}{min}{celsius} and $_->{temperature}{min}{celsius} = undef; |
48
|
|
|
|
|
|
|
ref $_->{temperature}{max}{fahrenheit} and $_->{temperature}{max}{fahrenheit} = undef; |
49
|
|
|
|
|
|
|
ref $_->{temperature}{min}{fahrenheit} and $_->{temperature}{min}{fahrenheit} = undef; |
50
|
|
|
|
|
|
|
} |
51
|
|
|
|
|
|
|
|
52
|
|
|
|
|
|
|
return $ref; |
53
|
|
|
|
|
|
|
} |
54
|
|
|
|
|
|
|
|
55
|
|
|
|
|
|
|
sub __get_cityid { |
56
|
|
|
|
|
|
|
my ($self,$city) = @_; |
57
|
|
|
|
|
|
|
$city =~ /^\d+$/ ? $city : $self->__forecastmap->{$city} or croak('Invalid city name. cannot find city id with '. $city); |
58
|
|
|
|
|
|
|
} |
59
|
|
|
|
|
|
|
|
60
|
|
|
|
|
|
|
sub __forecastmap { |
61
|
|
|
|
|
|
|
my $self = shift; |
62
|
|
|
|
|
|
|
unless ($self->{forecastmap}) { |
63
|
|
|
|
|
|
|
my $res = URI::Fetch->fetch(FORECASTMAP_URI, %{$self->{fetch}}); |
64
|
|
|
|
|
|
|
croak("Couldn't get forecastmap: " . URI::Fetch->errstr) unless $res; |
65
|
|
|
|
|
|
|
$self->{forecastmap} = $self->__parse_forecastmap($res->content); |
66
|
|
|
|
|
|
|
} |
67
|
|
|
|
|
|
|
return $self->{forecastmap}; |
68
|
|
|
|
|
|
|
} |
69
|
|
|
|
|
|
|
|
70
|
|
|
|
|
|
|
sub __parse_forecastmap { |
71
|
|
|
|
|
|
|
my ($self, $str) = @_; |
72
|
|
|
|
|
|
|
|
73
|
|
|
|
|
|
|
my $ref = eval { |
74
|
|
|
|
|
|
|
local $XML::Simple::PREFERRED_PARSER = 'XML::Parser'; |
75
|
|
|
|
|
|
|
XMLin($str, ForceArray => [qw[pref area city]]); |
76
|
|
|
|
|
|
|
}; |
77
|
|
|
|
|
|
|
if ($@) { |
78
|
|
|
|
|
|
|
local $Carp::CarpLevel = 1; |
79
|
|
|
|
|
|
|
croak('Oops! failed reading forecastmap: '. $@); |
80
|
|
|
|
|
|
|
} |
81
|
|
|
|
|
|
|
my %forecastmap; |
82
|
|
|
|
|
|
|
foreach my $pref ( @{$ref->{channel}{'ldWeather:source'}{pref}} ){ |
83
|
|
|
|
|
|
|
$forecastmap{$pref->{city}{$_}{title}} = $_ for keys %{$pref->{city}}; |
84
|
|
|
|
|
|
|
} |
85
|
|
|
|
|
|
|
return \%forecastmap; |
86
|
|
|
|
|
|
|
} |
87
|
|
|
|
|
|
|
|
88
|
|
|
|
|
|
|
1; |
89
|
|
|
|
|
|
|
__END__ |