工具:gsoap-2.8.66(這個是目前各個公司使用最多的,也是最完善的)html
系統環境:Centos7 64位ios
步驟:c++
1.手動編寫calc.h文件程序員
//gsoap ns service name: calc Simple calculator service described at https://www.genivia.com/dev.html //gsoap ns service protocol: SOAP //gsoap ns service style: rpc //gsoap ns service encoding: encoded //gsoap ns service namespace: http://localhost/calc.wsdl //gsoap ns service location: http://localhost/calcserver.cgi //gsoap ns schema namespace: urn:calc //gsoap ns service method: add Sums two values int ns__add(double a, double b, double &result); //gsoap ns service method: sub Subtracts two values int ns__sub(double a, double b, double &result); //gsoap ns service method: mul Multiplies two values int ns__mul(double a, double b, double &result); //gsoap ns service method: div Divides two values int ns__div(double a, double b, double &result); //gsoap ns service method: pow Raises a to b int ns__pow(double a, double b, double &result);
2.使用soapcpp2工具生成客戶端所需文件(執行命令以前先刪除上一個教程所生成的文件):web
./soapcpp2 -j -r -CL calc.h服務器
3.編寫calcclient.cpp客戶端代碼:多線程
#include "soapcalcProxy.h" #include "calc.nsmap" /* the Web service endpoint URL */ const char server[] = "http://localhost:8080"; int main(int argc, char **argv) { if (argc < 4) { fprintf(stderr, "Usage: [add|sub|mul|div|pow] num num\n"); exit(0); } calcProxy calc(server); double a, b, result; a = strtod(argv[2], NULL); b = strtod(argv[3], NULL); switch (*argv[1]) { case 'a': calc.add(a, b, result); break; case 's': calc.sub(a, b, result); break; case 'm': calc.mul(a, b, result); break; case 'd': calc.div(a, b, result); break; case 'p': calc.pow(a, b, result); break; default: fprintf(stderr, "Unknown command\n"); exit(0); } if (calc.soap->error) calc.soap_stream_fault(std::cerr); else std::cout << "result = " << result << std::endl; calc.destroy(); /* clean up */ return 0; }
4.執行編譯命令生成客戶端程序:dom
c++ -o calcclient calcclient.cpp soapC.cpp soapcalcProxy.cpp /home/webservice/gsoap-2.8/gsoap/stdsoap2.cppsocket
注: /home/webservice/gsoap-2.8/gsoap/ 是stdsoap2.cpp的具體路徑ide
5.使用soapcpp2工具生成服務端所需文件:
./soapcpp2 -j -r -SL calc.h
6.編寫calcserver.cpp服務端代碼:
#include <iostream> #include "soapcalcService.h" #include "calc.nsmap" #include "threads.h" int port = 8080; void *process_request(void *arg) { calcService *service = (calcService*)arg; THREAD_DETACH(THREAD_ID); if (service) { service->serve(); service->destroy(); /* clean up */ delete service; } return NULL; } int main() { calcService service(SOAP_IO_KEEPALIVE); /* enable HTTP kee-alive */ service.soap->send_timeout = service.soap->recv_timeout = 5; /* 5 sec socket idle timeout */ service.soap->transfer_timeout = 30; /* 30 sec message transfer timeout */ SOAP_SOCKET m = service.bind(NULL, port, 100); /* master socket */ if (soap_valid_socket(m)) { while (soap_valid_socket(service.accept())) { THREAD_TYPE tid; void *arg = (void*)service.copy(); /* use updated THREAD_CREATE from plugin/threads.h https://www.genivia.com/files/threads.zip */ if (arg) while (THREAD_CREATE(&tid, (void*(*)(void*))process_request, arg)) sleep(1); } } //service.soap_stream_fault(std::err); service.destroy(); /* clean up */ return 0; } /* service operation function */ int calcService::add(double a, double b, double &result) { result = a + b; return SOAP_OK; } /* service operation function */ int calcService::sub(double a, double b, double &result) { result = a - b; return SOAP_OK; } /* service operation function */ int calcService::mul(double a, double b, double &result) { result = a * b; return SOAP_OK; } /* service operation function */ int calcService::div(double a, double b, double &result) { if (b) result = a / b; else return soap_senderfault("Division by zero", NULL); return SOAP_OK; } /* service operation function */ int calcService::pow(double a, double b, double &result) { result = ::pow(a, b); if (soap_errno == EDOM) /* soap_errno is like errno, but portable */ return soap_senderfault("Power function domain error", NULL); return SOAP_OK; }
7.執行編譯命令生成服務端程序:
c++ -o calcserver calcserver.cpp -I/home/webservice/gsoap-2.8/gsoap -I/home/webservice/gsoap-2.8/gsoap/plugin /home/webservice/gsoap-2.8/gsoap/stdsoap2.cpp soapC.cpp soapcalcService.cpp -pthread
注:-I/home/webservice/gsoap-2.8/gsoap 是stdsoap2.h 的具體路徑 -I/home/webservice/gsoap-2.8/gsoap/plugin 是threads.h的具體路徑 /home/webservice/gsoap-2.8/gsoap 是stdsoap2.cpp的具體路徑
8.啓動服務端程序:
./calcserver
9.啓動客戶端程序:
./calcclient add 10 20
result = 30;
至此,本篇教程結束,完成了建立獨立(多線程)服務器,客戶端調用服務器的整個過程。
轉載請註明出處。