Fixing the problem that all items were getting biblioitem=1 set
[koha.git] / misc / migration_tools / bulkmarcimport.pl
1 #!/usr/bin/perl
2 # small script that import an iso2709 file into koha 2.0
3
4 use strict;
5
6 # Koha modules used
7 use MARC::File::USMARC;
8 use MARC::Record;
9 use MARC::Batch;
10 use C4::Context;
11 use C4::Biblio;
12 use Time::HiRes qw(gettimeofday);
13
14 use Getopt::Long;
15
16 my ( $input_marc_file, $number) = ('',0);
17 my ($version, $delete, $test_parameter,$char_encoding, $verbose, $commit);
18
19 GetOptions(
20         'commit:f'      => \$commit,
21     'file:s'    => \$input_marc_file,
22     'n:f' => \$number,
23     'h' => \$version,
24     'd' => \$delete,
25     't' => \$test_parameter,
26     'c:s' => \$char_encoding,
27     'v:s' => \$verbose,
28 );
29
30 if ($version || ($input_marc_file eq '')) {
31         print <<EOF
32 small script to import an iso2709 file into Koha.
33 parameters :
34 \th : this version/help screen
35 \tfile /path/to/file/to/dump : the file to dump
36 \tv : verbose mode. 1 means "some infos", 2 means "MARC dumping"
37 \tn : the number of records to import. If missing, all the file is imported
38 \tcommit : the number of records to wait before performing a 'commit' operation
39 \tt : test mode : parses the file, saying what he would do, but doing nothing.
40 \tc : the char encoding. At the moment, only MARC21 and UNIMARC supported. MARC21 by default.
41 \td : delete EVERYTHING related to biblio in koha-DB before import  :tables :
42 \t\tbiblio, \t\tbiblioitems, \t\tsubjects,\titems
43 \t\tadditionalauthors, \tbibliosubtitles, \tmarc_biblio,
44 \t\tmarc_subfield_table, \tmarc_word, \t\tmarc_blob_subfield
45 IMPORTANT : don't use this script before you've entered and checked your MARC parameters tables twice (or more!).
46 Otherwise, the import won't work correctly and you will get invalid data.
47
48 SAMPLE : 
49 \t\$ export KOHA_CONF=/etc/koha.conf
50 \t\$ perl misc/migration_tools/bulkmarcimport.pl -d -commit 1000 -file /home/jmf/koha.mrc -n 3000
51 EOF
52 ;#'
53 die;
54 }
55
56 my $dbh = C4::Context->dbh;
57
58 if ($delete) {
59         print "deleting biblios\n";
60         $dbh->do("delete from biblio");
61         $dbh->do("delete from biblioitems");
62         $dbh->do("delete from items");
63         $dbh->do("delete from bibliosubject");
64         $dbh->do("delete from additionalauthors");
65         $dbh->do("delete from bibliosubtitle");
66         $dbh->do("delete from marc_biblio");
67         $dbh->do("delete from marc_subfield_table");
68         $dbh->do("delete from marc_word");
69         $dbh->do("delete from marc_blob_subfield");
70 }
71 if ($test_parameter) {
72         print "TESTING MODE ONLY\n    DOING NOTHING\n===============\n";
73 }
74
75 $char_encoding = 'MARC21' unless ($char_encoding);
76 print "CHAR : $char_encoding\n" if $verbose;
77 my $starttime = gettimeofday;
78 my $batch = MARC::Batch->new( 'USMARC', $input_marc_file );
79 $batch->warnings_off();
80 $batch->strict_off();
81 my $i=0;
82 my $commitnum = 50;
83
84 if ($commit) {
85
86 $commitnum = $commit;
87
88 }
89
90 #1st of all, find item MARC tag.
91 my ($tagfield,$tagsubfield) = &MARCfind_marc_from_kohafield($dbh,"items.itemnumber",'');
92 # $dbh->do("lock tables biblio write, biblioitems write, items write, marc_biblio write, marc_subfield_table write, marc_blob_subfield write, marc_word write, marc_subfield_structure write, stopwords write");
93 while ( my $record = $batch->next() ) {
94 warn "I:".$i;
95 warn "NUM:".$number;
96         $i++;
97
98         if ($i==$number) {
99                 z3950_extended_services('commit',set_service_options('commit'));
100                 print "COMMIT OPERATION SUCCESSFUL\n";
101
102                 my $timeneeded = gettimeofday - $starttime;
103                 die "$i MARC records imported in $timeneeded seconds\n";
104         }
105         # perform the commit operation ever so often
106         if ($i==$commit) {
107                 z3950_extended_services('commit',set_service_options('commit'));
108                 $commit+=$commitnum;
109                 print "COMMIT OPERATION SUCCESSFUL\n";
110         }
111         #now, parse the record, extract the item fields, and store them in somewhere else.
112
113     ## create an empty record object to populate
114     my $newRecord = MARC::Record->new();
115         $newRecord->leader($record->leader());
116
117     # go through each field in the existing record
118     foreach my $oldField ( $record->fields() ) {
119
120         # just reproduce tags < 010 in our new record
121         if ( $oldField->tag() < 10 ) {
122             $newRecord->append_fields( $oldField );
123             next();
124         }
125
126         # store our new subfield data in this list
127         my @newSubfields = ();
128
129         # go through each subfield code/data pair
130         foreach my $pair ( $oldField->subfields() ) { 
131                 #$pair->[1] =~ s/\<//g;
132                 #$pair->[1] =~ s/\>//g;
133                 push( @newSubfields, $pair->[0], $pair->[1] ); #char_decode($pair->[1],$char_encoding) );
134         }
135
136         # add the new field to our new record
137         my $newField = MARC::Field->new(
138             $oldField->tag(),
139             $oldField->indicator(1),
140             $oldField->indicator(2),
141             @newSubfields
142         );
143
144         $newRecord->append_fields( $newField );
145
146     }
147
148         warn "$i ==>".$newRecord->as_formatted() if $verbose eq 2;
149         my @fields = $newRecord->field($tagfield);
150         my @items;
151         my $nbitems=0;
152
153         foreach my $field (@fields) {
154                 my $item = MARC::Record->new();
155                 $item->append_fields($field);
156                 push @items,$item;
157                 $newRecord->delete_field($field);
158                 $nbitems++;
159         }
160         print "$i : $nbitems items found\n" if $verbose;
161         # now, create biblio and items with NEWnewXX call.
162         unless ($test_parameter) {
163                 my ($bibid,$oldbibitemnum) = NEWnewbiblio($dbh,$newRecord,'');
164                 warn "ADDED biblio NB $bibid in DB\n" if $verbose;
165                 for (my $i=0;$i<=$#items;$i++) {
166                     warn "here is the biblioitemnumber $oldbibitemnum";
167                         NEWnewitem($dbh,$items[$i],$bibid,$oldbibitemnum);
168                 }
169         }
170 }
171 # final commit of the changes
172 z3950_extended_services('commit',set_service_options('commit'));
173 print "COMMIT OPERATION SUCCESSFUL\n";
174
175 my $timeneeded = gettimeofday - $starttime;
176 print "$i MARC records done in $timeneeded seconds\n";