when parsing state from city, anchor pattern on right
[migration-tools.git] / sql / base / base.sql
index 9ab48aa..751ce72 100644 (file)
@@ -117,7 +117,7 @@ CREATE OR REPLACE FUNCTION migration_tools.init (TEXT) RETURNS VOID AS $$
         END;
         PERFORM migration_tools.exec( $1, 'DROP TABLE IF EXISTS ' || migration_schema || '.config;' );
         PERFORM migration_tools.exec( $1, 'CREATE TABLE ' || migration_schema || '.config ( key TEXT UNIQUE, value TEXT);' );
-        PERFORM migration_tools.exec( $1, 'INSERT INTO ' || migration_schema || '.config (key,value) VALUES ( ''production_tables'', ''asset.call_number,asset.copy_location,asset.copy,asset.stat_cat,asset.stat_cat_entry,asset.stat_cat_entry_copy_map,asset.copy_note,actor.usr,actor.card,actor.usr_address,actor.stat_cat,actor.stat_cat_entry,actor.stat_cat_entry_usr_map,actor.usr_note,actor.usr_standing_penalty,action.circulation,action.hold_request,action.hold_notification,money.grocery,money.billing,money.cash_payment,money.forgive_payment'' );' );
+        PERFORM migration_tools.exec( $1, 'INSERT INTO ' || migration_schema || '.config (key,value) VALUES ( ''production_tables'', ''asset.call_number,asset.copy_location,asset.copy,asset.stat_cat,asset.stat_cat_entry,asset.stat_cat_entry_copy_map,asset.copy_note,actor.usr,actor.card,actor.usr_address,actor.stat_cat,actor.stat_cat_entry,actor.stat_cat_entry_usr_map,actor.usr_note,actor.usr_standing_penalty,action.circulation,action.hold_request,action.hold_notification,money.grocery,money.billing,money.cash_payment,money.forgive_payment,acq.provider,acq.provider_address,acq.provider_note,acq.fund,acq.fund_allocation,acq.fund_tag,acq.funding_source,acq.funding_source_credit,acq.lineitem,acq.purchase_order,acq.po_item,acq.invoice,acq.invoice_item,acq.invoice_entry,acq.lineitem_detail,acq.fund_debit,acq.fund_transfer,acq.po_note'' );' );
         PERFORM migration_tools.exec( $1, 'INSERT INTO ' || migration_schema || '.config (key,value) VALUES ( ''country_code'', ''USA'' );' );
         PERFORM migration_tools.exec( $1, 'DROP TABLE IF EXISTS ' || migration_schema || '.fields_requiring_mapping;' );
         PERFORM migration_tools.exec( $1, 'CREATE TABLE ' || migration_schema || '.fields_requiring_mapping( table_schema TEXT, table_name TEXT, column_name TEXT, data_type TEXT);' );
@@ -365,9 +365,9 @@ CREATE OR REPLACE FUNCTION migration_tools.address_parse_out_citystatezip (TEXT)
             state := REGEXP_REPLACE( city_state_zip, E'^(.*),(.*)$', E'\\2');
             city := REGEXP_REPLACE( city_state_zip, E'^(.*),(.*)$', E'\\1');
         ELSE
-            IF city_state_zip ~ E'\\s+[A-Z][A-Z]\\s*' THEN
-                state := REGEXP_REPLACE( city_state_zip, E'^.*,?\\s+([A-Z][A-Z])\\s*.*$', E'\\1' );
-                city := REGEXP_REPLACE( city_state_zip, E'^(.*?),?\\s+[A-Z][A-Z](\\s*.*)$', E'\\1\\2' );
+            IF city_state_zip ~ E'\\s+[A-Z][A-Z]\\s*$' THEN
+                state := REGEXP_REPLACE( city_state_zip, E'^.*,?\\s+([A-Z][A-Z])\\s*$', E'\\1' );
+                city := REGEXP_REPLACE( city_state_zip, E'^(.*?),?\\s+[A-Z][A-Z](\\s*)$', E'\\1\\2' );
             ELSE
                 IF city_state_zip ~ E'^\\S+$'  THEN
                     city := city_state_zip;
@@ -624,25 +624,18 @@ CREATE OR REPLACE FUNCTION migration_tools.expand_barcode (TEXT, TEXT, INTEGER,
     return "$prefix$new_barcode$suffix";
 $$ LANGUAGE PLPERLU STABLE;
 
-CREATE OR REPLACE FUNCTION migration_tools.attempt_cast (TEXT,TEXT,TEXT) RETURNS RECORD AS $$
+-- remove previous version of this function
+DROP FUNCTION IF EXISTS migration_tools.attempt_cast(TEXT, TEXT, TEXT);
+
+CREATE OR REPLACE FUNCTION migration_tools.attempt_cast (TEXT, TEXT) RETURNS TEXT AS $$
     DECLARE
         attempt_value ALIAS FOR $1;
         datatype ALIAS FOR $2;
-        fail_value ALIAS FOR $3;
-        output RECORD;
     BEGIN
-        FOR output IN
-            EXECUTE 'SELECT ' || quote_literal(attempt_value) || '::' || datatype || ' AS a;'
-        LOOP
-            RETURN output;
-        END LOOP;
+        EXECUTE 'SELECT ' || quote_literal(attempt_value) || '::' || datatype || ' AS a;';
+        RETURN attempt_value;
     EXCEPTION
-        WHEN OTHERS THEN
-            FOR output IN
-                EXECUTE 'SELECT ' || quote_literal(fail_value) || '::' || datatype || ' AS a;'
-            LOOP
-                RETURN output;
-            END LOOP;
+        WHEN OTHERS THEN RETURN NULL;
     END;
 $$ LANGUAGE PLPGSQL STRICT STABLE;
 
@@ -1368,7 +1361,7 @@ BEGIN
   -- Create destination volume if needed
   IF NOT FOUND THEN
     INSERT INTO asset.call_number (creator, editor, record, owning_lib, label, label_class) 
-      VALUES (1, 1, bib, owner, new_label, label_class);
+      VALUES (1, 1, bib, owner, new_label, cn_class);
     SELECT id INTO new_volume FROM asset.call_number
       WHERE 
         record = bib AND
@@ -1636,7 +1629,10 @@ MARC::Charset->assume_unicode(1);
 
 my $xml = shift;
 
-eval { my $r = MARC::Record->new_from_xml( $xml ); };
+eval {
+    my $r = MARC::Record->new_from_xml( $xml );
+    my $output_xml = $r->as_xml_record();
+};
 if ($@) {
     return 0;
 } else {
@@ -1833,3 +1829,62 @@ The first argument is an array of tag/subfield specifiers, e.g., ARRAY['001', '2
 The second argument is an array of text containing the values to plug into each field.  
 If the value for a given field is NULL or the empty string, it is not inserted.
 $$;
+
+CREATE OR REPLACE FUNCTION migration_tools.set_indicator (TEXT, TEXT, INTEGER, CHAR(1)) RETURNS TEXT AS $func$
+
+my ($marcxml, $tag, $pos, $value) = @_;
+
+use MARC::Record;
+use MARC::File::XML (BinaryEncoding => 'UTF-8');
+use MARC::Charset;
+use strict;
+
+MARC::Charset->assume_unicode(1);
+
+elog(ERROR, 'indicator position must be either 1 or 2') unless $pos =~ /^[12]$/;
+elog(ERROR, 'MARC tag must be numeric') unless $tag =~ /^\d{3}$/;
+elog(ERROR, 'MARC tag must not be control field') if $tag =~ /^00/;
+elog(ERROR, 'Value must be exactly one character') unless $value =~ /^.$/;
+
+my $xml = $marcxml;
+eval {
+    my $marc = MARC::Record->new_from_xml($marcxml, 'UTF-8');
+
+    foreach my $field ($marc->field($tag)) {
+        $field->update("ind$pos" => $value);
+    }
+    $xml = $marc->as_xml_record;
+    $xml =~ s/^<\?.+?\?>$//mo;
+    $xml =~ s/\n//sgo;
+    $xml =~ s/>\s+</></sgo;
+};
+return $xml;
+
+$func$ LANGUAGE PLPERLU;
+
+COMMENT ON FUNCTION migration_tools.set_indicator(TEXT, TEXT, INTEGER, CHAR(1)) IS $$Set indicator value of a specified MARC field.
+The first argument is a MARCXML string.
+The second argument is a MARC tag.
+The third argument is the indicator position, either 1 or 2.
+The fourth argument is the character to set the indicator value to.
+All occurences of the specified field will be changed.
+The function returns the revised MARCXML string.$$;
+
+CREATE OR REPLACE FUNCTION migration_tools.create_staff_user(
+    username TEXT,
+    password TEXT,
+    org TEXT,
+    perm_group TEXT,
+    first_name TEXT DEFAULT '',
+    last_name TEXT DEFAULT ''
+) RETURNS VOID AS $func$
+BEGIN
+    RAISE NOTICE '%', org ;
+    INSERT INTO actor.usr (usrname, passwd, ident_type, first_given_name, family_name, home_ou, profile)
+    SELECT username, password, 1, first_name, last_name, aou.id, pgt.id
+    FROM   actor.org_unit aou, permission.grp_tree pgt
+    WHERE  aou.shortname = org
+    AND    pgt.name = perm_group;
+END
+$func$
+LANGUAGE PLPGSQL;