1 /* This file is part of the YAZ toolkit.
2 * Copyright (C) 1995-2013 Index Data
3 * See the file LICENSE for details.
7 * \brief XML node inspection utilities
16 #include <yaz/wrbuf.h>
18 #include <libxml/parser.h>
19 #include <libxml/tree.h>
22 int yaz_match_xsd_element(xmlNodePtr ptr, const char *elem)
24 if (ptr->type == XML_ELEMENT_NODE && !xmlStrcmp(ptr->name, BAD_CAST elem))
33 int yaz_match_xsd_string_n(xmlNodePtr ptr, const char *elem, ODR o,
37 struct _xmlAttr *attr;
39 if (!yaz_match_xsd_element(ptr, elem))
42 for (attr = ptr->properties; attr; attr = attr->next)
43 if (!strcmp(attr->name, "type") &&
44 attr->children && attr->children->type == XML_TEXT_NODE)
46 const char *t = strchr(attr->children->content, ':');
50 t = attr->children->content;
51 if (!strcmp(t, "string"))
58 if (!ptr || ptr->type != XML_TEXT_NODE)
63 *val = odr_strdup(o, (const char *) ptr->content);
65 *len = xmlStrlen(ptr->content);
70 int yaz_match_xsd_string(xmlNodePtr ptr, const char *elem, ODR o, char **val)
72 return yaz_match_xsd_string_n(ptr, elem, o, val, 0);
75 int yaz_match_xsd_XML_n2(xmlNodePtr ptr, const char *elem, ODR o,
76 char **val, int *len, int fixup_root)
79 int no_root_nodes = 0;
81 if (!yaz_match_xsd_element(ptr, elem))
84 buf = xmlBufferCreate();
86 /* Copy each element nodes at top.
87 In most cases there is only one root node.. At least one server
88 http://www.theeuropeanlibrary.org/sru/sru.pl
89 has multiple root nodes in recordData.
91 for (ptr = ptr->children; ptr; ptr = ptr->next)
93 if (ptr->type == XML_ELEMENT_NODE)
95 /* copy node to get NS right (bug #740). */
96 xmlNode *tmp = xmlCopyNode(ptr, 1);
98 xmlNodeDump(buf, tmp->doc, tmp, 0, 0);
104 if (no_root_nodes != 1 && fixup_root)
106 /* does not appear to be an XML document. Make it so */
107 xmlBufferAddHead(buf, (const xmlChar *) "<yaz_record>", -1);
108 xmlBufferAdd(buf, (const xmlChar *) "</yaz_record>", -1);
110 *val = (char *) odr_malloc(o, buf->use + 1);
111 memcpy(*val, buf->content, buf->use);
112 (*val)[buf->use] = '\0';
122 int yaz_match_xsd_XML_n(xmlNodePtr ptr, const char *elem, ODR o,
123 char **val, int *len)
125 return yaz_match_xsd_XML_n2(ptr, elem, o, val, len, 0);
128 int yaz_match_xsd_integer(xmlNodePtr ptr, const char *elem, ODR o,
132 struct _xmlAttr *attr;
134 if (!yaz_match_xsd_element(ptr, elem))
137 for (attr = ptr->properties; attr; attr = attr->next)
138 if (!strcmp(attr->name, "type") &&
139 attr->children && attr->children->type == XML_TEXT_NODE)
141 const char *t = strchr(attr->children->content, ':');
145 t = attr->children->content;
146 if (!strcmp(t, "integer"))
153 if (!ptr || ptr->type != XML_TEXT_NODE)
155 *val = odr_intdup(o, odr_atoi((const char *) ptr->content));
166 * c-file-style: "Stroustrup"
167 * indent-tabs-mode: nil
169 * vim: shiftwidth=4 tabstop=8 expandtab