1 /* This file is part of the YAZ toolkit.
2 * Copyright (C) 1995-2013 Index Data
3 * See the file LICENSE for details.
9 #include <yaz/record_conv.h>
11 #include <yaz/wrbuf.h>
14 #include <yaz/proto.h>
15 #include <yaz/prt-ext.h>
16 #include <yaz/oid_db.h>
19 #include <libxml/parser.h>
20 #include <libxml/tree.h>
23 #include <libxslt/xslt.h>
26 yaz_record_conv_t conv_configure(const char *xmlstring, WRBUF w)
28 xmlDocPtr doc = xmlParseMemory(xmlstring, strlen(xmlstring));
31 wrbuf_printf(w, "xmlParseMemory");
36 xmlNodePtr ptr = xmlDocGetRootElement(doc);
37 yaz_record_conv_t p = yaz_record_conv_create();
41 const char *srcdir = getenv("srcdir");
43 yaz_record_conv_set_path(p, srcdir);
47 wrbuf_printf(w, "xmlDocGetRootElement");
48 yaz_record_conv_destroy(p);
53 wrbuf_printf(w, "yaz_record_conv_create");
59 int r = yaz_record_conv_configure(p, ptr);
63 wrbuf_puts(w, yaz_record_conv_get_error(p));
64 yaz_record_conv_destroy(p);
73 int conv_configure_test(const char *xmlstring, const char *expect_error,
74 yaz_record_conv_t *pt)
76 WRBUF w = wrbuf_alloc();
79 yaz_record_conv_t p = conv_configure(xmlstring, w);
83 if (expect_error && !strcmp(wrbuf_cstr(w), expect_error))
88 printf("%s\n", wrbuf_cstr(w));
103 yaz_record_conv_destroy(p);
109 static void tst_configure(void)
114 YAZ_CHECK(conv_configure_test("<bad", "xmlParseMemory", 0));
117 YAZ_CHECK(conv_configure_test("<backend syntax='usmarc' name='F'>"
119 "Element <backend>: expected <marc> or "
120 "<xslt> element, got <bad>", 0));
123 YAZ_CHECK(conv_configure_test("<backend syntax='usmarc' name='F'>"
124 "<xslt stylesheet=\"test_record_conv.xsl\"/>"
126 " inputcharset=\"marc-8\""
127 " outputcharset=\"marc-8\""
130 "Element <marc>: attribute 'inputformat' "
132 YAZ_CHECK(conv_configure_test("<backend syntax='usmarc' name='F'>"
135 "Element <xslt>: attribute 'stylesheet' "
137 YAZ_CHECK(conv_configure_test("<backend syntax='usmarc' name='F'>"
139 " inputcharset=\"utf-8\""
140 " outputcharset=\"marc-8\""
141 " inputformat=\"xml\""
142 " outputformat=\"marc\""
144 "<xslt stylesheet=\"test_record_conv.xsl\"/>"
148 YAZ_CHECK(conv_configure_test("<backend syntax='usmarc' name='F'>"
149 "<xslt stylesheet=\"test_record_conv.xsl\"/>"
152 " YAZ compiled without XSLT support", 0));
156 static int conv_convert_test(yaz_record_conv_t p,
157 const char *input_record,
158 const char *output_expect_record)
167 WRBUF output_record = wrbuf_alloc();
168 int r = yaz_record_conv_record(p, input_record, strlen(input_record),
172 if (output_expect_record)
174 printf("yaz_record_conv error=%s\n",
175 yaz_record_conv_get_error(p));
183 if (!output_expect_record)
187 else if (strcmp(output_expect_record, wrbuf_cstr(output_record)))
190 printf("got-output_record len=%ld: %s\n",
191 (long) wrbuf_len(output_record),
192 wrbuf_cstr(output_record));
193 printf("output_expect_record len=%ld %s\n",
194 (long) strlen(output_expect_record),
195 output_expect_record);
202 wrbuf_destroy(output_record);
207 static int conv_convert_test_iter(yaz_record_conv_t p,
208 const char *input_record,
209 const char *output_expect_record,
214 for (i = 0; i < num_iter; i++)
216 ret = conv_convert_test(p, input_record, output_expect_record);
223 static void tst_convert1(void)
225 yaz_record_conv_t p = 0;
226 const char *marcxml_rec =
227 "<record xmlns=\"http://www.loc.gov/MARC21/slim\">\n"
228 " <leader>00080nam a22000498a 4500</leader>\n"
229 " <controlfield tag=\"001\"> 11224466 </controlfield>\n"
230 " <datafield tag=\"010\" ind1=\" \" ind2=\" \">\n"
231 " <subfield code=\"a\"> 11224466 </subfield>\n"
234 const char *tmarcxml_rec =
235 "<r xmlns=\"http://www.indexdata.com/MARC21/turboxml\">\n"
236 " <l>00080nam a22000498a 4500</l>\n"
237 " <c001> 11224466 </c001>\n"
238 " <d010 i1=\" \" i2=\" \">\n"
239 " <sa> 11224466 </sa>\n"
242 const char *iso2709_rec =
243 "\x30\x30\x30\x38\x30\x6E\x61\x6D\x20\x61\x32\x32\x30\x30\x30\x34"
244 "\x39\x38\x61\x20\x34\x35\x30\x30\x30\x30\x31\x30\x30\x31\x33\x30"
245 "\x30\x30\x30\x30\x30\x31\x30\x30\x30\x31\x37\x30\x30\x30\x31\x33"
246 "\x1E\x20\x20\x20\x31\x31\x32\x32\x34\x34\x36\x36\x20\x1E\x20\x20"
247 "\x1F\x61\x20\x20\x20\x31\x31\x32\x32\x34\x34\x36\x36\x20\x1E\x1D";
249 YAZ_CHECK(conv_configure_test("<backend>"
251 " inputcharset=\"utf-8\""
252 " outputcharset=\"marc-8\""
253 " inputformat=\"xml\""
254 " outputformat=\"marc\""
258 YAZ_CHECK(conv_convert_test(p, marcxml_rec, iso2709_rec));
259 YAZ_CHECK(conv_convert_test(p, tmarcxml_rec, iso2709_rec));
260 yaz_record_conv_destroy(p);
262 YAZ_CHECK(conv_configure_test("<backend>"
264 " outputcharset=\"utf-8\""
265 " inputcharset=\"marc-8\""
266 " outputformat=\"marcxml\""
267 " inputformat=\"marc\""
271 YAZ_CHECK(conv_convert_test(p, iso2709_rec, marcxml_rec));
272 yaz_record_conv_destroy(p);
275 YAZ_CHECK(conv_configure_test("<backend>"
276 "<xslt stylesheet=\"test_record_conv.xsl\"/>"
277 "<xslt stylesheet=\"test_record_conv.xsl\"/>"
279 " inputcharset=\"utf-8\""
280 " outputcharset=\"marc-8\""
281 " inputformat=\"xml\""
282 " outputformat=\"marc\""
285 " outputcharset=\"utf-8\""
286 " inputcharset=\"marc-8\""
287 " outputformat=\"marcxml\""
288 " inputformat=\"marc\""
292 YAZ_CHECK(conv_convert_test(p, marcxml_rec, marcxml_rec));
293 yaz_record_conv_destroy(p);
296 YAZ_CHECK(conv_configure_test("<backend>"
297 "<xslt stylesheet=\"test_record_conv.xsl\"/>"
298 "<xslt stylesheet=\"test_record_conv.xsl\"/>"
300 " outputcharset=\"marc-8\""
301 " inputformat=\"xml\""
302 " outputformat=\"marc\""
305 " inputcharset=\"marc-8\""
306 " outputformat=\"marcxml\""
307 " inputformat=\"marc\""
311 YAZ_CHECK(conv_convert_test(p, marcxml_rec, marcxml_rec));
312 yaz_record_conv_destroy(p);
315 static void tst_convert2(void)
317 yaz_record_conv_t p = 0;
318 const char *marcxml_rec =
319 "<record xmlns=\"http://www.loc.gov/MARC21/slim\">\n"
320 " <leader>00080nam a22000498a 4500</leader>\n"
321 " <controlfield tag=\"001\"> 11224466 </controlfield>\n"
322 " <datafield tag=\"010\" ind1=\" \" ind2=\" \">\n"
323 " <subfield code=\"a\">københavn</subfield>\n"
326 const char *iso2709_rec =
327 "\x30\x30\x30\x37\x37\x6E\x61\x6D\x20\x61\x32\x32\x30\x30\x30\x34"
328 "\x39\x38\x61\x20\x34\x35\x30\x30\x30\x30\x31\x30\x30\x31\x33\x30"
329 "\x30\x30\x30\x30\x30\x31\x30\x30\x30\x31\x34\x30\x30\x30\x31\x33"
330 "\x1E\x20\x20\x20\x31\x31\x32\x32\x34\x34\x36\x36\x20\x1E\x20\x20"
331 "\x1F\x61\x6b\xb2\x62\x65\x6e\x68\x61\x76\x6e\x1E\x1D";
333 YAZ_CHECK(conv_configure_test("<backend>"
335 " inputcharset=\"utf-8\""
336 " outputcharset=\"marc-8\""
337 " inputformat=\"xml\""
338 " outputformat=\"marc\""
342 YAZ_CHECK(conv_convert_test_iter(p, marcxml_rec, iso2709_rec, 100));
343 yaz_record_conv_destroy(p);
346 static void tst_convert3(void)
348 NMEM nmem = nmem_create();
350 yaz_record_conv_t p = 0;
352 const char *iso2709_rec =
353 "\x30\x30\x30\x37\x37\x6E\x61\x6D\x20\x61\x32\x32\x30\x30\x30\x34"
354 "\x39\x38\x61\x20\x34\x35\x30\x30\x30\x30\x31\x30\x30\x31\x33\x30"
355 "\x30\x30\x30\x30\x30\x31\x30\x30\x30\x31\x34\x30\x30\x30\x31\x33"
356 "\x1E\x20\x20\x20\x31\x31\x32\x32\x34\x34\x36\x36\x20\x1E\x20\x20"
357 "\x1F\x61\x6b\xb2\x62\x65\x6e\x68\x61\x76\x6e\x1E\x1D";
359 const char *opacxml_rec =
361 " <bibliographicRecord>\n"
362 "<record xmlns=\"http://www.loc.gov/MARC21/slim\">\n"
363 " <leader>00077nam a22000498a 4500</leader>\n"
364 " <controlfield tag=\"001\"> 11224466 </controlfield>\n"
365 " <datafield tag=\"010\" ind1=\" \" ind2=\" \">\n"
366 " <subfield code=\"a\">k" "\xc3" "\xb8" /* oslash in UTF_8 */
367 "benhavn</subfield>\n"
370 " </bibliographicRecord>\n"
373 " <typeOfRecord>u</typeOfRecord>\n"
374 " <encodingLevel>U</encodingLevel>\n"
375 " <receiptAcqStatus>0</receiptAcqStatus>\n"
376 " <dateOfReport>000000</dateOfReport>\n"
377 " <nucCode>s-FM/GC</nucCode>\n"
378 " <localLocation>Main or Science/Business Reading Rms - STORED OFFSITE</localLocation>\n"
379 " <callNumber>MLCM 89/00602 (N)</callNumber>\n"
380 " <shelvingData>FT MEADE</shelvingData>\n"
381 " <copyNumber>Copy 1</copyNumber>\n"
384 " <availableNow value=\"1\"/>\n"
385 " <itemId>1226176</itemId>\n"
386 " <renewable value=\"0\"/>\n"
387 " <onHold value=\"0\"/>\n"
394 Z_OPACRecord *z_opac = nmem_malloc(nmem, sizeof(*z_opac));
395 Z_HoldingsAndCircData *h;
398 z_opac->bibliographicRecord =
399 z_ext_record_oid_nmem(nmem, yaz_oid_recsyn_usmarc,
400 iso2709_rec, strlen(iso2709_rec));
401 z_opac->num_holdingsData = 1;
402 z_opac->holdingsData = (Z_HoldingsRecord **)
403 nmem_malloc(nmem, sizeof(Z_HoldingsRecord *) * 1);
404 z_opac->holdingsData[0] = (Z_HoldingsRecord *)
405 nmem_malloc(nmem, sizeof(Z_HoldingsRecord));
406 z_opac->holdingsData[0]->which = Z_HoldingsRecord_holdingsAndCirc;
407 h = z_opac->holdingsData[0]->u.holdingsAndCirc = (Z_HoldingsAndCircData *)
408 nmem_malloc(nmem, sizeof(*h));
409 h->typeOfRecord = nmem_strdup(nmem, "u");
410 h->encodingLevel = nmem_strdup(nmem, "U");
412 h->receiptAcqStatus = nmem_strdup(nmem, "0");
413 h->generalRetention = 0;
415 h->dateOfReport = nmem_strdup(nmem, "000000");
416 h->nucCode = nmem_strdup(nmem, "s-FM/GC");
417 h->localLocation = nmem_strdup(nmem,
418 "Main or Science/Business Reading "
419 "Rms - STORED OFFSITE");
420 h->shelvingLocation = 0;
421 h->callNumber = nmem_strdup(nmem, "MLCM 89/00602 (N)");
422 h->shelvingData = nmem_strdup(nmem, "FT MEADE");
423 h->copyNumber = nmem_strdup(nmem, "Copy 1");
425 h->reproductionNote = 0;
426 h->termsUseRepro = 0;
430 h->num_circulationData = 1;
431 h->circulationData = (Z_CircRecord **)
432 nmem_malloc(nmem, 1 * sizeof(Z_CircRecord *));
433 circ = h->circulationData[0] = (Z_CircRecord *)
434 nmem_malloc(nmem, sizeof(Z_CircRecord));
435 circ->availableNow = nmem_booldup(nmem, 1);
436 circ->availablityDate = 0;
437 circ->availableThru = 0;
438 circ->restrictions = 0;
439 circ->itemId = nmem_strdup(nmem, "1226176");
440 circ->renewable = nmem_booldup(nmem, 0);
441 circ->onHold = nmem_booldup(nmem, 0);
442 circ->enumAndChron = 0;
444 circ->temporaryLocation = 0;
446 YAZ_CHECK(conv_configure_test("<backend>"
448 " inputcharset=\"marc-8\""
449 " outputcharset=\"utf-8\""
450 " inputformat=\"marc\""
451 " outputformat=\"marcxml\""
458 WRBUF output_record = wrbuf_alloc();
459 ret = yaz_record_conv_opac_record(p, z_opac, output_record);
463 ret = strcmp(wrbuf_cstr(output_record), opacxml_rec);
467 printf("got-output_record len=%ld: %s\n",
468 (long) wrbuf_len(output_record),
469 wrbuf_cstr(output_record));
470 printf("output_expect_record len=%ld %s\n",
471 (long) strlen(opacxml_rec),
475 yaz_record_conv_destroy(p);
476 wrbuf_destroy(output_record);
483 int main(int argc, char **argv)
485 YAZ_CHECK_INIT(argc, argv);
486 yaz_log_xml_errors(0, 0 /* disable log */);
494 xsltCleanupGlobals();
505 * c-file-style: "Stroustrup"
506 * indent-tabs-mode: nil
508 * vim: shiftwidth=4 tabstop=8 expandtab