Home | History | Annotate | Download | only in xml
      1 #include "xmpmeta/xml/utils.h"
      2 
      3 #include "android-base/logging.h"
      4 #include "base/port.h"
      5 #include "xmpmeta/xml/const.h"
      6 #include "xmpmeta/xml/search.h"
      7 
      8 namespace dynamic_depth {
      9 namespace xmpmeta {
     10 namespace xml {
     11 
     12 xmlNodePtr GetFirstDescriptionElement(const xmlDocPtr parent) {
     13   return DepthFirstSearch(parent, XmlConst::RdfDescription());
     14 }
     15 
     16 xmlNodePtr GetFirstSeqElement(xmlDocPtr parent) {
     17   // DepthFirstSearch will perform the null check.
     18   return DepthFirstSearch(parent, XmlConst::RdfSeq());
     19 }
     20 
     21 // Returns the first rdf:Seq element found in the given node.
     22 xmlNodePtr GetFirstSeqElement(xmlNodePtr parent) {
     23   // DepthFirstSearch will perform the null check.
     24   return DepthFirstSearch(parent, XmlConst::RdfSeq());
     25 }
     26 
     27 // Returns the ith (zero-indexed) element in the given node.
     28 // {@code parent} is an rdf:Seq node.
     29 xmlNodePtr GetElementAt(xmlNodePtr node, int index) {
     30   if (node == nullptr || index < 0) {
     31     LOG(ERROR) << "Node was null or index was negative";
     32     return nullptr;
     33   }
     34   const string node_name = FromXmlChar(node->name);
     35   if (strcmp(node_name.c_str(), XmlConst::RdfSeq())) {
     36     LOG(ERROR) << "Node is not an rdf:Seq node, was " << node_name;
     37     return nullptr;
     38   }
     39   int i = 0;
     40   for (xmlNodePtr child = node->children; child != nullptr && i <= index;
     41        child = child->next) {
     42     if (strcmp(FromXmlChar(child->name), XmlConst::RdfLi())) {
     43       // This is not an rdf:li node. This can occur because the node's content
     44       // is also treated as a node, and these should be ignored.
     45       continue;
     46     }
     47     if (i == index) {
     48       return child;
     49     }
     50     i++;
     51   }
     52   return nullptr;
     53 }
     54 
     55 const string GetLiNodeContent(xmlNodePtr node) {
     56   string value;
     57   if (node == nullptr || strcmp(FromXmlChar(node->name), XmlConst::RdfLi())) {
     58     LOG(ERROR) << "Node is null or is not an rdf:li node";
     59     return value;
     60   }
     61   xmlChar* node_content = xmlNodeGetContent(node);
     62   value = FromXmlChar(node_content);
     63   free(node_content);
     64   return value;
     65 }
     66 
     67 const string XmlDocToString(const xmlDocPtr doc) {
     68   xmlChar* xml_doc_contents;
     69   int doc_size = 0;
     70   xmlDocDumpFormatMemoryEnc(doc, &xml_doc_contents, &doc_size,
     71                             XmlConst::EncodingStr(), 1);
     72   const string xml_doc_string(FromXmlChar(xml_doc_contents));
     73   xmlFree(xml_doc_contents);
     74   return xml_doc_string;
     75 }
     76 
     77 }  // namespace xml
     78 }  // namespace xmpmeta
     79 }  // namespace dynamic_depth
     80