diff options
-rw-r--r-- | examples/nanohttp/postserver.c | 90 | ||||
-rw-r--r-- | libcsoap/Makefile.am | 36 | ||||
-rw-r--r-- | libcsoap/soap-call.c | 227 | ||||
-rw-r--r-- | libcsoap/soap-call.h | 63 | ||||
-rw-r--r-- | libcsoap/soap-fault.c | 120 | ||||
-rw-r--r-- | libcsoap/soap-fault.h | 44 | ||||
-rw-r--r-- | libcsoap/soap-xml.c | 113 | ||||
-rw-r--r-- | libcsoap/soap-xml.h | 45 |
8 files changed, 709 insertions, 29 deletions
diff --git a/examples/nanohttp/postserver.c b/examples/nanohttp/postserver.c new file mode 100644 index 0000000..a002f45 --- /dev/null +++ b/examples/nanohttp/postserver.c @@ -0,0 +1,90 @@ +/****************************************************************** + * $Id: postserver.c,v 1.1 2004/01/30 16:38:49 snowdrop Exp $ + * + * CSOAP Project: A http client/server library in C (example) + * Copyright (C) 2003 Ferhat Ayaz + * + * This library is free software; you can redistribute it and/or + * modify it under the terms of the GNU Library General Public + * License as published by the Free Software Foundation; either + * version 2 of the License, or (at your option) any later version. + * + * This library is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * Library General Public License for more details. + * + * You should have received a copy of the GNU Library General Public + * License along with this library; if not, write to the + * Free Software Foundation, Inc., 59 Temple Place - Suite 330, + * Boston, MA 02111-1307, USA. + * + * Email: ayaz@jprogrammer.net + ******************************************************************/ +#include <nanohttp/nanohttp-server.h> + +#include <stdio.h> + + +/* + SERVICE: http://host:port/postserver + */ +void post_service(httpd_conn_t *conn, hrequest_t *req) +{ + char *postdata; + long received; + + postdata = httpd_get_postdata(conn, req, &received, -1); + + if (postdata != NULL) { + + httpd_send_header(conn, 200, "OK", NULL); + hsocket_send(conn->sock, "<html><body>"); + hsocket_send(conn->sock, "<h3>You Posted:</h3><hr>"); + hsocket_nsend(conn->sock, postdata, received); + hsocket_send(conn->sock, "</body></html>"); + free(postdata); + + } else { + + httpd_send_header(conn, 200, "OK", NULL); + hsocket_send(conn->sock, "<html><body>"); + hsocket_send(conn->sock, "<form action=\"/postserver\" method=\"POST\">"); + hsocket_send(conn->sock, "Enter Postdata: <input name=\"field\" type=\"text\">"); + hsocket_send(conn->sock, "<input type=\"submit\">"); + hsocket_send(conn->sock, "</body></html>"); + + } + + +} + + +int main(int argc, char *argv[]) +{ + + if (httpd_init(argc, argv)) { + fprintf(stderr, "can not init httpd"); + return 1; + } + + if (!httpd_register("/postserver", post_service)) { + fprintf(stderr, "Can not register service"); + return 1; + } + + if (httpd_run()) { + fprintf(stderr, "can not run httpd"); + return 1; + } + + return 0; +} + + + + + + + + diff --git a/libcsoap/Makefile.am b/libcsoap/Makefile.am index d3889e9..1dea69d 100644 --- a/libcsoap/Makefile.am +++ b/libcsoap/Makefile.am @@ -1,35 +1,13 @@ ## Source directory -h_sources = csoap.h\ -csoapbody.h\ -csoapcall.h\ -csoapenv.h\ -csoaperror.h\ -csoapfault.h\ -csoaphttp.h\ -csoaplog.h\ -csoapmethod.h\ -csoapparam.h\ -csoapres.h\ -csoapsocket.h\ -csoaptypes.h\ -csoapurl.h\ -csoapxml.h - -cc_sources = csoap.c\ -csoapbody.c\ -csoapcall.c\ -csoapenv.c\ -csoapfault.c\ -csoaphttp.c\ -csoaplog.c\ -csoapmethod.c\ -csoapparam.c\ -csoapres.c\ -csoapsocket.c\ -csoapurl.c\ -csoapxml.c +h_sources = soap-xml.h\ +soap-fault.h\ +soap-call.h + +cc_sources = soap-xml.c\ +soap-fault.c\ +soap-call.c library_includedir=$(includedir)/$(GENERIC_LIBRARY_NAME)-$(GENERIC_API_VERSION)/$(GENERIC_LIBRARY_NAME) library_include_HEADERS = $(h_sources) diff --git a/libcsoap/soap-call.c b/libcsoap/soap-call.c new file mode 100644 index 0000000..31ec597 --- /dev/null +++ b/libcsoap/soap-call.c @@ -0,0 +1,227 @@ +/****************************************************************** + * $Id: soap-call.c,v 1.1 2004/01/30 16:39:34 snowdrop Exp $ + * + * CSOAP Project: A SOAP client/server library in C + * Copyright (C) 2003 Ferhat Ayaz + * + * This library is free software; you can redistribute it and/or + * modify it under the terms of the GNU Library General Public + * License as published by the Free Software Foundation; either + * version 2 of the License, or (at your option) any later version. + * + * This library is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * Library General Public License for more details. + * + * You should have received a copy of the GNU Library General Public + * License along with this library; if not, write to the + * Free Software Foundation, Inc., 59 Temple Place - Suite 330, + * Boston, MA 02111-1307, USA. + * + * Email: ayaz@jprogrammer.net + ******************************************************************/ +#include <libcsoap/soap-call.h> +#include <libcsoap/soap-xml.h> +#include <libcsoap/soap-fault.h> +#include <nanohttp/nanohttp-client.h> +#include <stdarg.h> + + +static char *soap_env_ns = "http://schemas.xmlsoap.org/soap/envelope/"; +static char *soap_env_enc = "http://schemas.xmlsoap.org/soap/encoding/"; +static char *soap_xsi_ns = "http://www.w3.org/1999/XMLSchema-instance"; +static char *soap_xsd_ns = "http://www.w3.org/1999/XMLSchema"; + +/* + Parameters: + 1- soap_env_ns + 2- soap_env_enc + 3- xsi_ns + 4- xsd_ns + 3- method name + 4- uri + 5- method name(again) + */ +#define _SOAP_MSG_TEMPLATE_ \ + "<SOAP-ENV:Envelope xmlns:SOAP-ENV=\"%s\" SOAP-ENV:encoding=\"%s\"" \ + " xmlns:xsi=\"%s\"" \ + " xmlns:xsd=\"%s\">" \ + " <SOAP-ENV:Body>"\ + " <m:%s xmlns:m=\"%s\">"\ + " </m:%s>" \ + " </SOAP-ENV:Body>"\ + "</SOAP-ENV:Envelope>" + + +/*--------------------------------- */ +static +xmlDocPtr _soap_call_build_result(hresponse_t *res); +/*--------------------------------- */ + + +SoapCall* soap_call_new(const char *urn, const char *method) +{ + xmlDocPtr env; + xmlNodePtr node; + SoapCall *call; + char buffer[1054]; + + + log_verbose3("URN = '%s'\nMethod = '%s'\n", urn, method); + + sprintf(buffer, _SOAP_MSG_TEMPLATE_, + soap_env_ns, soap_env_enc, soap_xsi_ns, + soap_xsd_ns, method, urn, method); + + env = xmlParseDoc(buffer); + if (env == NULL) { + log_error1("Can not create xml document!"); + return NULL; + } + + node = xmlDocGetRootElement(env); + if (node == NULL) { + log_error1("xml document is empty!"); + return NULL; + } + + call = (SoapCall*)malloc(sizeof(SoapCall)); + + /* set root */ + call->root = node; + + /* set method root + set call->cur (current node) to <method>. + xpath: //Envelope/Body/ + */ + node = soap_xml_get_children(call->root); + call->cur = soap_xml_get_children(node); + + return call; +} + + + +xmlNodePtr +soap_call_add_param(SoapCall *call, const char *type, + const char *name, const char *value) +{ + + xmlNodePtr newnode; + + newnode = xmlNewTextChild(call->cur, NULL, name, value); + + if (newnode == NULL) { + log_error1("Can not create new xml node"); + return NULL; + } + + if (type) { + if (!xmlNewProp(newnode, "xsi:type", type)) { + log_error1("Can not create new xml attribute"); + return NULL; + } + } + + return newnode; +} + + +xmlNodePtr +soap_call_add_paramf(SoapCall *call, const char *type, + const char *name, const char *format, ...) +{ + + va_list ap; + char buffer[1054]; + xmlNodePtr newnode; + + + va_start(ap, format); + vsprintf(buffer, format, ap); + va_end(ap); + + return soap_call_add_param(call, type, name, buffer); +} + +xmlNodePtr +soap_call_push_param(SoapCall *call, const char *type, + const char *name) +{ + + xmlNodePtr node; + + node = soap_call_add_param(call, type, name, ""); + + if (node) { + call->cur = node; + } + + return node; +} + + +void +soap_call_pop_param(SoapCall *call) +{ + call->cur = call->cur->parent; +} + + +xmlDocPtr +soap_call_invoke(SoapCall *call, const char *url) +{ + /* Result document */ + xmlDocPtr doc; + + /* Buffer variables*/ + xmlBufferPtr buffer; + char *content; + + /* Transport variables */ + httpc_conn_t *conn; + hresponse_t *res; + + /* Create buffer */ + buffer = xmlBufferCreate(); + xmlNodeDump(buffer, call->root->doc,call->root, 1 ,2); + content = (char*)xmlBufferContent(buffer); + + /* Transport via HTTP */ + conn = httpc_new(); + res = httpc_post(conn, url, strlen(content), content); + + /* Free buffer */ + xmlBufferFree(buffer); + + /* Build result */ + doc = _soap_call_build_result(res); + + return doc; +} + + +static +xmlDocPtr _soap_call_build_result(hresponse_t *res) +{ + xmlDocPtr doc; + + if (res == NULL) + return soap_fault_build(Fault_Client, + "Response is NULL","",""); + + if (res->body) + return soap_fault_build(Fault_Client, + "Empty response from server!","",""); + + + doc = xmlParseDoc(res->body); + if (doc == NULL) { + return soap_fault_build(Fault_Client, + "Response is not in XML format!","",""); + } + + return doc; +} + diff --git a/libcsoap/soap-call.h b/libcsoap/soap-call.h new file mode 100644 index 0000000..970b2ab --- /dev/null +++ b/libcsoap/soap-call.h @@ -0,0 +1,63 @@ +/****************************************************************** + * $Id: soap-call.h,v 1.1 2004/01/30 16:39:34 snowdrop Exp $ + * + * CSOAP Project: A SOAP client/server library in C + * Copyright (C) 2003 Ferhat Ayaz + * + * This library is free software; you can redistribute it and/or + * modify it under the terms of the GNU Library General Public + * License as published by the Free Software Foundation; either + * version 2 of the License, or (at your option) any later version. + * + * This library is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * Library General Public License for more details. + * + * You should have received a copy of the GNU Library General Public + * License along with this library; if not, write to the + * Free Software Foundation, Inc., 59 Temple Place - Suite 330, + * Boston, MA 02111-1307, USA. + * + * Email: ayaz@jprogrammer.net + ******************************************************************/ +#ifndef cSOAP_CALL_H +#define cSOAP_CALL_H + +#include <libcsoap/soap-xml.h> + + +typedef struct _SoapCall +{ + xmlNodePtr root; /* shortcut */ + xmlNodePtr cur; +}SoapCall; + + + +SoapCall* soap_call_new(const char *urn, const char *method); + +xmlNodePtr +soap_call_add_param(SoapCall *call, const char *type, + const char *name, const char *value); + +xmlNodePtr +soap_call_add_paramf(SoapCall *call, const char *type, + const char *name, const char *format, ...); + + +xmlNodePtr +soap_call_push_param(SoapCall *call, const char *type, + const char *name); + +void +soap_call_pop_param(SoapCall *call); + + +xmlDocPtr +soap_call_invoke(SoapCall *call, const char *url); + + +#endif + + diff --git a/libcsoap/soap-fault.c b/libcsoap/soap-fault.c new file mode 100644 index 0000000..30a972a --- /dev/null +++ b/libcsoap/soap-fault.c @@ -0,0 +1,120 @@ +/****************************************************************** + * $Id: soap-fault.c,v 1.1 2004/01/30 16:39:34 snowdrop Exp $ + * + * CSOAP Project: A SOAP client/server library in C + * Copyright (C) 2003 Ferhat Ayaz + * + * This library is free software; you can redistribute it and/or + * modify it under the terms of the GNU Library General Public + * License as published by the Free Software Foundation; either + * version 2 of the License, or (at your option) any later version. + * + * This library is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * Library General Public License for more details. + * + * You should have received a copy of the GNU Library General Public + * License along with this library; if not, write to the + * Free Software Foundation, Inc., 59 Temple Place - Suite 330, + * Boston, MA 02111-1307, USA. + * + * Email: ayaz@jprogrammer.net + ******************************************************************/ +#include <libcsoap/soap-fault.h> +#include <libcsoap/soap-xml.h> + + +static char *soap_env_ns = "http://schemas.xmlsoap.org/soap/envelope/"; +static char *soap_env_enc = "http://schemas.xmlsoap.org/soap/encoding/"; +static char *soap_xsi_ns = "http://www.w3.org/1999/XMLSchema-instance"; +static char *soap_xsd_ns = "http://www.w3.org/1999/XMLSchema"; + +/* + Parameters: + 1- soap_env_ns + 2- soap_env_enc + 3- xsi_ns + 4- xsd_ns + 5- faultcode + 6- faultstring + 7- faultactor + 8- detail + */ +#define _SOAP_FAULT_TEMPLATE_ \ + "<SOAP-ENV:Envelope xmlns:SOAP-ENV=\"%s\" SOAP-ENV:encoding=\"%s\"" \ + " xmlns:xsi=\"%s\"" \ + " xmlns:xsd=\"%s\">" \ + " <SOAP-ENV:Body>"\ + " <Fault>"\ + " <faultcode>%s</faultcode>"\ + " <faultstring>%s</faultstring>"\ + " <faultactor>%s</faultactor>"\ + " <faultdetail>%s</faultdetail>"\ + " </Fault>" \ + " </SOAP-ENV:Body>"\ + "</SOAP-ENV:Envelope>" + + + +static char *fault_vm = "VersionMismatch"; +static char *fault_mu = "MustUnderstand"; +static char *fault_client = "Client"; +static char *fault_server = "Server"; + +xmlDocPtr soap_fault_build(fault_code_t fcode, + const char *faultstring, + const char *faultactor, + const char *detail) +{ + + /* variables */ + char *faultcode; + int bufferlen = 200; + char *buffer; + xmlDocPtr fault; /* result */ + + switch (fcode) { + case Fault_VersionMismatch: + faultcode = fault_vm; + break; + case Fault_MustUnderstand: + faultcode = fault_mu; + break; + case Fault_Client: + faultcode = fault_client; + break; + case Fault_Server: + faultcode = fault_server; + break; + default: + faultcode = fault_client; + } + + /* calculate buffer length */ + if (faultstring) bufferlen += strlen(faultstring); + if (faultactor) bufferlen += strlen(faultactor); + if (detail) bufferlen += strlen(detail); + + buffer = (char*)malloc(bufferlen); + + sprintf(buffer, _SOAP_FAULT_TEMPLATE_, + soap_env_ns, soap_env_enc, soap_xsi_ns, + soap_xsd_ns, faultcode, + faultstring?faultstring:"error", + faultactor?faultactor:"", + detail?detail:""); + + fault = xmlParseDoc(buffer); + free(buffer); + + if (fault == NULL) { + log_error1("Can not create xml document!"); + + return soap_fault_build(fcode, "Can not create fault object in xml", + "soap_fault_build()", NULL); + } + + return fault; + +} diff --git a/libcsoap/soap-fault.h b/libcsoap/soap-fault.h new file mode 100644 index 0000000..a65d803 --- /dev/null +++ b/libcsoap/soap-fault.h @@ -0,0 +1,44 @@ +/****************************************************************** + * $Id: soap-fault.h,v 1.1 2004/01/30 16:39:34 snowdrop Exp $ + * + * CSOAP Project: A SOAP client/server library in C + * Copyright (C) 2003 Ferhat Ayaz + * + * This library is free software; you can redistribute it and/or + * modify it under the terms of the GNU Library General Public + * License as published by the Free Software Foundation; either + * version 2 of the License, or (at your option) any later version. + * + * This library is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * Library General Public License for more details. + * + * You should have received a copy of the GNU Library General Public + * License along with this library; if not, write to the + * Free Software Foundation, Inc., 59 Temple Place - Suite 330, + * Boston, MA 02111-1307, USA. + * + * Email: ayaz@jprogrammer.net + ******************************************************************/ +#ifndef cSOAP_FAULT_H +#define cSOAP_FAULT_H + +#include <libcsoap/soap-xml.h> + + +typedef enum _fault_code { + Fault_VersionMismatch, + Fault_MustUnderstand, + Fault_Client, + Fault_Server +}fault_code_t; + + +xmlDocPtr soap_fault_build(fault_code_t faultcode, + const char *faultstring, + const char *faultactor, + const char *detail); + + +#endif diff --git a/libcsoap/soap-xml.c b/libcsoap/soap-xml.c new file mode 100644 index 0000000..185672d --- /dev/null +++ b/libcsoap/soap-xml.c @@ -0,0 +1,113 @@ +/****************************************************************** + * $Id: soap-xml.c,v 1.1 2004/01/30 16:39:35 snowdrop Exp $ + * + * CSOAP Project: A SOAP client/server library in C + * Copyright (C) 2003 Ferhat Ayaz + * + * This library is free software; you can redistribute it and/or + * modify it under the terms of the GNU Library General Public + * License as published by the Free Software Foundation; either + * version 2 of the License, or (at your option) any later version. + * + * This library is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * Library General Public License for more details. + * + * You should have received a copy of the GNU Library General Public + * License along with this library; if not, write to the + * Free Software Foundation, Inc., 59 Temple Place - Suite 330, + * Boston, MA 02111-1307, USA. + * + * Email: ayaz@jprogrammer.net + ******************************************************************/ +#include <libcsoap/soap-xml.h> + + +xmlNodePtr soap_xml_get_children(xmlNodePtr param) +{ + xmlNodePtr children; + const char* FUNC = "soap_xml_get_children"; + + if (param == NULL) { + log_error1("Invalid parameter 'param' (null)"); + return NULL; + } + + children = param->xmlChildrenNode; + while (children != NULL) { + if (children->type != XML_ELEMENT_NODE) + children = children->next; + else break; + } + + return children; +} + + +xmlXPathObjectPtr +soap_xpath_eval(xmlDocPtr doc, const char *xpath) +{ + xmlXPathContextPtr context; + xmlXPathObjectPtr result; + + context = xmlXPathNewContext(doc); + result = xmlXPathEvalExpression((xmlChar*)xpath, context); + if(xmlXPathNodeSetIsEmpty(result->nodesetval)){ + /* no result */ + return NULL; + } + + xmlXPathFreeContext(context); + return result; +} + + +int +soap_xpath_foreach(xmlDocPtr doc, const char *xpath, + soap_xmlnode_callback cb) +{ + int i = 0; + xmlNodeSetPtr nodeset; + xmlXPathObjectPtr xpathobj; + + xpathobj = soap_xpath_eval(doc, xpath); + + if (!xpathobj) return 0; + + nodeset = xpathobj->nodesetval; + if (!nodeset) return 0; + + for (i=0;i < nodeset->nodeNr; i++) { + if (!cb(nodeset->nodeTab[i])) + break; + } + + xmlXPathFreeObject(nodeset); + return i; +} + + +void soap_xml_doc_print(xmlDocPtr doc) +{ + xmlBufferPtr buffer; + xmlNodePtr root; + + if (doc == NULL) { + puts("xmlDocPtr is NULL!"); + return; + } + + root = xmlDocGetRootElement(doc); + if (root == NULL) { + puts("Empty document!"); + return; + } + + + buffer = xmlBufferCreate(); + xmlNodeDump(buffer, doc, root, 1 ,2); + puts( (const char*)xmlBufferContent(buffer)); + xmlBufferFree(buffer); + +} diff --git a/libcsoap/soap-xml.h b/libcsoap/soap-xml.h new file mode 100644 index 0000000..4abdb8e --- /dev/null +++ b/libcsoap/soap-xml.h @@ -0,0 +1,45 @@ +/****************************************************************** + * $Id: soap-xml.h,v 1.1 2004/01/30 16:39:35 snowdrop Exp $ + * + * CSOAP Project: A SOAP client/server library in C + * Copyright (C) 2003 Ferhat Ayaz + * + * This library is free software; you can redistribute it and/or + * modify it under the terms of the GNU Library General Public + * License as published by the Free Software Foundation; either + * version 2 of the License, or (at your option) any later version. + * + * This library is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * Library General Public License for more details. + * + * You should have received a copy of the GNU Library General Public + * License along with this library; if not, write to the + * Free Software Foundation, Inc., 59 Temple Place - Suite 330, + * Boston, MA 02111-1307, USA. + * + * Email: ayaz@jprogrammer.net + ******************************************************************/ +#ifndef cSOAP_XML_H +#define cSOAP_XML_H + +#include <libxml/xpath.h> + +#include <nanohttp/nanohttp-common.h> + +typedef int (*soap_xmlnode_callback)(xmlNodePtr); + + +xmlNodePtr soap_xml_get_children(xmlNodePtr param); + +xmlXPathObjectPtr +soap_xpath_eval(xmlDocPtr doc, const char *xpath); + +int +soap_xpath_foreach(xmlDocPtr doc, const char *xpath, + soap_xmlnode_callback cb); + + + +#endif |