added zebra_insert_record call, function in perl api, documentation and tests
authorpop <pop>
Thu, 13 Mar 2003 04:25:17 +0000 (04:25 +0000)
committerpop <pop>
Thu, 13 Mar 2003 04:25:17 +0000 (04:25 +0000)
index/extract.c
index/index.h
index/zebraapi.c
perl/IDZebra.i
perl/IDZebra_wrap.c
perl/lib/IDZebra.pm
perl/lib/IDZebra/Session.pm
perl/t/03_record_update.t

index e431453..edf6e37 100644 (file)
@@ -1,4 +1,4 @@
-/* $Id: extract.c,v 1.142 2003-03-12 17:11:23 pop Exp $
+/* $Id: extract.c,v 1.143 2003-03-13 04:25:17 pop Exp $
    Copyright (C) 1995,1996,1997,1998,1999,2000,2001,2002,2003
    Index Data Aps
 
@@ -918,7 +918,7 @@ int extract_rec_in_mem (ZebraHandle zh, const char *recordType,
                                 sysno,
                                 match_criteria,
                                 "<no file>",
-                                0));
+                                0,1));
 }
 /*
   If sysno is provided, then it's used to identify the reocord.
@@ -935,7 +935,8 @@ int bufferExtractRecord (ZebraHandle zh,
                         int *sysno,
                         const char *match_criteria,
                         const char *fname,
-                        int force_update)
+                        int force_update,
+                        int allow_update)
 
 {
     RecordAttr *recordAttr;
@@ -1094,13 +1095,20 @@ int bufferExtractRecord (ZebraHandle zh,
         extract_flushRecordKeys (zh, *sysno, 1, &zh->reg->keys);
 
         zh->records_inserted++;
-    }
+    } 
     else
     {
         /* record already exists */
         struct recKeys delkeys;
         struct sortKeys sortKeys;
 
+       if (!allow_update) {
+             logf (LOG_LOG, "skipped %s %s %ld", 
+                   recordType, fname, (long) recordOffset);
+             logRecord(zh);
+             return -1;
+       }
+
         rec = rec_get (zh->reg->records, *sysno);
         assert (rec);
        
index 56e7292..1f0ac62 100644 (file)
@@ -1,4 +1,4 @@
-/* $Id: index.h,v 1.96 2003-03-12 17:11:23 pop Exp $
+/* $Id: index.h,v 1.97 2003-03-13 04:25:17 pop Exp $
    Copyright (C) 1995,1996,1997,1998,1999,2000,2001,2002
    Index Data Aps
 
@@ -421,7 +421,8 @@ int bufferExtractRecord (ZebraHandle zh,
                         int *sysno,
                         const char *match_criteria,
                         const char *fname,
-                        int force_update);
+                        int force_update,
+                        int allow_update);
 
 int extract_rec_in_mem (ZebraHandle zh, const char *recordType,
                         const char *buf, size_t buf_size,
index 7ce50b9..01c6433 100644 (file)
@@ -1,4 +1,4 @@
-/* $Id: zebraapi.c,v 1.92 2003-03-12 17:11:23 pop Exp $
+/* $Id: zebraapi.c,v 1.93 2003-03-13 04:25:17 pop Exp $
    Copyright (C) 1995,1996,1997,1998,1999,2000,2001,2002,2003
    Index Data Aps
 
@@ -1776,6 +1776,32 @@ void api_records_retrieve (ZebraHandle zh, ODR stream,
   If not, and a record is provided, then sysno is got from there
 */
 
+int zebra_insert_record (ZebraHandle zh, 
+                        struct recordGroup *rGroup,
+                        const char *recordType,
+                        int sysno, const char *match, const char *fname,
+                        const char *buf, int buf_size,
+                        int force_update) // This one is ignored
+{
+    int res;
+
+    if (buf_size < 1) buf_size = strlen(buf);
+
+    zebra_begin_trans(zh, 1);
+    res=bufferExtractRecord (zh, buf, buf_size, rGroup, 
+                            0, // delete_flag 
+                            0, // test_mode,
+                            recordType,
+                            &sysno,   
+                            match, fname,
+                            force_update, 
+                            0); // allow_update     
+    zebra_end_trans(zh); 
+    if (res < 0) return (res);
+    return sysno; 
+}
+
 int zebra_update_record (ZebraHandle zh, 
                         struct recordGroup *rGroup,
                         const char *recordType,
@@ -1795,11 +1821,14 @@ int zebra_update_record (ZebraHandle zh,
                             recordType,
                             &sysno,   
                             match, fname,
-                            force_update);     
+                            force_update, 
+                            1); // allow_update    
     zebra_end_trans(zh); 
     return sysno; 
 }
 
+
+
 int zebra_delete_record (ZebraHandle zh, 
                         struct recordGroup *rGroup, 
                         const char *recordType,
@@ -1818,7 +1847,8 @@ int zebra_delete_record (ZebraHandle zh,
                             recordType,
                             &sysno,
                             match,fname,
-                            force_update);    
+                            force_update,
+                            1); // allow_update    
     zebra_end_trans(zh);
     return sysno;   
 }
index 27af217..6a9c75d 100644 (file)
@@ -278,6 +278,17 @@ void zebra_repository_show (ZebraHandle zh);
    If not, and match_criteria is provided, then sysno is guessed
    If not, and a record is provided, then sysno is got from there */
 
+%name(insert_record)       
+int zebra_insert_record (ZebraHandle zh, 
+                        recordGroup *rGroup, 
+                        const char *recordType,
+                        int sysno, 
+                        const char *match, 
+                        const char *fname,
+                        const char *buf, 
+                        int buf_size,
+                        int force_update);
+
 %name(update_record)       
 int zebra_update_record (ZebraHandle zh, 
                         recordGroup *rGroup, 
index 73c64e9..e147810 100644 (file)
@@ -212,7 +212,7 @@ SWIG_TypeClientData(swig_type_info *ti, void *clientdata) {
  * perl5.swg
  *
  * Perl5 runtime library
- * $Header: /home/cvsroot/idis/perl/Attic/IDZebra_wrap.c,v 1.15 2003-03-12 17:08:53 pop Exp $
+ * $Header: /home/cvsroot/idis/perl/Attic/IDZebra_wrap.c,v 1.16 2003-03-13 04:25:17 pop Exp $
  * ----------------------------------------------------------------------------- */
 
 #define SWIGPERL
@@ -3976,6 +3976,61 @@ XS(_wrap_repository_show) {
 }
 
 
+XS(_wrap_insert_record) {
+    char _swigmsg[SWIG_MAX_ERRMSG] = "";
+    const char *_swigerr = _swigmsg;
+    {
+        ZebraHandle arg1 ;
+        recordGroup *arg2 ;
+        char *arg3 ;
+        int arg4 ;
+        char *arg5 ;
+        char *arg6 ;
+        char *arg7 ;
+        int arg8 ;
+        int arg9 ;
+        int result;
+        int argvi = 0;
+        dXSARGS;
+        
+        if ((items < 9) || (items > 9)) {
+            SWIG_croak("Usage: insert_record(zh,rGroup,recordType,sysno,match,fname,buf,buf_size,force_update);");
+        }
+        {
+            ZebraHandle * argp;
+            if (SWIG_ConvertPtr(ST(0),(void **) &argp, SWIGTYPE_p_ZebraHandle,0) < 0) {
+                SWIG_croak("Type error in argument 1 of insert_record. Expected _p_ZebraHandle");
+            }
+            arg1 = *argp;
+        }
+        {
+            if (SWIG_ConvertPtr(ST(1), (void **) &arg2, SWIGTYPE_p_recordGroup,0) < 0) {
+                SWIG_croak("Type error in argument 2 of insert_record. Expected _p_recordGroup");
+            }
+        }
+        if (!SvOK((SV*) ST(2))) arg3 = 0;
+        else arg3 = (char *) SvPV(ST(2), PL_na);
+        arg4 = (int) SvIV(ST(3));
+        if (!SvOK((SV*) ST(4))) arg5 = 0;
+        else arg5 = (char *) SvPV(ST(4), PL_na);
+        if (!SvOK((SV*) ST(5))) arg6 = 0;
+        else arg6 = (char *) SvPV(ST(5), PL_na);
+        if (!SvOK((SV*) ST(6))) arg7 = 0;
+        else arg7 = (char *) SvPV(ST(6), PL_na);
+        arg8 = (int) SvIV(ST(7));
+        arg9 = (int) SvIV(ST(8));
+        result = (int)zebra_insert_record(arg1,arg2,(char const *)arg3,arg4,(char const *)arg5,(char const *)arg6,(char const *)arg7,arg8,arg9);
+        
+        ST(argvi) = sv_newmortal();
+        sv_setiv(ST(argvi++), (IV) result);
+        XSRETURN(argvi);
+        fail:
+        (void) _swigerr;
+    }
+    croak(_swigerr);
+}
+
+
 XS(_wrap_update_record) {
     char _swigmsg[SWIG_MAX_ERRMSG] = "";
     const char *_swigerr = _swigmsg;
@@ -8464,6 +8519,7 @@ static swig_command_info swig_commands[] = {
 {"IDZebrac::repository_update", _wrap_repository_update},
 {"IDZebrac::repository_delete", _wrap_repository_delete},
 {"IDZebrac::repository_show", _wrap_repository_show},
+{"IDZebrac::insert_record", _wrap_insert_record},
 {"IDZebrac::update_record", _wrap_update_record},
 {"IDZebrac::delete_record", _wrap_delete_record},
 {"IDZebrac::search_PQF", _wrap_search_PQF},
index 8540a01..927e004 100644 (file)
@@ -64,6 +64,7 @@ package IDZebra;
 *repository_update = *IDZebrac::repository_update;
 *repository_delete = *IDZebrac::repository_delete;
 *repository_show = *IDZebrac::repository_show;
+*insert_record = *IDZebrac::insert_record;
 *update_record = *IDZebrac::update_record;
 *delete_record = *IDZebrac::delete_record;
 *search_PQF = *IDZebrac::search_PQF;
index 258ffc5..a98a232 100644 (file)
@@ -1,4 +1,4 @@
-# $Id: Session.pm,v 1.14 2003-03-12 17:08:53 pop Exp $
+# $Id: Session.pm,v 1.15 2003-03-13 04:25:18 pop Exp $
 # 
 # Zebra perl API header
 # =============================================================================
@@ -15,7 +15,7 @@ BEGIN {
     use IDZebra::ScanList;
     use IDZebra::RetrievalRecord;
     require Exporter;
-    our $VERSION = do { my @r = (q$Revision: 1.14 $ =~ /\d+/g); sprintf "%d."."%02d" x $#r, @r }; 
+    our $VERSION = do { my @r = (q$Revision: 1.15 $ =~ /\d+/g); sprintf "%d."."%02d" x $#r, @r }; 
     our @ISA = qw(IDZebra::Logger Exporter);
     our @EXPORT = qw (TRANS_RW TRANS_RO);
 }
@@ -451,6 +451,12 @@ sub _update_args {
 # -----------------------------------------------------------------------------
 # Per record update
 # -----------------------------------------------------------------------------
+sub insert_record {
+    my ($self, %args) = @_;
+    $self->checkzh;
+    return(IDZebra::insert_record($self->{zh},
+                                 $self->_record_update_args(%args)));
+}
 
 sub update_record {
     my ($self, %args) = @_;
@@ -540,7 +546,7 @@ sub cql2pqf {
     my $res = "\0" x 2048;
     my $r = IDZebra::cql2pqf($self->{cql_ct}, $cqlquery, $res, 2048);
     if ($r) {
-       carp ("Error transforming CQL query: '$cqlquery', status:$r");
+#      carp ("Error transforming CQL query: '$cqlquery', status:$r");
     }
     $res=~s/\0.+$//g;
     return ($res,$r); 
@@ -950,15 +956,36 @@ where sysno in itself is sufficient to identify the record
 
 This case the record is extracted, and if already exists, located in the database, then deleted... 
 
-  $sysno = $sess->delete_record(data       => $rec1,
+  $sysno = $sess->update_record(data       => $rec1,
                                 match      => $myid,
                                 recordType => 'grs.perl.pod',
                                groupName  => "demo1");
 
-Don't try this at home! This case, the record identifier string (which is normally generated according to the rules set in recordId directive of zebra.cfg) is provided directly....
+Don't try this at home! This case, the record identifier string (which is normally generated according to the rules set in I<recordId> member of the record group, or in the I<recordId> parameter) is provided directly.... Looks much better this way:
+
+  $sysno = $sess->update_record(data          => $rec1,
+                                databaseName  => 'books',
+                                recordId      => '(bib1,ISBN)',
+                                recordType    => 'grs.perl.pod',
+                                flagStoreData => 1,
+                                flagStoreKeys => 1);
+
+You can notice, that it's not necessary to define a record group in zebra.cfg: you can do it "on the fly" in your code.
 
+B<Important:> Note, that one record can be updated only once within a transaction - all subsequent updates are skipped. If you'd like to override this feature, use the I<force=E<gt>1> flag:
+
+  $sysno = $sess->update_record(data       => $rec1,
+                               recordType => 'grs.perl.pod',
+                               groupName  => "demo1",
+                                force      => 1);
+
+If you don't like to update the record, if it alerady exists, use the I<insert_record> method:
+
+  $sysno = $sess->insert_record(data       => $rec1,
+                               recordType => 'grs.perl.pod',
+                               groupName  => "demo1");
 
-B<Important:> Note, that one record can be updated only once within a transaction - all subsequent updates are skipped. 
+In this case, sysno will be -1, if the record could not be added, because there was already one in the database, with the same record identifier (generated according to the I<recordId> setting).
 
 =head1 DATABASE SELECTION
 
index ae5f865..ab15e07 100644 (file)
@@ -1,6 +1,6 @@
 #!perl
 # =============================================================================
-# $Id: 03_record_update.t,v 1.2 2003-03-05 13:55:22 pop Exp $
+# $Id: 03_record_update.t,v 1.3 2003-03-13 04:25:18 pop Exp $
 #
 # Perl API header
 # =============================================================================
@@ -14,7 +14,7 @@ BEGIN {
 use strict;
 use warnings;
 
-use Test::More tests => 7;
+use Test::More tests => 11;
 
 # ----------------------------------------------------------------------------
 # Session opening and closing
@@ -57,13 +57,23 @@ $stat = $sess->end_trans;
 ok(($stat->{deleted} == 1), "Deleted 1 records");
 
 $sess->begin_trans;
-$sysno = $sess->update_record(data       => $rec2,
-                              recordType => 'grs.perl.pod',
-                              groupName  => "demo1",
-                              );
+$sysno = $sess->insert_record(data       => $rec2,
+                             recordType => 'grs.perl.pod',
+                             groupName  => "demo1",
+                             );
 $stat = $sess->end_trans;
 ok(($stat->{inserted} == 1), "Inserted 1 records");
+ok(($sysno > 0),"Inserted record got valid sysno");
 
+$sess->begin_trans;
+$sysno = $sess->insert_record(data       => $rec2,
+                             recordType => 'grs.perl.pod',
+                             groupName  => "demo1",
+                             );
+$stat = $sess->end_trans;
+ok(($stat->{inserted} == 0), "Inserted 0 records");
+ok(($stat->{updated} == 0), "Updated 0 records");
+ok(($sysno < 0),"Inserted record got invalid sysno");