updated Storage server
[Evergreen.git] / Open-ILS / src / perlmods / OpenILS / Application / Storage / Publisher.pm
1 package OpenILS::Application::Storage::Publisher;
2 use base qw/OpenILS::Application::Storage/;
3 our $VERSION = 1;
4 my $pg = 'OpenILS::Application::Storage::Driver::Pg';
5
6 use OpenSRF::EX qw/:try/;;
7 use OpenSRF::Utils::Logger;
8 my $log = 'OpenSRF::Utils::Logger';
9
10 use OpenILS::Utils::Fieldmapper;
11 use OpenILS::Application::Storage::CDBI;
12
13 #use OpenILS::Application::Storage::CDBI::actor;
14 #use OpenILS::Application::Storage::CDBI::asset;
15 #use OpenILS::Application::Storage::CDBI::biblio;
16 #use OpenILS::Application::Storage::CDBI::config;
17 #use OpenILS::Application::Storage::CDBI::metabib;
18
19 use OpenILS::Application::Storage::Publisher::actor;
20 #use OpenILS::Application::Storage::Publisher::asset;
21 use OpenILS::Application::Storage::Publisher::biblio;
22 use OpenILS::Application::Storage::Publisher::config;
23 use OpenILS::Application::Storage::Publisher::metabib;
24
25 sub retrieve_node {
26         my $self = shift;
27         my $client = shift;
28         my @ids = @_;
29
30         my $cdbi = $self->{cdbi};
31
32         for my $id ( @ids ) {
33                 next unless ($id);
34
35                 my ($rec) = $cdbi->fast_fieldmapper($id);
36                 $client->respond( $rec ) if ($rec);
37
38                 last if ($self->api_name !~ /batch/o);
39         }
40         return undef;
41 }
42
43 sub search {
44         my $self = shift;
45         my $client = shift;
46         my $searches = shift;
47
48         my $cdbi = $self->{cdbi};
49
50         $log->debug("Searching $cdbi for { ".join(',', map { "$_ => $$searches{$_}" } keys %$searches).' }',DEBUG);
51
52         for my $obj ($cdbi->search($searches)) {
53                 $client->respond( $obj->to_fieldmapper );
54         }
55         return undef;
56 }
57
58 sub search_one_field {
59         my $self = shift;
60         my $client = shift;
61         my @terms = @_;
62
63         (my $search_type = $self->api_name) =~ s/.*\.(search[^.]*).*/$1/o;
64         (my $col = $self->api_name) =~ s/.*\.$search_type\.([^.]+).*/$1/;
65         my $cdbi = $self->{cdbi};
66
67         my $like = 0;
68         $like = 1 if ($search_type =~ /like$/o);
69
70         for my $term (@terms) {
71                 $log->debug("Searching $cdbi for $col using type $search_type, value '$term'",DEBUG);
72                 $client->respond( [ $cdbi->fast_fieldmapper($term,$col,$like) ] );
73         }
74         return undef;
75 }
76
77
78 sub create_node {
79         my $self = shift;
80         my $client = shift;
81         my $node = shift;
82
83         my $cdbi = $self->{cdbi};
84
85         my $success;
86         try {
87                 my $rec = $cdbi->create($node);
88                 $success = $rec->id if ($rec);
89         } catch Error with {
90                 $success = 0;
91         };
92
93         return $success;
94 }
95
96 sub update_node {
97         my $self = shift;
98         my $client = shift;
99         my $node = shift;
100
101         my $cdbi = $self->{cdbi};
102
103         return $cdbi->update($node);
104 }
105
106 sub mass_delete {
107         my $self = shift;
108         my $client = shift;
109         my $search = shift;
110
111         my $where = 'WHERE ';
112
113         my $cdbi = $self->{cdbi};
114         my $table = $cdbi->table;
115
116         my @keys = sort keys %$search;
117         
118         my @wheres;
119         for my $col ( @keys ) {
120                 push @wheres, "$col = ?";
121         }
122         $where .= join ' AND ', @wheres;
123
124         my $delete = "DELETE FROM $table $where";
125
126         $log->debug("Performing MASS deletion : $delete",DEBUG);
127
128         my $dbh = $cdbi->db_Main;
129         my $success = 1;
130         try {
131                 my $sth = $dbh->prepare($delete);
132                 $sth->execute( map { "$_" } @$search{@keys} );
133                 $sth->finish;
134                 $log->debug("MASS Delete succeeded",DEBUG);
135         } catch Error with {
136                 $log->debug("MASS Delete FAILED : ".shift(),DEBUG);
137                 $success = 0;
138         };
139         return $success;
140 }
141
142 sub delete_node {
143         my $self = shift;
144         my $client = shift;
145         my $node = shift;
146
147         my $cdbi = $self->{cdbi};
148
149         my $success = 1;
150         try {
151                 $success = $cdbi->delete($node);
152         } catch Error with {
153                 $success = 0;
154         };
155         return $success;
156 }
157
158 sub batch_call {
159         my $self = shift;
160         my $client = shift;
161         my @nodes = @_;
162
163         my $cdbi = $self->{cdbi};
164         my $api_name = $self->api_name;
165         (my $single_call_api_name = $api_name) =~ s/batch\.//o;
166
167         $log->debug("Default $api_name looking up $single_call_api_name...",INTERNAL);
168         my $method = $self->method_lookup($single_call_api_name);
169
170         my @success;
171         while ( my $node = shift(@nodes) ) {
172                 my ($res) = $method->run( $node ); 
173                 push(@success, 1) if ($res >= 0);
174         }
175
176         my $insert_total = 0;
177         $insert_total += $_ for (@success);
178
179         return $insert_total;
180 }
181
182 for my $fmclass ( Fieldmapper->classes ) {
183         (my $cdbi = $fmclass) =~ s/^Fieldmapper:://o;
184         (my $class = $cdbi) =~ s/::.*//o;
185         (my $api_class = $cdbi) =~ s/::/./go;
186         my $registration_class = __PACKAGE__ . "::$class";
187         my $api_prefix = 'open-ils.storage.'.$api_class;
188
189         # Create the search method
190         unless ( __PACKAGE__->is_registered( $api_prefix.'.search' ) ) {
191                 __PACKAGE__->register_method(
192                         api_name        => $api_prefix.'.search',
193                         method          => 'search',
194                         api_level       => 1,
195                         stream          => 1,
196                         cdbi            => $cdbi,
197                 );
198         }
199
200         # Create the retrieve method
201         unless ( __PACKAGE__->is_registered( $api_prefix.'.retrieve' ) ) {
202                 __PACKAGE__->register_method(
203                         api_name        => $api_prefix.'.retrieve',
204                         method          => 'retrieve_node',
205                         api_level       => 1,
206                         cdbi            => $cdbi,
207                 );
208         }
209
210         # Create the batch retrieve method
211         unless ( __PACKAGE__->is_registered( $api_prefix.'.batch.retrieve' ) ) {
212                 __PACKAGE__->register_method(
213                         api_name        => $api_prefix.'.batch.retrieve',
214                         method          => 'retrieve_node',
215                         api_level       => 1,
216                         stream          => 1,
217                         cdbi            => $cdbi,
218                 );
219         }
220
221         for my $field ($fmclass->real_fields) {
222                 unless ( __PACKAGE__->is_registered( $api_prefix.'.search.'.$field ) ) {
223                         __PACKAGE__->register_method(
224                                 api_name        => $api_prefix.'.search.'.$field,
225                                 method          => 'search_one_field',
226                                 api_level       => 1,
227                                 cdbi            => $cdbi,
228                         );
229                 }
230                 unless ( __PACKAGE__->is_registered( $api_prefix.'.search_like.'.$field ) ) {
231                         __PACKAGE__->register_method(
232                                 api_name        => $api_prefix.'.search_like.'.$field,
233                                 method          => 'search_one_field',
234                                 api_level       => 1,
235                                 cdbi            => $cdbi,
236                         );
237                 }
238         }
239
240
241         # Create the create method
242         unless ( __PACKAGE__->is_registered( $api_prefix.'.create' ) ) {
243                 __PACKAGE__->register_method(
244                         api_name        => $api_prefix.'.create',
245                         method          => 'create_node',
246                         api_level       => 1,
247                         cdbi            => $cdbi,
248                 );
249         }
250
251         # Create the batch create method
252         unless ( __PACKAGE__->is_registered( $api_prefix.'.batch.create' ) ) {
253                 __PACKAGE__->register_method(
254                         api_name        => $api_prefix.'.batch.create',
255                         method          => 'batch_call',
256                         api_level       => 1,
257                         cdbi            => $cdbi,
258                 );
259         }
260
261         # Create the update method
262         unless ( __PACKAGE__->is_registered( $api_prefix.'.update' ) ) {
263                 __PACKAGE__->register_method(
264                         api_name        => $api_prefix.'.update',
265                         method          => 'update_node',
266                         api_level       => 1,
267                         cdbi            => $cdbi,
268                 );
269         }
270
271         # Create the batch update method
272         unless ( __PACKAGE__->is_registered( $api_prefix.'.batch.update' ) ) {
273                 __PACKAGE__->register_method(
274                         api_name        => $api_prefix.'.batch.update',
275                         method          => 'batch_call',
276                         api_level       => 1,
277                         cdbi            => $cdbi,
278                 );
279         }
280
281         # Create the delete method
282         unless ( __PACKAGE__->is_registered( $api_prefix.'.delete' ) ) {
283                 __PACKAGE__->register_method(
284                         api_name        => $api_prefix.'.delete',
285                         method          => 'delete_node',
286                         api_level       => 1,
287                         cdbi            => $cdbi,
288                 );
289         }
290
291         # Create the batch delete method
292         unless ( __PACKAGE__->is_registered( $api_prefix.'.batch.delete' ) ) {
293                 __PACKAGE__->register_method(
294                         api_name        => $api_prefix.'.batch.delete',
295                         method          => 'batch_call',
296                         api_level       => 1,
297                         cdbi            => $cdbi,
298                 );
299         }
300
301         # Create the search-based mass delete method
302         unless ( __PACKAGE__->is_registered( $api_prefix.'.mass_delete' ) ) {
303                 __PACKAGE__->register_method(
304                         api_name        => $api_prefix.'.mass_delete',
305                         method          => 'mass_delete',
306                         api_level       => 1,
307                         cdbi            => $cdbi,
308                 );
309         }
310
311 }
312
313 1;