package Web::oEmbed;
use strict;
use 5.8.1;
our $VERSION = '0.04';
use Any::Moose;
has 'format' => (is => 'rw', default => 'json');
has 'discovery' => (is => 'rw');
has 'providers' => (is => 'rw', isa => 'ArrayRef', default => sub { [] });
has 'agent' => (is => 'rw', isa => 'LWP::UserAgent', default => sub {
require LWP::UserAgent;
LWP::UserAgent->new( agent => __PACKAGE__ . "/" . $VERSION );
});
use URI;
use Web::oEmbed::Response;
sub register_provider {
my($self, $provider) = @_;
$provider->{regexp} = $self->_compile_url($provider->{url});
push @{$self->providers}, $provider;
}
sub _compile_url {
my($self, $url) = @_;
my $res;
my $uri = URI->new($url);
$res = $uri->scheme . "://";
$res .= _run_regexp($uri->host, '[0-9a-zA-Z\-]+');
$res .= _run_regexp($uri->path, "[$URI::uric]+" );
$res;
}
sub _run_regexp {
my($str, $replacement) = @_;
$str =~ s/(?:(\*)|([^\*]+))/$1 ? $replacement : quotemeta($2)/eg;
$str;
}
sub provider_for {
my($self, $uri) = @_;
for my $provider (@{$self->providers}) {
if ($uri =~ m!^$provider->{regexp}!) {
return $provider;
}
}
return;
}
sub request_url {
my($self, $uri, $opt) = @_;
my $params = {
url => $uri,
format => $opt->{format} || $self->format,
};
$params->{maxwidth} = $opt->{maxwidth} if exists $opt->{maxwidth};
$params->{maxheight} = $opt->{maxheight} if exists $opt->{maxheight};
my $provider = $self->provider_for($uri) or return;
my $req_uri = URI->new( $provider->{api} );
if ($req_uri->path =~ /%7Bformat%7D/) { # yuck
my $path = $req_uri->path;
$path =~ s/%7Bformat%7D/$params->{format}/;
$req_uri->path($path);
delete $params->{format};
}
$req_uri->query_form($params);
$req_uri;
}
sub embed {
my($self, $uri, $opt) = @_;
my $url = $self->request_url($uri, $opt) or return;
my $res = $self->agent->get($url);
Web::oEmbed::Response->new_from_response($res, $uri);
}
1;
__END__
=encoding utf-8
=for stopwords oEmbed
=head1 NAME
Web::oEmbed - oEmbed consumer
=head1 SYNOPSIS
use Web::oEmbed;
my $consumer = Web::oEmbed->new({ format => 'json' });
$consumer->register_provider({
url => 'http://*.flickr.com/*',
api => 'http://www.flickr.com/services/oembed/',
});
my $response = eval { $consumer->embed("http://www.flickr.com/photos/bulknews/2752124387/") };
if ($response) {
$response->matched_uri; # 'http://www.flickr.com/photos/bulknews/2752124387/'
$response->type; # 'photo'
$response->title; # title of the photo
$response->url; # JPEG URL
$response->width; # JPEG width
$response->height; # JPEG height
$response->provider_name; # Flickr
$response->provider_url; # http://www.flickr.com/
print $response->render; # handy shortcut to generate
tag
}
=head1 DESCRIPTION
Web::oEmbed is a module that implements oEmbed consumer.
=head1 METHODS
=over 4
=item new
$consumer = Web::oEmbed->new;
$consumer = Web::oEmbed->new({ format => 'json' });
Creates a new Web::oEmbed instance. You can specify the default format
that will be used when it's not specified in the C