/*
xpath2 ini/config.xml '//anode'
* section: XPath
* synopsis: Load a document, locate subelements with XPath,
* usage: xpath2 <xml-file> <xpath-expr>
* test: xpath2 test3.xml '//discarded'
*/
#include <stdlib.h>
#include <stdio.h>
#include <string.h>
#include <assert.h>
#include <vector>
#include <libxml/tree.h>
#include <libxml/parser.h>
#include <libxml/xpath.h>
#include <libxml/xpathInternals.h>
#if defined(LIBXML_XPATH_ENABLED) && defined(LIBXML_SAX1_ENABLED) && \
defined(LIBXML_OUTPUT_ENABLED)
static int getvalue
(xmlXPathContextPtr xpathCtx
, const xmlChar
* xpathExpr
, std
::vector <xmlChar
*> &retval
);
static xmlChar
* getvalue
(xmlXPathContextPtr xpathCtx
, const xmlChar
* xpathExpr
, int which
=0);
int
main
(int argc
, char **argv
) {
std
::vector<xmlChar
*> retval
;
xmlDocPtr doc
;
xmlXPathContextPtr xpathCtx
;
int size
;
xmlInitParser
();
LIBXML_TEST_VERSION
/* Load XML document */
doc
= xmlParseFile
(argv
[1]);
if (doc
== NULL
) {
fprintf(stderr
, "Error: unable to parse file \"%s\"\n", argv
[1]);
return(-1);
}
/* Create xpath evaluation context */
xpathCtx
= xmlXPathNewContext
(doc
);
if(xpathCtx
== NULL
) {
fprintf(stderr
,"Error: unable to create new XPath context\n");
xmlFreeDoc
(doc
);
return(-1);
}
for (int i
=2; i
<argc
;i
++){
size
= getvalue
(xpathCtx
, BAD_CAST argv
[i
] , retval
);
printf ("-->size = %d value %s\n",size
, getvalue
(xpathCtx
, BAD_CAST argv
[i
]) );
}
xmlXPathFreeContext
(xpathCtx
);
xmlFreeDoc
(doc
);
xmlCleanupParser
();
xmlMemoryDump
();
return 0;
}
/**
* getvalue:
* @xpathCtx: the input xmlXPathContextPtr
* @xpathExpr: the xpath expression for evaluation.
*
* evaluates XPath expression
*
* Returns node content
*/
int getvalue
(xmlXPathContextPtr xpathCtx
, const xmlChar
* xpathExpr
, std
::vector<xmlChar
*> &retval
) {
xmlXPathObjectPtr xpathObj
;
xmlNodeSetPtr nodes
;
xmlChar
* ret
=NULL
;
int size
;
int i
;
assert(xpathExpr
);
/* Evaluate xpath expression */
xpathObj
= xmlXPathEvalExpression
(xpathExpr
, xpathCtx
);
if(xpathObj
== NULL
) {
fprintf(stderr
,"Error: unable to evaluate xpath expression \"%s\"\n", xpathExpr
);
return retval.
size();
}
nodes
= xpathObj
->nodesetval
;
size
= (nodes
) ? nodes
->nodeNr
: 0;
for(i
= 0; i
< size
; i
++) {
ret
= xmlNodeGetContent
(nodes
->nodeTab
[i
]);
if(ret
) {
retval.
push_back(ret
);
printf("[%d] %s Return value: %s\n", i
, xpathExpr
, ret
);
}
}
/* Cleanup of XPath data */
xmlXPathFreeObject
(xpathObj
);
return retval.
size();
}
xmlChar
* getvalue
(xmlXPathContextPtr xpathCtx
, const xmlChar
* xpathExpr
, int which
) {
xmlXPathObjectPtr xpathObj
;
xmlNodeSetPtr nodes
;
xmlChar
* ret
=NULL
;
int size
;
int i
;
assert(xpathExpr
);
/* Evaluate xpath expression */
xpathObj
= xmlXPathEvalExpression
(xpathExpr
, xpathCtx
);
if(xpathObj
== NULL
) {
fprintf(stderr
,"Error: unable to evaluate xpath expression \"%s\"\n", xpathExpr
);
return NULL
;
}
nodes
= xpathObj
->nodesetval
;
size
= (nodes
) ? nodes
->nodeNr
: 0;
for(i
= 0; i
< size
; i
++) {
ret
= xmlNodeGetContent
(nodes
->nodeTab
[i
]);
if(ret
) {
printf("%s Return value: %s\n", xpathExpr
, ret
);
return ret
;
}
}
/* Cleanup of XPath data */
xmlXPathFreeObject
(xpathObj
);
return NULL
;
}
#endif