/[mws]/trunk/MWS.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

Annotation of /trunk/MWS.pm

Parent Directory Parent Directory | Revision Log Revision Log


Revision 14 - (hide annotations)
Thu May 6 19:46:58 2004 UTC (20 years ago) by dpavlin
File size: 4826 byte(s)
Make mbox2swish universal for all indexer (moving index-specific
thinks in own .pm) -- after MWS_plucene.pm update it should work with it.
Use Text::AutoFormat to re-format messages wider than wrap_margin
(from global.conf). Hard-coded ISO-8859-2 encoding now works correctly,
Subject searches now remove common subject prefixes, template updates.

1 dpavlin 2 #!/usr/bin/perl -w
2    
3     package MWS;
4    
5     use strict;
6     use warnings;
7     use Carp;
8    
9 dpavlin 3 use Mail::Box::Manager;
10 dpavlin 4 use Config::IniFiles;
11 dpavlin 13 use POSIX qw(strftime);
12 dpavlin 14 use Text::Autoformat;
13    
14 dpavlin 12 #use MWS_plucene;
15     use MWS_swish;
16 dpavlin 3
17 dpavlin 2 require Exporter;
18    
19     our @ISA = qw(Exporter);
20    
21     our %EXPORT_TAGS = ();
22     our @EXPORT_OK;
23     our @EXPORT;
24    
25     our $VERSION = '1.00';
26    
27     my $folder; # placeholder for folders
28    
29 dpavlin 13 my $debug = 2;
30 dpavlin 2
31     sub new {
32     my $class = shift;
33     my $self = {};
34     bless($self, $class);
35    
36 dpavlin 4 my $config_file = shift || die "need index file";
37 dpavlin 2
38 dpavlin 4 $self->{config} = new Config::IniFiles( -file => $config_file );
39 dpavlin 2
40 dpavlin 4 my $index_file = $self->{config}->val('global', 'index') || croak "can't find [index] section in config file with path of index";
41    
42 dpavlin 12 $self->{mgr} = Mail::Box::Manager->new(access => 'r');
43     $self->{index_file} = $index_file;
44 dpavlin 4
45 dpavlin 2 # placeholder for opened folders
46     $self->{folder} = {};
47    
48 dpavlin 14 $self->{wrap_margin} = $self->{config}->val('global', 'wrap_margin');
49    
50 dpavlin 2 return $self;
51     }
52    
53 dpavlin 14 sub mbox_name2path {
54     my $self = shift;
55    
56     my $mbox = shift || croak "folder_name2path needs mbox name";
57    
58     return $self->{config}->val('folders', $mbox) || croak "comeone removed folder $mbox from config?";
59     }
60    
61 dpavlin 7 sub open_folder {
62 dpavlin 2 my $self = shift;
63    
64 dpavlin 7 my $mbox = shift || croak "open_folder needs mbox name";
65 dpavlin 2
66     if (! $self->{folder}->{$mbox}) {
67 dpavlin 14 my $mbox_path = $self->mbox_name2path($mbox);
68    
69 dpavlin 13 print STDERR "about to open_folder($mbox)\n" if ($debug == 2);
70 dpavlin 14
71 dpavlin 4 $self->{folder}->{$mbox} = $self->{mgr}->open($mbox_path) || croak "can't open folder $mbox at '$mbox_path': $!";
72 dpavlin 14
73     print STDERR "open_folder($mbox) ok\n" if ($debug);
74 dpavlin 2 }
75    
76 dpavlin 7 return $self->{folder}->{$mbox};
77    
78     }
79    
80 dpavlin 14 sub close_folder {
81     my $self = shift;
82    
83     my $mbox = shift || croak "open_folder needs mbox name";
84    
85     return $self->{folder}->{$mbox}->close(write => 'NEVER');
86     }
87    
88 dpavlin 7 sub fetch_message {
89     my $self = shift;
90    
91     my $mbox_id = shift || die "need mbox_id!";
92     my ($mbox,$id) = split(/ /,$mbox_id);
93    
94     # return message with ID
95 dpavlin 13 print STDERR "fetch $id from $mbox\n" if ($debug);
96 dpavlin 7 return $self->open_folder($mbox)->find($id) ||
97 dpavlin 2 print STDERR "can't find message $id in $mbox. Time to re-index?\n";
98     }
99    
100    
101     sub search {
102     my $self = shift;
103    
104     my $s = shift || carp "search called without argument!";
105    
106 dpavlin 13 print STDERR "search_index($s)\n" if ($debug == 2);
107 dpavlin 9 my @index_ids = $self->search_index($s);
108 dpavlin 2
109     $self->{'index_ids'} = \@index_ids;
110    
111     my $results = $#index_ids + 1;
112     $self->{'results'} = $results;
113    
114     $self->{'curr_result'} = 0;
115    
116 dpavlin 13 print STDERR "$results results\n" if ($debug == 2);
117    
118 dpavlin 2 return $results || 'error';
119     }
120    
121     sub unroll($$$) {
122 dpavlin 13 my $self = shift;
123    
124 dpavlin 2 my ($message,$part,$sub) = @_;
125    
126     my @arr;
127    
128     foreach my $from ($message->$part) {
129 dpavlin 7 my $tmp = $from->$sub;
130 dpavlin 14 if ($tmp) {
131     $tmp =~ s/^\s*["'](.*)["']\s*$/$1/;
132     push @arr, $tmp;
133     }
134 dpavlin 2 }
135 dpavlin 14
136     return @arr;
137 dpavlin 2 }
138 dpavlin 4
139     sub fetch_all_results {
140     my $self = shift;
141    
142     croak "results called before search!" if (! $self->{'index_ids'});
143    
144 dpavlin 14 print STDERR "fetch_all_results [",scalar @{$self->{'index_ids'}},"]\n" if ($debug == 2);
145 dpavlin 13
146 dpavlin 4 my @arr;
147    
148     foreach my $id (@{$self->{'index_ids'}}) {
149     push @arr, $self->fetch_result_by_id($id);
150     }
151    
152     return @arr;
153     }
154    
155 dpavlin 2 sub fetch_result {
156     my $self = shift;
157    
158 dpavlin 3 my $args = {@_};
159    
160 dpavlin 2 croak "results called before search!" if (! $self->{'index_ids'});
161    
162     my $curr = $self->{'curr_result'}++;
163    
164     my $id = $self->{'index_ids'}->[$curr];
165 dpavlin 14
166     print STDERR "fetch_result: $curr = $id\n" if ($debug == 2);
167 dpavlin 2
168 dpavlin 4 return $self->fetch_result_by_id($id);
169     }
170 dpavlin 2
171 dpavlin 7 sub plain_text_body {
172     my $self = shift;
173     my $message = shift || croak "plain_text_body needs message!";
174    
175 dpavlin 14 my $body;
176    
177 dpavlin 7 if (! $message->isMultipart) {
178 dpavlin 14 $body = $message->decoded->string;
179 dpavlin 7 } else {
180     foreach my $part ($message->parts) {
181     if ($part->body->mimeType eq 'text/plain') {
182 dpavlin 14 $body = $part->decoded->string;
183     last;
184 dpavlin 7 }
185     }
186     }
187 dpavlin 14
188     # reformat with Text::Autoformat
189     my $wrap = $self->{wrap_margin};
190     if ($wrap && $body && $body =~ m/^.{$wrap}..*$/m) {
191     $body = autoformat $body;
192     $body .="\n[reformated using autoformat, margin at $wrap]" if ($debug == 2);
193     }
194    
195     return $body;
196 dpavlin 7 }
197    
198    
199 dpavlin 4 sub fetch_result_by_id {
200     my $self = shift;
201    
202     my $id = shift || return;
203    
204 dpavlin 13 my $row = $self->{cache}->{$id};
205 dpavlin 2
206 dpavlin 13 if (! $row) {
207 dpavlin 2
208 dpavlin 13 print STDERR "fetch_result_by_id($id) not in cache, hitting disk\n" if ($debug == 2);
209 dpavlin 2
210 dpavlin 13 my $message = $self->fetch_message($id) || print STDERR "can't fetch message '$id'";
211    
212     $row->{'id'} = $id;
213 dpavlin 14 @{$row->{'from'}} = $self->unroll($message,'from','phrase');
214     @{$row->{'to'}} = $self->unroll($message,'to','phrase');
215     @{$row->{'cc'}} = $self->unroll($message,'cc','phrase');
216 dpavlin 13 $row->{'subject'} = $message->subject;
217     $row->{'body'} = $self->plain_text_body($message);
218     $row->{'date'} = $message->date;
219    
220     # XXX store in cache?
221     $self->{cache}->{$id} = $row;
222     print STDERR "$id stored in cache\n" if ($debug == 2);
223     } else {
224     print STDERR "fetch_result_by_id($id) in cache\n" if ($debug == 2);
225     }
226    
227 dpavlin 2 return $row;
228    
229     }

Properties

Name Value
svn:executable *

  ViewVC Help
Powered by ViewVC 1.1.26