1 /* $Id: zeerex.c,v 1.3 2007-02-08 19:26:33 adam Exp $ */
5 #include <yaz/yaz-util.h>
7 #include <libxml/parser.h>
8 #include <libxml/tree.h>
12 // Replace this with something that will take a callback
13 static void fail(const char *s, xmlNode *n)
15 yaz_log(YLOG_WARN, "Zeerex Err '%s' in elem '%s/%s'", s, n->parent->name, n->name);
18 // returns an nmem-allocated string if attr is present, or null
19 static char *attrtostr(NMEM m, xmlNode *n, const char *name)
21 char *s = xmlGetProp(n, name);
24 char *r = nmem_strdup(m, s);
32 static int attrtoint(xmlNode *n, const char *name)
34 char *s = xmlGetProp(n, name);
45 static Zr_bool attrtobool(xmlNode *node, const char *name)
47 char *v = xmlGetProp(node, name);
51 if (!strcmp(v, "true"))
53 else if (!strcmp(v, "false"))
56 res = Zr_bool_unknown;
61 return Zr_bool_unknown;
64 static char *valuetostr(NMEM m, xmlNode *n)
66 char *val = xmlNodeGetContent(n);
69 char *res = nmem_strdup(m, val);
77 static int valuetoint(xmlNode *n)
79 char *s = xmlNodeGetContent(n);
90 static Zr_langstr *findlangstr(NMEM m, xmlNode *node, const char *name)
94 for (n = node->children; n; n = n->next)
96 if (n->type == XML_ELEMENT_NODE && !strcmp(n->name, name))
98 Zr_langstr *new = nmem_malloc(m, sizeof(*new));
99 memset(new, 0, sizeof(*new));
100 new->primary = attrtobool(n, "primary");
101 new->lang = attrtostr(m, n, "lang");
102 new->str = valuetostr(m, n);
110 static struct zr_authentication *authentication(NMEM m, xmlNode *node)
113 struct zr_authentication *r = nmem_malloc(m, sizeof(*r));
114 memset(r, 0, sizeof(*r));
115 r->type = attrtostr(m, node, "type");
116 for (n = node->children; n; n = n->next)
118 if (n->type != XML_ELEMENT_NODE)
120 if (!strcmp(n->name, "open"))
121 r->open = valuetostr(m, n);
122 else if (!strcmp(n->name, "user"))
123 r->user = valuetostr(m, n);
124 else if (!strcmp(n->name, "group"))
125 r->group = valuetostr(m, n);
126 else if (!strcmp(n->name, "password"))
127 r->password = valuetostr(m, n);
130 fail("Unexpected element", n);
138 static struct zr_serverInfo *serverInfo(NMEM m, xmlNode *node)
141 struct zr_serverInfo *r = nmem_malloc(m, sizeof(*r));
142 memset(r, 0, sizeof(*r));
144 r->protocol = attrtostr(m, n, "protocol");
145 r->version = attrtostr(m, n, "version");
146 r->transport = attrtostr(m, n, "transport");
147 r->method = attrtostr(m, n, "method");
148 for (n = node->children; n; n = n->next)
150 if (n->type != XML_ELEMENT_NODE)
152 if (!strcmp(n->name, "host"))
153 r->host = valuetostr(m, n);
154 else if (!strcmp(n->name, "port"))
155 r->port = valuetoint(n);
156 else if (!strcmp(n->name, "database"))
157 r->database = valuetostr(m, n);
158 else if (!strcmp(n->name, "authentication") && !(r->authentication =
159 authentication(m, n)))
163 fail("Unexpected element", n);
170 static struct zr_agent *agent(NMEM m, xmlNode *node)
172 struct zr_agent *r = nmem_malloc(m, sizeof(*r));
173 memset(r, 0, sizeof(*r));
174 r->type = attrtostr(m, node, "type");
175 r->identifier = attrtostr(m, node, "identifier");
176 r->value = valuetostr(m, node);
180 static struct zr_implementation *implementation(NMEM m, xmlNode *node)
183 struct zr_implementation *r = nmem_malloc(m, sizeof(*r));
184 memset(r, 0, sizeof(*r));
185 r->identifier = attrtostr(m, node, "identifier");
186 r->version = attrtostr(m, node, "version");
187 r->title = findlangstr(m, node, "title");
188 for (n = node->children; n; n = n->next)
190 if (n->type != XML_ELEMENT_NODE)
192 if (!strcmp(n->name, "agent"))
194 struct zr_agent *ag = agent(m, node);
197 ag->next = r->agents;
204 struct zr_databaseInfo *databaseInfo(NMEM m, xmlNode *node)
207 struct zr_databaseInfo *r = nmem_malloc(m, sizeof(*r));
208 memset(r, 0, sizeof(*r));
210 r->title = findlangstr(m, node, "title");
211 r->description = findlangstr(m, node, "description");
212 r->history = findlangstr(m, node, "history");
213 r->extent = findlangstr(m, node, "extent");
214 r->restrictions = findlangstr(m, node, "restrictions");
215 r->langUsage = findlangstr(m, node, "langUsage");
217 for (n = node->children; n; n = n->next)
219 if (n->type != XML_ELEMENT_NODE)
221 if (!strcmp(n->name, "agents"))
224 for (n2 = n->children; n2; n2 = n2->next)
226 if (n2->type != XML_ELEMENT_NODE)
228 if (strcmp(n2->name, "agent"))
232 struct zr_agent *ag = agent(m, n2);
235 ag->next = r->agents;
240 else if (!strcmp(n->name, "implementation") &&
241 !(r->implementation = implementation(m, n)))
243 else if (!strcmp(n->name, "links"))
246 for (n2 = n->children; n2; n2 = n2->next)
248 if (!n2->type != XML_ELEMENT_NODE)
250 if (!strcmp(n2->name, "link"))
254 struct zr_link *li = nmem_malloc(m, sizeof(*li));
255 memset(li, 0, sizeof(*li));
256 li->type = attrtostr(m, n2, "type");
257 li->value = valuetostr(m, n2);
263 else if (!strcmp(n->name, "history") && !r->lastUpdate)
264 r->lastUpdate = attrtostr(m, n, "lastUpdate");
265 else if (!strcmp(n->name, "extent") && !r->numberOfRecords)
266 r->numberOfRecords = attrtoint(n, "numberOfRecords");
267 else if (!strcmp(n->name, "langUsage") && !r->codes)
268 r->codes = attrtostr(m, n, "codes");
273 struct zr_metaInfo *metaInfo(NMEM m, xmlNode *node)
276 struct zr_metaInfo *r = nmem_malloc(m, sizeof(*r));
277 memset(r, 0, sizeof(*r));
279 for (n = node->children; n; n = n->next)
281 if (!n->type == XML_ELEMENT_NODE)
283 if (!strcmp(n->name, "dateModified"))
284 r->dateModified = valuetostr(m, n);
285 else if (!strcmp(n->name, "dateAggregated"))
286 r->dateAggregated = valuetostr(m, n);
287 else if (!strcmp(n->name, "aggregatedFrom"))
288 r->aggregatedFrom = valuetostr(m, n);
291 fail("Unexpected element", n);
298 struct zr_set *set(NMEM m, xmlNode *node)
300 struct zr_set *r = nmem_malloc(m, sizeof(*r));
301 memset(r, 0, sizeof(*r));
302 r->name = attrtostr(m, node, "name");
303 r->identifier = attrtostr(m, node, "identifier");
304 r->title = findlangstr(m, node, "title");
308 struct zr_attr *attr(NMEM m, xmlNode *node)
310 struct zr_attr *r = nmem_malloc(m, sizeof(*r));
311 memset(r, 0, sizeof(*r));
312 r->type = attrtoint(node, "type");
313 r->set = attrtostr(m, node, "set");
317 static struct zr_map *map(NMEM m, xmlNode *node)
320 struct zr_map *r = nmem_malloc(m, sizeof(*r));
321 memset(r, 0, sizeof(*r));
323 r->lang = attrtostr(m, node, "lang");
324 r->primary = attrtobool(node, "primary");
325 for (n = node->children; n; n = n->next)
327 if (n->type != XML_ELEMENT_NODE)
329 if (!strcmp(n->name, "name"))
331 r->set = attrtostr(m, n, "set");
332 r->name = valuetostr(m, n);
334 else if (!strcmp(n->name, "attr"))
336 struct zr_attr *new = attr(m, n);
339 new->next = r->attrs;
344 fail("Unexpected element", n);
351 static Zr_setting *findsetting(NMEM m, xmlNode *node, char *name)
353 static Zr_setting *r = 0;
355 for (n = node->children; n; n = n->next)
357 if (node->type == XML_ELEMENT_NODE && !strcmp(n->name, name))
360 struct zr_setting *new = nmem_malloc(m, sizeof(*new));
361 memset(new, 0, sizeof(*new));
362 new->type = attrtostr(m, n, "type");
363 for (n2 = n->children; n2; n2 = n2->next)
365 if (n2->type == XML_ELEMENT_NODE && !strcmp(n2->name, "map"))
367 new->map = map(m, n2);
374 new->value = xmlNodeGetContent(n);
382 static struct zr_configInfo *configInfo(NMEM m, xmlNode *node)
384 struct zr_configInfo *r = nmem_malloc(m, sizeof(*r));
386 r->defaultv = findsetting(m, node, "default");
387 r->setting = findsetting(m, node, "setting");
388 r->supports = findsetting(m, node, "supports");
392 static struct zr_index *parse_index(NMEM m, xmlNode *node)
395 struct zr_index *r = nmem_malloc(m, sizeof(*r));
396 memset(r, 0, sizeof(*r));
398 r->search = attrtobool(node, "search");
399 r->scan = attrtobool(node, "scan");
400 r->sort = attrtobool(node, "sort");
401 r->id = attrtostr(m, node, "id");
402 r->title = findlangstr(m, node, "title");
404 for (n = node->children; n; n = n->next)
406 if (!strcmp(n->name, "map"))
408 struct zr_map *new = map(m, n);
414 else if (!strcmp(n->name, "configInfo") && !(r->configInfo = configInfo(m, n)))
416 else if (strcmp(n->name, "title"))
418 fail("Unknown child element", n);
425 static struct zr_sortKeyword *sortKeyword(NMEM m, xmlNode *node)
427 struct zr_sortKeyword *r = nmem_malloc(m, sizeof(*r));
428 memset(r, 0, sizeof(*r));
429 r->value = valuetostr(m, node);
433 static struct zr_indexInfo *indexInfo(NMEM m , xmlNode *node)
436 struct zr_indexInfo *r = nmem_malloc(m, sizeof(*r));
437 memset(r, 0, sizeof(*r));
439 for (n = node->children; n; n = n->next)
441 if (n->type != XML_ELEMENT_NODE)
443 if (!strcmp(n->name, "set"))
445 struct zr_set *new = set(m, n);
451 else if (!strcmp(n->name, "index"))
453 struct zr_index *new = parse_index(m, n);
456 new->next = r->indexes;
459 else if (!strcmp(n->name, "sortKeyword"))
461 struct zr_sortKeyword *new = sortKeyword(m, n);
464 new->next = r->sortKeywords;
465 r->sortKeywords = new;
467 else if (!strcmp(n->name, "sortKeyword") && !(r->configInfo = configInfo(m, n)))
471 fail("Unknown child element", n);
478 static struct zr_elementSet *elementSet(NMEM m, xmlNode *node)
480 struct zr_elementSet *r = nmem_malloc(m, sizeof(*r));
481 memset(r, 0, sizeof(*r));
482 r->name = attrtostr(m, node, "name");
483 r->identifier = attrtostr(m, node, "identifier");
484 r->title = findlangstr(m, node, "title");
488 static struct zr_recordSyntax *recordSyntax(NMEM m, xmlNode *node)
491 struct zr_recordSyntax *r = nmem_malloc(m, sizeof(*r));
492 struct zr_elementSet **elementp = &r->elementSets;
494 memset(r, 0, sizeof(*r));
495 r->name = attrtostr(m, node, "name");
496 r->identifier = attrtostr(m, node, "identifier");
497 for (n = node->children; n; n = n->next)
499 if (n->type != XML_ELEMENT_NODE)
501 if (!strcmp(n->name, "elementSet"))
503 if (!(*elementp = elementSet(m, n)))
505 elementp = &(*elementp)->next;
509 fail("Unknown child element", n);
516 static struct zr_recordInfo *recordInfo(NMEM m, xmlNode *node)
519 struct zr_recordInfo *r = nmem_malloc(m, sizeof(*r));
520 struct zr_recordSyntax **syntaxp = &r->recordSyntaxes;
522 memset(r, 0, sizeof(*r));
523 for (n = node->children; n; n = n->next)
525 if (n->type != XML_ELEMENT_NODE)
527 if (!strcmp(n->name, "recordSyntax"))
529 if (!(*syntaxp = recordSyntax(m, n)))
531 syntaxp = &(*syntaxp)->next;
535 fail("Unknown child element", n);
543 static struct zr_schema *schema(NMEM m, xmlNode *node)
545 struct zr_schema *r = nmem_malloc(m, sizeof(*r));
546 memset(r, 0, sizeof(*r));
548 r->name = attrtostr(m, node, "name");
549 r->identifier = attrtostr(m, node, "identifier");
550 r->retrieve = attrtobool(node, "retrieve");
551 r->sort = attrtobool(node, "sort");
552 r->location = attrtostr(m, node, "location");
553 r->title = findlangstr(m, node, "title");
557 static struct zr_schemaInfo *schemaInfo(NMEM m, xmlNode *node)
560 struct zr_schemaInfo *r = nmem_malloc(m, sizeof(*r));
561 struct zr_schema **schemap = &r->schemas;
563 memset(r, 0, sizeof(*r));
564 for (n = node->children; n; n = n->next)
566 if (n->type != XML_ELEMENT_NODE)
568 if (!strcmp(n->name, "schema"))
570 if (!(*schemap = schema(m, n)))
572 schemap = &(*schemap)->next;
576 fail("Unknown child element", n);
583 static struct zr_explain *explain(NMEM m, xmlNode *node)
586 struct zr_explain *r = nmem_malloc(m, sizeof(*r));
587 memset(r, 0, sizeof(*r));
589 for (n = node->children; n; n = n->next)
591 if (n->type != XML_ELEMENT_NODE)
593 if (!strcmp(n->name, "serverInfo") && !(r->serverInfo = serverInfo(m, n)))
595 else if (!strcmp(n->name, "databaseInfo") && !(r->databaseInfo = databaseInfo(m, n)))
597 else if (!strcmp(n->name, "metaInfo") && !(r->metaInfo = metaInfo(m, n)))
599 else if (!strcmp(n->name, "indexInfo") && !(r->indexInfo = indexInfo(m, n)))
601 else if (!strcmp(n->name, "recordInfo") && !(r->recordInfo = recordInfo(m, n)))
603 else if (!strcmp(n->name, "schemaInfo") && !(r->schemaInfo = schemaInfo(m, n)))
605 else if (!strcmp(n->name, "configInfo") && !(r->configInfo = configInfo(m, n)))
609 fail("Unknown child element", n);
616 struct zr_explain *zr_read_xml(NMEM m, xmlNode *n)
618 return explain(m, n);
621 struct zr_explain *zr_read_file(NMEM m, const char *fn)
623 xmlDoc *doc = xmlParseFile(fn);
624 struct zr_explain *r;
627 yaz_log(YLOG_WARN|YLOG_ERRNO, "Unable to open %s", fn);
630 r = explain(m, xmlDocGetRootElement(doc));
638 * indent-tabs-mode: nil
640 * vim: shiftwidth=4 tabstop=8 expandtab