1 #include <opensrf/xml_utils.h>
4 static jsonObject* _xmlToJSON(xmlNodePtr node, jsonObject*);
7 @brief Write then contents of an xmlNode to standard output.
8 @param node Pointer to an xmlNode
10 Write the text content of an xmlNode, and all its dependent nodes recursively, to
13 void recurse_doc( xmlNodePtr node ) {
14 if( node == NULL ) return;
15 printf("Recurse: %s => %s", node->name, node->content );
16 xmlNodePtr t = node->children;
23 jsonObject* xmlDocToJSON(xmlDocPtr doc) {
25 return _xmlToJSON(xmlDocGetRootElement(doc), NULL);
28 static jsonObject* _xmlToJSON(xmlNodePtr node, jsonObject* obj) {
30 if(!node) return NULL;
31 if(xmlIsBlankNode(node)) return NULL;
32 if(obj == NULL) obj = jsonNewObject(NULL);
34 if(node->type == XML_TEXT_NODE) {
35 jsonObjectSetString(obj, (char*) node->content);
37 } else if(node->type == XML_ELEMENT_NODE || node->type == XML_ATTRIBUTE_NODE ) {
39 jsonObject* new_obj = jsonNewObject(NULL);
43 /* do the duplicate node / array shuffle */
44 if( (old = jsonObjectGetKey(obj, (char*) node->name)) ) {
45 if(old->type == JSON_ARRAY ) {
46 jsonObjectPush(old, new_obj);
48 jsonObject* arr = jsonNewObject(NULL);
49 jsonObjectPush(arr, jsonObjectClone(old));
50 jsonObjectPush(arr, new_obj);
51 jsonObjectSetKey(obj, (char*) node->name, arr);
54 jsonObjectSetKey(obj, (char*) node->name, new_obj);
57 xmlNodePtr child = node->children;
58 if (child) { // at least one...
59 if (child != node->last) { // more than one -- ignore TEXT nodes
61 if (child->type != XML_TEXT_NODE) _xmlToJSON(child, new_obj);
65 _xmlToJSON(child, new_obj);
74 char* xmlDocToString(xmlDocPtr doc, int full) {
84 xmlDocDumpMemory(doc, &xmlbuf, &size);
85 xml = strdup((char*) (xmlbuf));
91 xmlBufferPtr xmlbuf = xmlBufferCreate();
92 xmlNodeDump( xmlbuf, doc, xmlDocGetRootElement(doc), 0, 0);
93 xml = strdup((char*) (xmlBufferContent(xmlbuf)));
94 xmlBufferFree(xmlbuf);
101 @brief Search for the value of a given attribute in an attribute array.
102 @param atts Pointer to the attribute array to be searched.
103 @param atts Pointer to the attribute name to be sought.
104 @return A pointer to the attribute value if found, or NULL if not.
106 The @a atts parameter points to a ragged array of strings. The @a atts[0] pointer points
107 to an attribute name, and @a atts[1] points to the corresponding attribute value. The
108 remaining pointers likewise point alternately to names and values. The end of the
109 list is marked by a NULL.
111 In practice, the @a atts array is constructed by the XML parser and passed to a callback
115 const char* xmlSaxAttr( const xmlChar** atts, const char* name ) {
118 for(i = 0; (atts[i] != NULL); i++) {
119 if(!strcmp((char*) atts[i], name)) {
121 return (const char*) atts[i];
129 @brief Add a series of attributes to an xmlNode.
130 @param node Pointer to the xmlNode to which the attributes will be added.
131 @param atts Pointer to the attributes to be added.
132 @return Zero in all cases.
134 The @a atts parameter points to a ragged array of strings. The @a atts[0] pointer points
135 to an attribute name, and @a atts[1] points to the corresponding attribute value. The
136 remaining pointers likewise point alternately to names and values. The end of the
137 list is marked by a NULL.
139 In practice, the @a atts array is constructed by the XML parser and passed to a callback
142 int xmlAddAttrs( xmlNodePtr node, const xmlChar** atts ) {
145 for(i = 0; (atts[i] != NULL); i++) {
147 xmlSetProp(node, atts[i], atts[i+1]);