SOAP Client: Using SOAP Toolkit 3.0






3.26/5 (16 votes)
Nov 3, 2003

252121

2929
A SOAP client, using SOAP Toolkit 3.0.
Introduction
This article describes a project that provides a SOAP Client using SOAP Toolkit 3.0. It can be altered to use with SOAP Toolkit 2.0.
Using the code
The project is a Win32 console application. The user needs to change the method name as well as the path of the WSDL file.
Requirements
- SOAP Toolkit 2.0 or 3.0
- MSXML 4.0
Instructions to download as well as install these are present in the MSDN website.
//Code HRESULT hRes = CoInitialize(NULL); ///////////////////NEW VERSION CString csMethodName="MEthodName"; //OLECHAR FAR* fszMemberFunc[] = {L"MethodName"}; //Name of method being called LPOLESTR fszMemberFunc; IDispatch FAR* pdisp; //Pointer to IDispatch object DISPID dispid; //ID of method unsigned int uArgErr = 0; DISPPARAMS dispparams; //Parameter workarea EXCEPINFO excepinfo; //Exception Information HRESULT hresult; //return value, system functions VARIANT returnval; //return value(s) from server being called CString CEMessage; _bstr_t bstrWSDLFile (_T("http://xxx.xxx.xxx.xx/abcd/xyz/asaffsf.WSDL")); BSTR xmlInput; CString tempValue= "<TEST>Hi there</TEST>"; xmlInput= tempValue.AllocSysString(); dispparams.rgvarg = NULL; // CComPtr<ISOAPClient> m_ptrSoapClient; CComPtr<ISoapClient> m_ptrSoapClient;//For SOAPTOOLKIT 3.0 try { hresult = AnsiToUnicode(csMethodName,&fszMemberFunc); if(S_OK!=hresult) { CEMessage.Format("Unable to execute AnsiToUnicode" " for ProgID %s, with Error : %d", csMethodName, hresult); throw (CEMessage); //error converting the method anme } hresult=-1; //For SOAPTOOLKIT 2.0 // hresult = m_ptrSoapClient.CoCreateInstance(__uuidof(SoapClient)); //For SOAPTOOLKIT 3.0 hresult = m_ptrSoapClient.CoCreateInstance(__uuidof(SoapClient30)); if (S_OK != hresult) { CEMessage.Format("CoCreateInstance failed for" " SOAP CLIENT with the Error : %d", hresult); throw (CEMessage); //error creating an instance } _bstr_t tmp(_T("")); hresult=-1; hresult = m_ptrSoapClient->MSSoapInit(bstrWSDLFile, "","","");//For SOAPTOOLKIT 3.0 // hresult = m_ptrSoapClient->mssoapinit(bstrWSDLFile, "","","");//For SOAPTOOLKIT 2.0 if (S_OK != hresult) { CEMessage.Format("Initialization failed" " for SOAP Client with Error : %d", hresult); throw (CEMessage); }//Falied to inialize // GetID of Member Function Being called hresult = -1; hresult = m_ptrSoapClient->GetIDsOfNames(IID_NULL, &fszMemberFunc, 1, LOCALE_SYSTEM_DEFAULT, &dispid); if (S_OK != hresult) { CEMessage.Format("GetIDsOfNames failed for" " ProgID SoapClient, Function Name %s, with Error : %d", fszMemberFunc,hresult); throw (CEMessage); } //Now setup arguments for transfer to server dispparams.rgvarg = new VARIANTARG[1]; if (NULL == dispparams.rgvarg) throw ("Unable to allocate from the heap"); dispparams.cArgs = 1; dispparams.cNamedArgs = 0; dispparams.rgdispidNamedArgs = NULL; dispparams.rgvarg[0].vt = VT_BYREF|VT_BSTR; dispparams.rgvarg[0].pbstrVal = &xmlInput; //Setup initial conditions and Invoke Call VariantInit(&returnval); excepinfo.wCode = 0; excepinfo.bstrSource = NULL; excepinfo.bstrDescription = NULL; excepinfo.bstrHelpFile = NULL; hresult = -1; hresult = m_ptrSoapClient->Invoke(dispid, IID_NULL, LOCALE_USER_DEFAULT, DISPATCH_METHOD, &dispparams, &returnval, &excepinfo, &uArgErr); if (S_OK != hresult) { if (DISP_E_EXCEPTION == hresult) { char src[256]; char dsc[256]; DWORD iLengthS = SysStringByteLen (excepinfo.bstrSource); DWORD iLengthD = SysStringByteLen (excepinfo.bstrDescription); WideCharToMultiByte(CP_ACP, NULL, excepinfo.bstrSource,iLengthS, src, sizeof(src), NULL, NULL); WideCharToMultiByte(CP_ACP, NULL, excepinfo.bstrDescription,iLengthD, dsc, sizeof(dsc), NULL, NULL); CEMessage.Format("exceptinfo: bstrSource '%s', bstrDescription '%s', wCode '%d'", src, dsc, excepinfo.wCode); // } bstr_t faultString=m_ptrSoapClient->GetFaultString(); CString tempFaultString=(LPCSTR)faultString; bstr_t detail=m_ptrSoapClient->GetDetail(); CString tempfaultdetail=(LPCSTR) detail; CEMessage.Format("IDispatch.Invoke() failed for" " ProgID SoapClient, Function Name %s with HRESULT" " %d FaultString %s and FaltDetails %s", csMethodName,hresult,tempFaultString,tempfaultdetail); throw (CEMessage); } CString temp= returnval.bstrVal;//temp has the results SysFreeString(xmlInput);; } catch (CString& csMsg) { SysFreeString(xmlInput); } catch (CException* pException) { SysFreeString(xmlInput); char msg[256]; pException->GetErrorMessage(msg,sizeof(msg),NULL); delete pException; } catch (...) { SysFreeString(xmlInput); } if (m_ptrSoapClient) { m_ptrSoapClient.Release(); pdisp = NULL; } if (NULL != dispparams.rgvarg) delete [] dispparams.rgvarg; CoUninitialize(); //
Points of interest
Couple of points which are worth mentioning:
- In case the user encounters this error:
exceptinfo: bstrSource 'Connector', bstrDescription 'Connector:Connection time out. HRESULT=0x800A1527 - Client:An unanticipated error occurred during the processing of this request. HRESULT=0x800A1527 - Client:Sending the Soap message failed or no recognizable response was received HRESULT=0x800A1527 - ClieConnector', wCode '0'
Bump up the timeout. It might fix it.
- If WinINET connector to be used instead of WinHTTP, rename/delete whsc30.dll under program files\common files\MSSoap\Binaries.