/[webpac2]/Webpacus/lib/Webpacus/Controller/Search.pm
This is repository of my old source code which isn't updated any more. Go to git.rot13.org for current projects!
ViewVC logotype

Contents of /Webpacus/lib/Webpacus/Controller/Search.pm

Parent Directory Parent Directory | Revision Log Revision Log


Revision 441 - (show annotations)
Sun Apr 30 23:41:58 2006 UTC (18 years ago) by dpavlin
File size: 6083 byte(s)
 r542@llin:  dpavlin | 2006-05-01 01:42:45 +0200
 pager partially works

1 package Webpacus::Controller::Search;
2
3 use strict;
4 use warnings;
5 use base 'Catalyst::Controller';
6
7 use lib '/data/webpac2/lib';
8 use WebPAC::Search::Estraier 0.03;
9 use Data::SpreadPagination;
10
11
12 =head1 NAME
13
14 Webpacus::Controller::Search - Search WebPAC data
15
16 =head1 SYNOPSIS
17
18 See L<WebPAC>, L<Webpacus>
19
20 =head1 DESCRIPTION
21
22 Catalyst Controller for search fields Hyper Estraier
23
24 =head1 METHODS
25
26 =over 4
27
28 =item default
29
30 =cut
31
32 sub default : Private {
33 my ( $self, $c ) = @_;
34
35 $c->log->dumper($c->req->params, 'params');
36
37 $c->stash->{template} = 'search.tt';
38 }
39
40 =item suggest
41
42 Returns results for REST URIs like:
43
44 C<search/suggest?search=FieldName&show=TitleProper&FieldName=query%20string>
45
46 It will use C<search> field to filter results (and using additional
47 C<FieldName> as value of search) and return C<TitleProper> field
48 for results.
49
50 If C<search> field has magic value <all>, it will search over all data, not
51 just one specified field:
52
53 C<search/suggest?search=all&show=TitleProper&all=query%20string>
54
55 =cut
56
57 sub suggest : Local {
58 my ( $self, $c ) = @_;
59
60 my $search = $c->req->params->{search};
61 my $show = $c->req->params->{show};
62
63 my $log = $c->log;
64
65 my $webpac = $c->comp('Model::WebPAC');
66 #$c->log->dumper( $c->stash, 'stash' );
67 $webpac->setup_site( $c->stash->{site} );
68
69 my $q = $c->req->params->{ $search || 'all' } || $c->response->body("no results");
70
71 $log->info("search for '$q' in $search and display $show\n");
72
73 my $max = $c->config->{'hits_for_suggest'};
74 if (! $max) {
75 $log->info("hits_for_suggest isn't defined, defaulting to 10");
76 $c->config->{'hits_for_suggest'} = 10;
77 $max = 10;
78 }
79
80 $c->forward('filter_database');
81
82 my $hits = $webpac->search(
83 phrase => $q,
84 add_attr => $c->stash->{attr},
85 get_attr => [ $show ],
86 max => $max,
87 );
88
89 my $used;
90 my @suggestions;
91
92 foreach my $res (@{$hits}) {
93 my $v = $res->{ $show } || next;
94 next if ($used->{ $v }++);
95 push @suggestions, $v;
96 }
97
98 $log->debug( ($#suggestions + 1) . " unique hits returned");
99
100 $c->response->body( $c->prototype->auto_complete_result( \@suggestions ) );
101 }
102
103
104 =item results
105
106 Returns results for search query
107
108 =cut
109
110 sub results : Local {
111 my ( $self, $c ) = @_;
112
113 my $params = $c->req->params;
114
115 # do full-page refresh for clients without JavaScript
116 $c->stash->{results} = $c->subreq('/search/results/ajax', {}, $params);
117 $c->stash->{template} = 'search.tt';
118 }
119
120
121 =item results_ajax
122
123 Private method which uses C<Model::WebPAC> and returns results for search
124 query It generatets just I<inner> HTML for results div, so it has C<_ajax>
125 in name.
126
127 =cut
128
129 # specify all Hyper Estraier operators which should stop this module
130 # from splitting search query and joining it with default operator
131 my $hest_op_regex = '(:?\[(:?BW|EW|RX)\]|AND|OR|ANDNOT)';
132
133 sub results_ajax : Path( 'results/ajax' ) {
134 my ( $self, $c ) = @_;
135
136 my $params = $c->req->params;
137 my $webpac = $c->comp('Model::WebPAC');
138 $webpac->setup_site( $c->stash->{site} );
139 my $log = $c->log;
140
141 $log->dumper($params, 'params');
142
143 if (! $params->{_page} || $params->{_page} < 1) {
144 $params->{_page} = 1;
145 $log->warn("fixed _page parametar to 1");
146 }
147
148 my @words;
149 # default operator to join fields/words
150 my $operator = 'AND';
151
152 foreach my $f (keys %{ $params }) {
153
154 next if ($f =~ m/^_/o);
155
156 my $v = $params->{$f} || next;
157
158 if (my $op = $params->{ '_' . $f}) {
159 if ($v =~ /$hest_op_regex/) {
160 # don't split words if there is Hyper Estraier
161 # operator in them
162 push @words, $v;
163 } else {
164 push @words, join(" $op ", split(/\s+/, $v) );
165 }
166 } else {
167 push @words, $v;
168 }
169
170 next if ($f eq 'all'); # don't add_attr for magic field all
171
172 if ($v !~ /\s/) {
173 push @{ $c->stash->{attr} }, "$f ISTRINC $v";
174 } else {
175 map {
176 push @{ $c->stash->{attr} }, "$f ISTRINC $_";
177 } grep { ! /$hest_op_regex/ } split(/\s+/, $v);
178 }
179 }
180
181 $c->forward('filter_database');
182
183 my $q = join(" $operator ", @words);
184
185 my $template = $params->{'_template'} || $c->config->{webpac}->{template};
186
187 $log->die("can't find _template or default from configuration!") unless ($template);
188
189 my $hits_on_page = $c->config->{'hyperestraier'}->{'hits_on_page'} || 10;
190
191 $log->debug("using template $template to produce $hits_on_page results");
192
193 $c->stash->{html_results} = $webpac->search(
194 phrase => $q,
195 template => $template,
196 add_attr => $c->{stash}->{attr},
197 get_attr => [ '@uri' ],
198 max => $hits_on_page,
199 page => $params->{'_page'},
200 );
201
202 $c->stash->{hints} = $webpac->hints;
203
204 $c->stash->{phrase} = $q;
205 $c->stash->{page} = $params->{_page};
206 $c->stash->{hits_on_page} = $hits_on_page;
207
208 # create pager
209 $c->stash->{pager} = new Data::SpreadPagination({
210 totalEntries => $webpac->hints->{hit},
211 entriesPerPage => $hits_on_page,
212 currentPage => $params->{_page},
213 maxPages => $c->config->{pager}->{max_pages} || 10,
214 });
215
216 # generate URL for pager without _page param
217 my $params_nopage = $params;
218 delete($params_nopage->{_page});
219 $c->stash->{uri_nopage} = $c->uri_for('results', $params_nopage)->as_string;
220
221 $c->stash->{template} = 'results.tt';
222
223 }
224
225 =item filter_database
226
227 Takes C<< $c->req->params >> and adds Hyper Estraier
228 filters for checked databases to C<< $c->stash->{attr} >>.
229
230 =cut
231
232 sub filter_database : Private {
233 my ( $self, $c ) = @_;
234
235 my $params = $c->req->params;
236
237 if ($params->{_database}) {
238 my $type = $c->config->{hyperstraier}->{type} || 'search';
239 my $attr;
240 if (ref($params->{_database}) eq 'ARRAY') {
241 # FIXME do we need to add $ at end?
242 $attr .= '(' . join("|",@{$params->{_database}}) . ')';
243 } else {
244 $attr .= $params->{_database};
245 }
246 push @{ $c->stash->{attr} }, '@uri STRRX /' . $type . '/' . $attr . '/';
247 $c->log->debug("filter_database: " . join(",", @{ $c->stash->{attr} }) );
248 }
249
250
251 }
252
253 =item record
254
255 forwarded to C</editor/record>
256
257 =cut
258
259 sub record : Local {
260 my ( $self, $c ) = @_;
261
262 $c->detach( '/editor/record' );
263 }
264
265 =back
266
267 =head1 AUTHOR
268
269 Dobrica Pavlinusic C<< <dpavlin@rot13.org> >>
270
271 =head1 LICENSE
272
273 This library is free software, you can redistribute it and/or modify
274 it under the same terms as Perl itself.
275
276 =cut
277
278 1;

  ViewVC Help
Powered by ViewVC 1.1.26