root/WWW-OpenSearch/trunk/lib/WWW/OpenSearch.pm

Revision 1523 (checked in by miyagawa, 16 years ago)

impoert

  • Property svn:keywords set to Id Revision
Line 
1 package WWW::OpenSearch;
2
3 use strict;
4 use vars qw($VERSION);
5 $VERSION = '0.01';
6
7 use Carp;
8 use Data::Page;
9 use LWP::UserAgent;
10 use URI::Escape;
11 use XML::RSS;
12 use XML::Simple;
13
14 sub new {
15     my($class, $url) = @_;
16     $url or croak "Usage: WWW::OpenSearch->new(URL)";
17     my $self = bless { DescriptionUrl => $url }, $class;
18     $self->_init();
19     $self->fetch_description($url);
20     $self;
21 }
22
23 sub _init {
24     my $self = shift;
25     $self->{ua} = LWP::UserAgent->new(agent => "WWW::OpenSearch/$VERSION");
26     $self->{pager} = Data::Page->new();
27     $self->{pager}->current_page(1);
28 }
29
30 sub ua    { shift->{ua} }
31 sub pager { shift->{pager} }
32
33 sub fetch_description {
34     my($self, $url) = @_;
35     my $response = $self->ua->get($url);
36     croak "Error while fetching $url: ". $response->status_line
37         unless $response->is_success;
38     eval {
39         my $data = XML::Simple::XMLin($response->content);
40         for my $attr (keys %$data) {
41             next if $attr eq 'xmlns';
42             $self->{$attr} = $data->{$attr};
43         }
44     };
45     if ($@) {
46         croak "Error while parsing Description XML: $@";
47     }
48 }
49
50 sub search {
51     my($self, $query) = @_;
52     my $url = $self->setup_query($query);
53
54     my $response = $self->ua->get($url);
55     croak "Error while fetching $url: ", $response->status_line
56         unless $response->is_success;
57
58     my $rss;
59     eval {
60         $rss = XML::RSS->new();
61         $rss->add_module(
62             prefix => "openSearch",
63             uri => "http://a9.com/-/spec/opensearchrss/1.0/",
64         );
65         $rss->parse($response->content);
66         if (my $page = $rss->channel->{openSearch}) {
67             $self->pager->total_entries($page->{totalResults});
68             # XXX I don't understand how I parse startIndex attr.
69             $self->pager->entries_per_page($page->{itemsPerPage});
70         }
71     };
72     if ($@) {
73         croak "Error while parsing RSS feed: $@";
74     }
75     return $rss;
76 }
77
78 sub setup_query {
79     my($self, $query) = @_;
80     my $data;
81     $data->{searchTerms} = uri_escape($query);
82     $data->{count}       = $self->pager->entries_per_page;
83     $data->{startIndex}  = $self->pager->first == 0 ? 0 : $self->pager->first - 1;
84     $data->{startPage}   = $self->pager->current_page;
85
86     my $url = $self->{Url}; # copy
87     $url =~ s/{(searchTerms|count|startIndex|startPage)}/$data->{$1}/g;
88     $url;
89 }
90
91 1;
92 __END__
93
94 =head1 NAME
95
96 WWW::OpenSearch - Search A9 OpenSearch compatible engines
97
98 =head1 SYNOPSIS
99
100   use WWW::OpenSearch;
101
102   my $url = "http://bulkfeeds.net/opensearch.xml";
103   my $engine = WWW::OpenSearch->new($url);
104
105   my $name = $engine->{ShortName};
106   my @tags = $engine->{Tags};
107
108   my $feed = $engine->search("iPod");
109   for my $item (@{$feed->items}) {
110       print $item->{description};
111   }
112
113   # if you want to page through page 2 with 20 items in each page
114   # Note that some engine doesn't allow changing these values
115   $engine->pager->entries_per_page(20);
116   $engine->pager->current_page(2);
117   my $feed = $engine->search("iPod");
118
119 =head1 BETA
120
121 This module is in beta version, which means its API interface and functionalities may be changes in future releases.
122
123 =head1 DESCRIPTION
124
125 WWW::OpenSearch is a module to search A9's OpenSearch compatible search engines. See http://opensearch.a9.com/ for details.
126
127 =head1 AUTHOR
128
129 Tatsuhiko Miyagawa E<lt>miyagawa@bulknews.netE<gt>
130
131 This library is free software; you can redistribute it and/or modify
132 it under the same terms as Perl itself.
133
134 =head1 SEE ALSO
135
136 L<XML::Simple>, L<XML::RSS>, L<Data::Page>, L<LWP>
137
138 =cut
Note: See TracBrowser for help on using the browser.