diff options
-rw-r--r-- | libcsoap/soap-router.c | 34 | ||||
-rw-r--r-- | libcsoap/soap-router.h | 5 | ||||
-rw-r--r-- | libcsoap/soap-server.c | 140 |
3 files changed, 110 insertions, 69 deletions
diff --git a/libcsoap/soap-router.c b/libcsoap/soap-router.c index 7b93b03..c4252c2 100644 --- a/libcsoap/soap-router.c +++ b/libcsoap/soap-router.c @@ -1,5 +1,5 @@ /****************************************************************** -* $Id: soap-router.c,v 1.7 2006/02/27 22:26:02 snowdrop Exp $ +* $Id: soap-router.c,v 1.8 2006/03/07 16:22:24 m0gg Exp $ * * CSOAP Project: A SOAP client/server library in C * Copyright (C) 2003 Ferhat Ayaz @@ -29,6 +29,10 @@ #include <string.h> #endif +#ifdef HAVE_ERRNO_H +#include <errno.h> +#endif + #include "soap-router.h" SoapRouter * @@ -36,10 +40,12 @@ soap_router_new(void) { SoapRouter *router; - router = (SoapRouter *) malloc(sizeof(SoapRouter)); - router->service_head = NULL; - router->service_tail = NULL; - router->default_service = NULL; + if (!(router = (SoapRouter *) malloc(sizeof(SoapRouter)))) + { + log_error2("malloc failed (%s)", strerror(errno)); + return NULL; + } + memset(router, 0, sizeof(SoapRouter)); return router; } @@ -68,6 +74,17 @@ soap_router_register_service(SoapRouter * router, } void +soap_router_register_description(SoapRouter * router, xmlDocPtr wsdl) +{ + if (router->wsdl) + xmlFreeDoc(router->wsdl); + + router->wsdl = xmlCopyDoc(wsdl, 1); + + return; +} + +void soap_router_register_default_service(SoapRouter *router, SoapServiceFunc func, const char *method, const char *urn) { SoapService *service; @@ -123,7 +140,8 @@ soap_router_free(SoapRouter * router) { SoapServiceNode *node; log_verbose2("enter: router=%p", router); - if (router == NULL) + + if (!router) return; while (router->service_head) @@ -135,7 +153,11 @@ soap_router_free(SoapRouter * router) free(router->service_head); router->service_head = node; } + if (router->wsdl) + xmlFreeDoc(router->wsdl); free(router); log_verbose1("leave with success"); + + return; } diff --git a/libcsoap/soap-router.h b/libcsoap/soap-router.h index 41ea95f..ff44988 100644 --- a/libcsoap/soap-router.h +++ b/libcsoap/soap-router.h @@ -1,5 +1,5 @@ /****************************************************************** - * $Id: soap-router.h,v 1.6 2006/03/06 13:37:38 m0gg Exp $ + * $Id: soap-router.h,v 1.7 2006/03/07 16:22:24 m0gg Exp $ * * CSOAP Project: A SOAP client/server library in C * Copyright (C) 2003 Ferhat Ayaz @@ -35,6 +35,7 @@ typedef struct _SoapRouter SoapServiceNode *service_head; SoapServiceNode *service_tail; SoapService *default_service; + xmlDocPtr wsdl; } SoapRouter; @@ -71,6 +72,8 @@ void soap_router_register_service(SoapRouter * router, void soap_router_register_default_service(SoapRouter * router, SoapServiceFunc func, const char *method, const char *urn); +void soap_router_register_description(SoapRouter *router, xmlDocPtr doc); + /** Searches for a registered soap service. diff --git a/libcsoap/soap-server.c b/libcsoap/soap-server.c index 33e1736..0e414f5 100644 --- a/libcsoap/soap-server.c +++ b/libcsoap/soap-server.c @@ -1,5 +1,5 @@ /****************************************************************** -* $Id: soap-server.c,v 1.19 2006/03/06 13:37:38 m0gg Exp $ +* $Id: soap-server.c,v 1.20 2006/03/07 16:22:24 m0gg Exp $ * * CSOAP Project: A SOAP client/server library in C * Copyright (C) 2003 Ferhat Ayaz @@ -162,7 +162,7 @@ _soap_server_send_ctx(httpd_conn_t * conn, SoapCtx * ctx) xpathCtx = xmlXPathNewContext(ctx->env->root->doc); xpathObj = xmlXPathEvalExpression("//Fault", xpathCtx); - snprintf(buflen, 100, "%d", strlen((const char *) xmlBufferContent(buffer))); + snprintf(buflen, 100, "%d", xmlBufferLength(buffer)); httpd_set_header(conn, HEADER_CONTENT_LENGTH, buflen); if ((xpathObj->nodesetval) ? xpathObj->nodesetval->nodeNr : 0) { @@ -184,6 +184,26 @@ _soap_server_send_ctx(httpd_conn_t * conn, SoapCtx * ctx) return; } +static void +_soap_server_send_description(httpd_conn_t *conn, xmlDocPtr wsdl) +{ + char length[16]; + xmlBufferPtr buf; + + buf = xmlBufferCreate(); + xmlNodeDump(buf, wsdl, xmlDocGetRootElement(wsdl), 0, 0); + + sprintf(length, "%d", xmlBufferLength(buf)); + httpd_set_header(conn, HEADER_CONTENT_LENGTH, length); + httpd_send_header(conn, 200, "OK"); + + http_output_stream_write_string(conn->out, xmlBufferContent(buf)); + + xmlBufferFree(buf); + + return; +} + static SoapRouterNode * router_node_new(SoapRouter * router, const char *context, SoapRouterNode * next) { @@ -238,9 +258,19 @@ soap_server_entry(httpd_conn_t * conn, hrequest_t * req) SoapEnv *env; herror_t err; - if (req->method != HTTP_REQUEST_POST) + if (!(router = router_find(req->path))) { + _soap_server_send_fault(conn, "Cannot find router"); + return; + } + else if (req->method == HTTP_REQUEST_GET && router->wsdl) + { + _soap_server_send_description(conn, router->wsdl); + return; + } + if (req->method != HTTP_REQUEST_POST) + { httpd_send_header(conn, 200, "OK"); http_output_stream_write_string(conn->out, "<html>" @@ -286,44 +316,61 @@ soap_server_entry(httpd_conn_t * conn, hrequest_t * req) /* soap_xml_doc_print(env->root->doc); */ - router = router_find(req->path); + if (!(urn=soap_env_find_urn(ctx->env))) + { + + _soap_server_send_fault(conn, "No URN found!"); + soap_ctx_free(ctx); + return; + } + else + { + log_verbose2("urn: '%s'", urn); + } - if (router == NULL) + if (!(method=soap_env_find_methodname(ctx->env))) { - _soap_server_send_fault(conn, "Can not find router!"); + _soap_server_send_fault(conn, "No method found!"); + soap_ctx_free(ctx); + return; } else { + log_verbose2("method: '%s'", method); + } - if (!(urn=soap_env_find_urn(ctx->env))) - { + service = soap_router_find_service(router, urn, method); - _soap_server_send_fault(conn, "No URN found!"); - soap_ctx_free(ctx); - return; - } - else - { - log_verbose2("urn: '%s'", urn); - } + if (service == NULL) + { - if (!(method=soap_env_find_methodname(ctx->env))) + sprintf(buffer, "URN '%s' not found", urn); + _soap_server_send_fault(conn, buffer); + soap_ctx_free(ctx); + return; + } + else + { + + log_verbose2("func: %p", service->func); + ctxres = soap_ctx_new(NULL); + /* ===================================== */ + /* CALL SERVICE FUNCTION */ + /* ===================================== */ + if ((err = service->func(ctx, ctxres)) != H_OK) { - _soap_server_send_fault(conn, "No method found!"); + sprintf(buffer, "Service returned following error message: '%s'", + herror_message(err)); + herror_release(err); + _soap_server_send_fault(conn, buffer); soap_ctx_free(ctx); return; } - else - { - log_verbose2("method: '%s'", method); - } - - service = soap_router_find_service(router, urn, method); - if (service == NULL) + if (ctxres->env == NULL) { - sprintf(buffer, "URN '%s' not found", urn); + sprintf(buffer, "Service '%s' returned no envelope", urn); _soap_server_send_fault(conn, buffer); soap_ctx_free(ctx); return; @@ -331,44 +378,13 @@ soap_server_entry(httpd_conn_t * conn, hrequest_t * req) else { - log_verbose2("func: %p", service->func); - ctxres = soap_ctx_new(NULL); - /* ===================================== */ - /* CALL SERVICE FUNCTION */ - /* ===================================== */ - err = service->func(ctx, ctxres); - if (err != H_OK) - { - sprintf(buffer, "Service returned following error message: '%s'", - herror_message(err)); - herror_release(err); - _soap_server_send_fault(conn, buffer); - soap_ctx_free(ctx); - return; - } - - if (ctxres->env == NULL) - { - - sprintf(buffer, "Service '%s' returned no envelope", urn); - _soap_server_send_fault(conn, buffer); - soap_ctx_free(ctx); - return; - - } - else - { - -/* httpd_send_header(conn, 200, "OK"); - _soap_server_send_env(conn->out, ctxres->env); +/* httpd_send_header(conn, 200, "OK"); + _soap_server_send_env(conn->out, ctxres->env); */ - _soap_server_send_ctx(conn, ctxres); - /* free envctx */ - soap_ctx_free(ctxres); - } - + _soap_server_send_ctx(conn, ctxres); + /* free envctx */ + soap_ctx_free(ctxres); } - } } soap_ctx_free(ctx); |