首 页 | 新 闻 | Symbian | Android| Windows Mobile | J2ME | 下载中心 | 游戏策划招聘与求职 | 购书指南 | 视频教程
您现在的位置: 开发视界 >> Symbian >> Symbian入门 >> 文章正文
Symbian学习笔记(18)——初探WebServices API的使用(中)
作者:SHARE & …    文章来源:SHARE & TOP    更新时间:2008-6-19 11:00:14

继续刚才的,现在来看具体代码,先是ConnectL的实现:

void CWebEngine::ConnectL()   

   {   

CSenXmlServiceDescription* pattern = CSenXmlServiceDescription::NewLC();       

 pattern->SetFrameworkIdL(KDefaultBasicWebServicesFrameworkID);   

 pattern->SetEndPointL(KWSEndPoint);   

 delete iConnection;   

iConnection = NULL;   

iConnection = CSenServiceConnection::NewL(*this, *pattern);   

CleanupStack::PopAndDestroy(pattern);    
   }  

这里注意一点与那个AddressBook例子不同的是我们声明了不同框架类型是KDefaultBasicWebServicesFrameworkID,并且这样只需要提供EndPoint而不需要Contract了。KWSEndPoint的值是在CPP前声明了:_LIT8(KWSEndPoint,"http://192.168.0.201/uim/PService.asmx");

CSenServiceConnection::NewL的两个参数,一是自己(即MSenServiceConsumer)负责处理回调,二是一个CSenXmlServiceDescription负责参数配置。

在回调SetStatus中我只是简单地打印出状态值。

再看那个SayHello的实现吧,在这个函数中要负责封装SOAP消息包,这时我才遇到了使用Symbian的WebServiceAPI烦人的问题:原来这个SOAP包要自己封装啊!同样SOAP的结果也要自己去解析!!

void CWebEngine::SayHello()     
  {   

   if(iConnectionState==1){   

   //send    

 CSenSoapEnvelope  *env = CSenSoapEnvelope::NewL();   

 CleanupStack::PushL(env);   

  env->SetSoapActionL(KWSContract);       

  env->BodyL().AddElementL(KWSNamespace,KWSHelloworld);   

 iConnection->SendL(*env);   

 CleanupStack::PopAndDestroy(env);    
   }    

 }  

好在HelloWorld不需要参数,所以这个SOAP请求还算简单,注意这个SetSoapActionL函数它的KWSContract就是那个"urn:pservice:helloworld" (见上篇中的SOAP请求描述)。因为CSenSoapEnvelope同样派生于CSenBaseFragment ,所以它的Body也可以增加下级节点,上面的代码很好理解。

一旦调用了iConnection->SendL以后,手机会弹出选择接入点,说明这里开始连接网络了,得到结果后,我们回调HandleMessageL中处理结果。

void CWebEngine::HandleMessageL(const TDesC8& aMessage)    

 {   

RDebug::Printf("===================HandleMessageL");   

 LOG_ALL(aMessage);   

 SetReader(*iXmlReader);   

  ParseL(aMessage);   

  }  

这里我们将得到的结果(完整的SOAP响应的XML内容)交给iXmlReader去解析,于是此时又会涉及到另两个回调StartElement和EndElement。注意这里补充一下iXmlReader的初始化在WebEngine的ConstructL中完成:

void CWebEngine::ConstructL()   

 {   

  LOG_OPEN();   

   CSenBaseFragment::BaseConstructL(KQueryResponseLocalName);    

    iXmlReader = CSenXmlReader::NewL();   

    }  

两句话:一是因为自己是派生于CSenBaseFragment,所以先调用BaseConstructL构造一下自己是一个HelloWorldResponse标签的XML节点。二是构造出iXmlReader实例。

下面继续说解析XML的回调处理:

void CWebEngine::StartElementL(const TDesC8& aNsUri,    const TDesC8& aLocalName,   const TDesC8& aQName, const Xml::RAttributeArray& aAttrs)     

{     

RDebug::Printf("================StartElement");       

_LIT(KFmt,"StartElement (%s)");     

LOG_FORMAT((KFmt,aLocalName));   

if(aLocalName==KQueryResponseLocalName){   

delegate = CHelloWorldResult::NewL(aNsUri,aLocalName,aQName);     

CleanupStack::PushL(delegate);     

DelegateParsingL(*delegate);   

CleanupStack::Pop(delegate);     

}     

}     

void CWebEngine::EndElementL(const TDesC8& aNsUri,  const TDesC8& aLocalName, const TDesC8& aQName)     

 {     

RDebug::Printf("==================EndElement");    

_LIT(KFmt,"EndElement (%s)");     

LOG_FORMAT((KFmt,aLocalName));    

CSenBaseFragment::EndElementL(aNsUri, aLocalName, aQName);     

 }  

这个EndElement没啥好说的,就是调一下老子的EndElement罢了。倒是那个StartElement函数它在遇到HelloWorldResponse标签时会交给delegate去处理下级节点,就是说<HelloWorldResponse>以下的XML内容由CHelloWorldResult类的负责处理了。

相关文章:
Symbian学习笔记(21)——原来还有这个工具wsdl2cpp,访问webservice也很简单
Symbian学习笔记(20)——用gSOAP更简单地实现Web Services Client
Symbian学习笔记(19)——初探WebServices API的使用(下)
Symbian学习笔记(17)——初探WebServices API的使用(上)
Symbian学习笔记(16)——解析XML文件(下)
Symbian学习笔记(15)——解析XML文件(上)
Symbian学习笔记(14)——使用Browser Control API
Symbian学习笔记(13)——让程序随系统启动的尝试