r-lib / xml2

Bindings to libxml2
https://xml2.r-lib.org/
Other
218 stars 82 forks source link

Can't add nodeset via xml_add_sibling() #170

Closed krlmlr closed 6 years ago

krlmlr commented 7 years ago

Issue Description and Expected Result

xml_add_sibling() throws an error when passing a nodeset as .value argument. I'd expect all nodes to be copied/moved.

Reproducible Example

library(xml2)

xml <- read_xml("<parent><child1/><child2/><child3/></parent>")
children <- xml_children(xml)
children
#> {xml_nodeset (3)}
#> [1] <child1/>
#> [2] <child2/>
#> [3] <child3/>
# Can't add nodeset
xml_add_sibling(children[[1]], children)
#> Error: `.value` must be a character
xml
#> {xml_document}
#> <parent>
#> [1] <child1/>
#> [2] <child2/>
#> [3] <child3/>
# Can add individual nodes
xml_add_sibling(children[[1]], children[[2]])
xml
#> {xml_document}
#> <parent>
#> [1] <child1/>
#> [2] <child2/>
#> [3] <child2/>
#> [4] <child3/>
Session info ``` r devtools::session_info() #> Session info ------------------------------------------------------------- #> setting value #> version R version 3.3.2 (2016-10-31) #> system x86_64, linux-gnu #> ui X11 #> language en_US:en #> collate en_US.UTF-8 #> tz Europe/Busingen #> date 2017-03-01 #> Packages ----------------------------------------------------------------- #> package * version date source #> backports 1.0.5 2017-01-18 CRAN (R 3.3.2) #> devtools 1.12.0.9000 2017-01-25 local #> digest 0.6.12 2017-01-27 cran (@0.6.12) #> evaluate 0.10 2016-10-11 cran (@0.10) #> htmltools 0.3.5 2016-03-21 CRAN (R 3.3.0) #> knitr 1.15.1 2016-11-22 CRAN (R 3.3.2) #> magrittr 1.5 2016-05-26 local #> memoise 1.0.0 2016-01-29 CRAN (R 3.3.0) #> pkgbuild 0.0.0.9000 2016-12-06 local #> pkgload 0.0.0.9000 2017-01-25 local #> Rcpp 0.12.9 2017-01-14 CRAN (R 3.3.2) #> rmarkdown 1.3 2016-12-21 CRAN (R 3.3.2) #> rprojroot 1.2 2017-01-25 local (krlmlr/rprojroot@6d1069c) #> stringi 1.1.2 2016-10-01 cran (@1.1.2) #> stringr 1.1.0.9000 2017-01-25 local #> withr 1.0.2 2017-02-24 local #> xml2 * 1.1.1 2017-01-24 CRAN (R 3.3.2) #> yaml 2.1.14 2016-11-12 CRAN (R 3.3.2) ```
jordansread commented 7 years ago

same with xml_add_child, where the docs look like .value can be a nodeset, but it has the same error as above.

@krlmlr do you have a current workaround? I am running into similar trouble adding a lot of nodes (~30K) at once as looping per child bogs down the more I add.

krlmlr commented 7 years ago

Unfortunately not.

jordansread commented 7 years ago

Thanks

jimhester commented 7 years ago

All of the modification functions have nodeset methods for the first argument, not the second. So you can do xml_add_sibling(children, children[[1]]), but not the reverse. If you want to do what you are suggesting just use a loop.

for (child in children) {
  xml_add_sibling(children[[1]], child)
}
krlmlr commented 7 years ago

Is this a limitation of the libxml2 API, or could we perhaps support these use cases? I needed this to move a chunk of a HTML document to another place.

jordansread commented 7 years ago

Part of the confusion on this for me is that the doc says

https://github.com/r-lib/xml2/blob/1856377a5d04060a1825cc2770e3a2157695e40d/man/xml_replace.Rd#L26 should it just be node to insert. ?