Cmd-Dwarf
view release on metacpan or search on metacpan
examples/helloworld/app/lib/Dwarf/Module/SocialMedia/Mixi.pm view on Meta::CPAN
package Dwarf::Module::SocialMedia::Mixi;
use Dwarf::Pragma;
use parent 'Dwarf::Module';
use Dwarf::HTTP::Async;
use Dwarf::Util qw/encode_utf8 decode_utf8 shuffle_array/;
use HTTP::Request::Common ();
use JSON;
use LWP::UserAgent;
use Dwarf::Accessor qw/
ua ua_async urls
key secret
access_token refresh_token expires_in got_access_token_at
user_id name profile_image friends
on_error
/;
sub init {
my $self = shift;
$self->{ua} ||= LWP::UserAgent->new;
$self->{ua_async} ||= Dwarf::HTTP::Async->new;
$self->{urls} ||= {
api => 'http://api.mixi-platform.com/2',
authorization => 'https://mixi.jp/connect_authorize.pl',
access_token => 'https://secure.mixi-platform.com/2/token',
};
$self->{on_error} ||= sub { die @_ };
}
sub _build_name {
my $self = shift;
$self->init_user unless defined $self->{name};
return $self->{name};
}
sub _build_profile_image {
my $self = shift;
$self->init_user unless defined $self->{profile_image};
return $self->{profile_image};
}
sub _bulid_friends {
my $self = shift;
my $data = $self->call('people/@me/@friends', 'GET', { count => 1000 });
return $data->{entry};
}
sub init_user {
my $self = shift;
$self->authorized;
my $user = $self->show_user;
$self->{name} = encode_utf8($user->{displayName});
$self->{profile_image} = encode_utf8($user->{thumbnailUrl});
}
sub authorized {
my ($self, $will_die) = @_;
$will_die ||= 1;
my $authorized = defined $self->access_token;
if ($will_die && !$authorized) {
$self->on_error("Unauthorized");
}
return $authorized;
examples/helloworld/app/lib/Dwarf/Module/SocialMedia/Mixi.pm view on Meta::CPAN
sub request_access_token {
my ($self, %params) = @_;
die 'key must be specified.' unless defined $self->{key};
die 'secret must be specified.' unless defined $self->{secret};
die "grant_type must be specified." unless defined $params{grant_type};
$params{client_id} ||= $self->key;
$params{client_secret} ||= $self->secret;
my $now = time;
my $res = $self->ua->post(
$self->urls->{access_token},
\%params
);
my $data = $self->validate($res);
$self->access_token($data->{access_token});
$self->refresh_token($data->{refresh_token});
$self->expires_in($data->{expires_in});
$self->got_access_token_at($now);
}
sub renew_access_token {
my $self = shift;
my $now = time;
if (defined $self->expires_in and defined $self->got_access_token_at) {
if ($now > $self->got_access_token_at + $self->expires_in) {
$self->request_access_token(
grant_type => "refresh_token",
refresh_token => $self->refresh_token,
);
}
}
}
sub _make_request {
my ($self, $command, $method, $params, $content) = @_;
$method = uc $method;
my $uri = URI->new($self->urls->{api} . '/' . $command);
my @p;
if ($method eq 'GET') {
$uri->query_form(%{ $params });
@p = ($uri, 'Authorization' => 'OAuth ' . $self->access_token);
} else {
@p = ($uri, $params, 'Authorization' => 'OAuth ' . $self->access_token);
if (defined $content) {
push @p, (
'Content-Type' => 'application/json',
'Content' => $content
);
}
}
no strict 'refs';
my $req = &{"HTTP::Request::Common::$method"}(@p);
return $req;
}
sub call {
my ($self, $command, $method, $params, $content) = @_;
$self->authorized;
$self->renew_access_token;
my $req = $self->_make_request($command, $method, $params);
my $res = $self->ua->request($req);
return $self->validate($res);
}
sub call_async {
my $self = shift;
$self->authorized;
$self->renew_access_token;
my @requests;
for my $row (@_) {
push @requests, $self->_make_request(@{ $row });
}
my @responses = $self->ua_async->request_in_parallel(@requests);
my @contents;
for my $res (@responses) {
push @contents, $self->validate($res);
}
return @contents;
}
sub validate {
my ($self, $res) = @_;
my $content = eval { decode_json($res->content) };
if ($@) {
$content = $res->content;
}
unless ($res->code =~ /^2/) {
if (my $error = $res->header("www-authenticate")) {
$self->on_error->($error);
}
$self->on_error->("Unknown Error.");
}
return $content;
}
1;
( run in 0.486 second using v1.01-cache-2.11-cpan-d8267643d1d )