1 #include "xmlutilities.h"
2 
3 #include <cstring>
4 
5 namespace rsspp {
6 
get_content(xmlNode * node)7 std::string get_content(xmlNode* node)
8 {
9 	std::string retval;
10 	if (node) {
11 		xmlChar* content = xmlNodeGetContent(node);
12 		if (content) {
13 			retval = (const char*)content;
14 			xmlFree(content);
15 		}
16 	}
17 	return retval;
18 }
19 
get_xml_content(xmlNode * node,xmlDocPtr doc)20 std::string get_xml_content(xmlNode* node, xmlDocPtr doc)
21 {
22 	xmlBufferPtr buf = xmlBufferCreate();
23 	std::string result;
24 
25 	cleanup_namespaces(node);
26 
27 	if (node->children) {
28 		for (xmlNodePtr ptr = node->children; ptr != nullptr;
29 			ptr = ptr->next) {
30 			if (xmlNodeDump(buf, doc, ptr, 0, 0) >= 0) {
31 				result.append(
32 					(const char*)xmlBufferContent(buf));
33 				xmlBufferEmpty(buf);
34 			} else {
35 				result.append(get_content(ptr));
36 			}
37 		}
38 	} else {
39 		result = get_content(node); // fallback
40 	}
41 	xmlBufferFree(buf);
42 
43 	return result;
44 }
45 
cleanup_namespaces(xmlNodePtr node)46 void cleanup_namespaces(xmlNodePtr node)
47 {
48 	node->ns = nullptr;
49 	for (auto ptr = node->children; ptr != nullptr; ptr = ptr->next) {
50 		cleanup_namespaces(ptr);
51 	}
52 }
53 
get_prop(xmlNode * node,const std::string & prop,const std::string & ns)54 std::string get_prop(xmlNode* node, const std::string& prop,
55 	const std::string& ns)
56 {
57 	std::string retval;
58 	if (node) {
59 		xmlChar* value = nullptr;
60 		if (ns.empty()) {
61 			value = xmlGetProp(node,
62 					reinterpret_cast<const xmlChar*>(prop.c_str()));
63 		} else {
64 			value = xmlGetNsProp(node,
65 					reinterpret_cast<const xmlChar*>(prop.c_str()),
66 					reinterpret_cast<const xmlChar*>(ns.c_str()));
67 		}
68 		if (value) {
69 			retval = reinterpret_cast<const char*>(value);
70 			xmlFree(value);
71 		}
72 	}
73 	return retval;
74 }
75 
has_namespace(xmlNode * node,const char * ns_uri)76 bool has_namespace(xmlNode* node, const char* ns_uri)
77 {
78 	if (!ns_uri && !node->ns) {
79 		return true;
80 	}
81 	if (ns_uri && node->ns && node->ns->href &&
82 		strcmp((const char*)node->ns->href, ns_uri) == 0) {
83 		return true;
84 	}
85 	return false;
86 }
87 
node_is(xmlNode * node,const char * name,const char * ns_uri)88 bool node_is(xmlNode* node, const char* name, const char* ns_uri)
89 {
90 	if (!node || !name || !node->name) {
91 		return false;
92 	}
93 
94 	if (strcmp((const char*)node->name, name) == 0) {
95 		return has_namespace(node, ns_uri);
96 	}
97 	return false;
98 }
99 
100 } // namespace rsspp
101