Search code examples
libxml2

Create a new node and its child nodes from a string


I've tried functions xmlNewDocNode and xmlNewDocRawNode, but they both XML-escape the content string we pass to them as a argument. Therefore, it's obviously both of them can only create a single node instead of a subtree. Is there a function that allows us to create a subtree? For instance, if we pass a string <foo><bar>baz</bar></foo> to the function, it will create a subtree:

foo: xmlNode
`- bar: xmlNode
   `- baz: plaintext

instead of

foo: xmlNode
`- <bar>baz</bar>: plaintext

Re-edit: It's doable to parse the text into a temporary document node, and then find the node we want and detach it from the document. This way of creating new node from text seems kind of overkill. I'm wondering is there a libxml2 function that can do it for us.


Solution

  • There is xmlParseBalancedChunkMemory. It's behaviour is slightly more general in that it can parse a series of nodes. But that's easily checked for, as in the following C example:

    #include <stdio.h>
    #include <libxml/parser.h>
    #include <libxml/tree.h>
    int
    main(int argc, char **argv)
    {
        xmlDoc *doc = NULL;
        xmlNodePtr nodes = NULL;
        xmlChar *string = "<foo><bar>baz</bar></foo><blah/>";
        int stat = xmlParseBalancedChunkMemory(NULL, NULL, NULL, 0, string, &nodes );
        printf("stat: %d\n", stat);
        if (stat == 0) {
            printf("first: %s\n", nodes->name);
            printf("first-child: %s\n", nodes->children->name);
            printf("next: %s\n", nodes->next->name);
        }
        if (nodes != NULL) xmlFreeNodeList(nodes);
    }
    

    Output:

    stat: 0
    first: foo
    first-child: bar
    next: blah