How to create xml from R objects, e.g., is there a 'listToXml' function? How to create xml from R objects, e.g., is there a 'listToXml' function? xml xml

How to create xml from R objects, e.g., is there a 'listToXml' function?


The function newXMLNode does what you need, i.e., write XML output. See the detailed help and examples in ?newXMLNode for more details. Here is a short extract:

library(XML)    top = newXMLNode("a")newXMLNode("b", attrs=c(x=1, y='abc'), parent=top)newXMLNode("c", "With some text", parent=top)top

Resulting in:

<a>  <b x="1" y="abc"/>  <c>With some text</c></a> 


I am surprised that no function already exists for this -- surely there's something already packaged out there.

Regardless, I use the following script to accomplish this:

root <- newXMLNode("root")li <- list(a = list(aa = 1, ab=2), b=list(ba = 1, bb= 2, bc =3))listToXML <- function(node, sublist){    for(i in 1:length(sublist)){        child <- newXMLNode(names(sublist)[i], parent=node);        if (typeof(sublist[[i]]) == "list"){            listToXML(child, sublist[[i]])        }        else{            xmlValue(child) <- sublist[[i]]        }    } }listToXML(root, li)

You can use the XML::saveXML() function to grab this as a character, if you prefer.


Here is the listToXML function that we ended up creating

At first I adapted the answer by @Jeff

listToXml <- function(item, tag){  if(typeof(item)!='list')    return(xmlNode(tag, item))  xml <- xmlNode(tag)  for(name in names(item)){    xml <- append.xmlNode(xml, listToXml(item[[name]], name))  }  return(xml)}

But since the function has benefited from further development:

##' Convert List to XML##'##' Can convert list or other object to an xml object using xmlNode##' @title List to XML##' @param item ##' @param tag xml tag##' @return xmlNode##' @export##' @author David LeBauer, Carl Davidson, Rob KooperlistToXml <- function(item, tag) {  # just a textnode, or empty node with attributes  if(typeof(item) != 'list') {    if (length(item) > 1) {      xml <- xmlNode(tag)      for (name in names(item)) {        xmlAttrs(xml)[[name]] <- item[[name]]      }      return(xml)    } else {      return(xmlNode(tag, item))    }  }  # create the node  if (identical(names(item), c("text", ".attrs"))) {    # special case a node with text and attributes    xml <- xmlNode(tag, item[['text']])  } else {    # node with child nodes    xml <- xmlNode(tag)    for(i in 1:length(item)) {      if (names(item)[i] != ".attrs") {        xml <- append.xmlNode(xml, listToXml(item[[i]], names(item)[i]))      }    }      }  # add attributes to node  attrs <- item[['.attrs']]  for (name in names(attrs)) {    xmlAttrs(xml)[[name]] <- attrs[[name]]  }  return(xml)}