]> git.evergreen-ils.org Git - working/Evergreen.git/blob - Open-ILS/src/sql/Pg/upgrade/XXXX.function.biblio.extract_located_uris.sql
LP#1482757: More careful Located URI remapping
[working/Evergreen.git] / Open-ILS / src / sql / Pg / upgrade / XXXX.function.biblio.extract_located_uris.sql
1 BEGIN;
2
3 CREATE OR REPLACE FUNCTION biblio.extract_located_uris( bib_id BIGINT, marcxml TEXT, editor_id INT ) RETURNS VOID AS $func$
4 DECLARE
5     uris            TEXT[];
6     uri_xml         TEXT;
7     uri_label       TEXT;
8     uri_href        TEXT;
9     uri_use         TEXT;
10     uri_owner_list  TEXT[];
11     uri_owner       TEXT;
12     uri_owner_id    INT;
13     uri_id          INT;
14     uri_cn_id       INT;
15     uri_map_id      INT;
16     current_uri     INT;
17     uri_map_count   INT;
18     current_map_owner_list  INT[];
19     orphaned_uri_list       INT[];
20 BEGIN
21
22     uris := oils_xpath('//*[@tag="856" and (@ind1="4" or @ind1="1") and (@ind2="0" or @ind2="1")]',marcxml);
23     IF ARRAY_UPPER(uris,1) > 0 THEN
24         FOR i IN 1 .. ARRAY_UPPER(uris, 1) LOOP
25             -- First we pull info out of the 856
26             uri_xml     := uris[i];
27
28             uri_href    := (oils_xpath('//*[@code="u"]/text()',uri_xml))[1];
29             uri_label   := (oils_xpath('//*[@code="y"]/text()|//*[@code="3"]/text()',uri_xml))[1];
30             uri_use     := (oils_xpath('//*[@code="z"]/text()|//*[@code="2"]/text()|//*[@code="n"]/text()',uri_xml))[1];
31
32             IF uri_label IS NULL THEN
33                 uri_label := uri_href;
34             END IF;
35             CONTINUE WHEN uri_href IS NULL;
36
37             -- Get the distinct list of libraries wanting to use 
38             SELECT  ARRAY_AGG(
39                         DISTINCT REGEXP_REPLACE(
40                             x,
41                             $re$^.*?\((\w+)\).*$$re$,
42                             E'\\1'
43                         )
44                     ) INTO uri_owner_list
45               FROM  UNNEST(
46                         oils_xpath(
47                             '//*[@code="9"]/text()|//*[@code="w"]/text()|//*[@code="n"]/text()',
48                             uri_xml
49                         )
50                     )x;
51
52             IF ARRAY_UPPER(uri_owner_list,1) > 0 THEN
53
54                 -- look for a matching uri
55                 IF uri_use IS NULL THEN
56                     SELECT id INTO uri_id
57                         FROM asset.uri
58                         WHERE label = uri_label AND href = uri_href AND use_restriction IS NULL AND active
59                         ORDER BY id LIMIT 1;
60                     IF NOT FOUND THEN -- create one
61                         INSERT INTO asset.uri (label, href, use_restriction) VALUES (uri_label, uri_href, uri_use);
62                         SELECT id INTO uri_id
63                             FROM asset.uri
64                             WHERE label = uri_label AND href = uri_href AND use_restriction IS NULL AND active;
65                     END IF;
66                 ELSE
67                     SELECT id INTO uri_id
68                         FROM asset.uri
69                         WHERE label = uri_label AND href = uri_href AND use_restriction = uri_use AND active
70                         ORDER BY id LIMIT 1;
71                     IF NOT FOUND THEN -- create one
72                         INSERT INTO asset.uri (label, href, use_restriction) VALUES (uri_label, uri_href, uri_use);
73                         SELECT id INTO uri_id
74                             FROM asset.uri
75                             WHERE label = uri_label AND href = uri_href AND use_restriction = uri_use AND active;
76                     END IF;
77                 END IF;
78
79                 FOR j IN 1 .. ARRAY_UPPER(uri_owner_list, 1) LOOP
80                     uri_owner := uri_owner_list[j];
81
82                     SELECT id INTO uri_owner_id FROM actor.org_unit WHERE shortname = uri_owner;
83                     CONTINUE WHEN NOT FOUND;
84
85                     -- we need a call number to link through
86                     SELECT id INTO uri_cn_id FROM asset.call_number WHERE owning_lib = uri_owner_id AND record = bib_id AND label = '##URI##' AND NOT deleted;
87                     IF NOT FOUND THEN
88                         INSERT INTO asset.call_number (owning_lib, record, create_date, edit_date, creator, editor, label)
89                             VALUES (uri_owner_id, bib_id, 'now', 'now', editor_id, editor_id, '##URI##');
90                         SELECT id INTO uri_cn_id FROM asset.call_number WHERE owning_lib = uri_owner_id AND record = bib_id AND label = '##URI##' AND NOT deleted;
91                     END IF;
92
93                     -- now, link them if they're not already
94                     SELECT id INTO uri_map_id FROM asset.uri_call_number_map WHERE call_number = uri_cn_id AND uri = uri_id;
95                     IF NOT FOUND THEN
96                         INSERT INTO asset.uri_call_number_map (call_number, uri) VALUES (uri_cn_id, uri_id);
97                     END IF;
98
99                     current_map_owner_list := current_map_owner_list || uri_cn_id
100
101                 END LOOP;
102
103             END IF;
104
105         END LOOP;
106     END IF;
107
108     -- Clear any orphaned URIs, URI mappings and call
109     -- numbers for this bib that weren't mapped above.
110     FOR uri_cn_id IN
111         SELECT  id
112           FROM  asset.call_number
113           WHERE record = bib_id
114                 AND label = '##URI##'
115                 AND NOT deleted
116                 AND NOT (id = ANY (current_map_owner_list))
117     LOOP
118         -- Check for URIs to-be-orphaned URIs
119         FOR current_uri IN
120             SELECT  uri
121               FROM  asset.uri_call_number_map
122               WHERE call_number = uri_cn_id
123         LOOP
124             SELECT COUNT(*) INTO uri_map_count FROM asset.uri_call_number_map WHERE uri = current_uri;
125             IF uri_map_count = 1 THEN -- only one means it's the last
126                 orphaned_uri_list := orphaned_uri_list || current_uri;
127             END IF;
128         END LOOP;
129         -- Remove links
130         DELETE FROM asset.uri_call_number_map WHERE call_number = uri_cn_id;
131         DELETE FROM asset.call_number WHERE id = uri_cn_id;
132         DELETE FROM asset.uri WHERE id = ANY (orphaned_uri_list);
133     END LOOP;
134
135     RETURN;
136 END;
137 $func$ LANGUAGE PLPGSQL;
138
139 COMMIT;
140