AngularJS - 与 AngularJS 模型的 SOAP 服务集成
Posted
技术标签:
【中文标题】AngularJS - 与 AngularJS 模型的 SOAP 服务集成【英文标题】:AngularJS - SOAP Service Integration With AngularJS Model 【发布时间】:2013-07-03 15:37:51 【问题描述】:我是一名经验丰富的 Flex 开发人员,正在学习 AngularJS。这太混乱了!!!
无论如何,我正在尝试通过 SOAP WSDL 请求对我的后端(在同一域上)服务器进行服务调用,并使用 AngularJS 模型对象填充数据。我正在尝试 Ajax,但在获取实际数据时遇到了一些问题。我认为我创建 SOAP 标记的方式有问题。我得到了成功的回复,但没有数据。
在搞不懂 Ajax 方法后,我偶然发现了 soapclient.js,发现它非常简单,代码比 Ajax 少。 soapclient.js 为您完成了大部分工作,类似于 Ajax 方法,这使得代码更少。此外,使用soapclient.js,我可以进行SOAP调用,还可以将数据返回到XML格式的响应中。
http://javascriptsoapclient.codeplex.com
我的问题是我正在尝试使用 AngularJS 将 XML 响应转储到 AnularJS 模型对象中。我不确定如何为我正在做的事情设置 AngularJS 项目,但我真的很想知道最好的方法,以保持我正在做的事情的解耦。我一直在疯狂地搜索 Google,但大多数示例对于初学者来说似乎过于复杂。
这是我所拥有的:
<html>
<head>
<script language="JavaScript" type="text/javascript" src="jquery-1.10.1.js"></script>
<script language="JavaScript" type="text/javascript" src="soapclient.js"></script>
<script type="text/javascript">
function getData()
var url2 = "https://myService";
var pl = new SOAPClientParameters();
pl.add("arg0", false);
SOAPClient.invoke(url2, "methodToCall", pl, true, getDataCallback);
function getDataCallback(r, soapResponse)
alert(r.contents.payeeMailName);
</script>
</head>
<body>
<form>
<input type="button" value="Click Here to Call Web Service" onClick="getData()" style="width: 192px">
</form>
<div id="result">Result?</div>
</body>
</html>
现在,SOAP 服务返回如下数据:
<return>
<contents>
<eftAcctType>S</eftAcctType>
<id>
<djNumber>201-16-39063</djNumber>
<djSequence>1</djSequence>
</id>
<payeeAddrLine1>124 Agate Drive</payeeAddrLine1>
</contents>
<contents>
<eftAcctType/>
<id>
<djNumber>201-16-39201</djNumber>
<djSequence>1</djSequence>
</id>
<payeeAddrLine1>c/o Kevin Martinez, Attorney at Law</payeeAddrLine1>
</contents>
<contents>
<eftAcctType>C</eftAcctType>
<id>
<djNumber>201-16-38561</djNumber>
<djSequence>1</djSequence>
</id>
<payeeAddrLine1>1360 South Highway 191</payeeAddrLine1>
</contents>
<status>0</status>
</return>
什么是AngularJS中进行服务调用的“正确”方式,假设我这样做的方式没问题,如果不是让我知道最好的方式,然后在结果中,我如何循环遍历数据XML 响应并将其解析为 Angular 模型对象?我最终想在 DataGrid 中使用这些数据。
任何帮助将不胜感激。
【问题讨论】:
【参考方案1】:我想最好的方法是将其实现为$http interceptor。我在我们的项目中这样做了,效果很好,因为角度 $http 调用保持不变。
这是我为我们的项目创建的提供商的链接:http://jsfiddle.net/gqp9m/ 我从soapclient 库中复制粘贴了一些内容,并将其移至提供程序中。我还更改了一些语法,因此代码将通过 jsHint。大多数修改后的功能都用文档注释进行了注释。它还需要 jQuery(对于 $.parseXML 函数 - 您可以重构它以删除 jQuery 中的依赖项)。
最大的不同是我的代码不会在第一次请求时加载 wsdl,而是需要您在进行任何调用之前对其进行缓存,如下所示:
myModule.service(['myModule.soap-interceptor', function(soap)
$http.get('http://www.myveryfakedomain.com/CRMAPIWS74?wsdl',
isJSON: true ).then(function(result)
soap.setWSDL('http:/www.myveryfakedomain.com/CRMAPIWS74', result.data);
);
]);
soap 是注入的 soap-interceptor 实例。您调用 wsdl,然后调用 soap.setWSDL,将基本 url 和解析的 wsdl 传递给它。还要注意传递给 $http 调用的 isJSON 参数。这是因为默认情况下我的代码将每个调用都视为 SOAP 请求。这就是拦截器所做的。 isJSON:true 将允许您按照上帝的意图使用 $http ;)
在调用 setWSDL 之后,只需像往常一样调用 $http:
$http.get('http:/www.myveryfakedomain.com/CRMAPIWS74/action').then(function(result)
// do something...
);
请记住,此代码是为我们的项目编写的,它不是受支持的开源项目或其他东西。在您使用它之前,它可能需要进行一定程度的维护或重构,但这是一个好的开始。
【讨论】:
谢谢。很难,但我从肥皂服务器上得到了一个 wsdl。如何在其中运行命令 getPrice()?<wsdl:message name="getPriceRequest"> <wsdl:part name="symbol" type="xsd:string"/> </wsdl:message> <wsdl:message name="getPriceResponse"> <wsdl:part name="return" type="xsd:float"/> </wsdl:message>
我不是 SOAP 专家,我更喜欢 javascript,但您通常通过引用 SOAP 服务的 url 并在末尾添加操作来调用 SOAP 操作 - 像这样:http// www.fakedomain.com/api/getPriceRequest 您使用 POST 执行此操作,并在请求正文中发送 WSDL 中描述的消息。
谢谢。如何通过 SOAP 调用传递数据?
你会碰巧有一个包含这个的小项目吗?我是 AngularJS 的新手,我是一名 Flex 开发人员......在学习 AngularJS 的同时,我试图将这一切拼凑起来。谢谢
抱歉,我的实现是特定于项目的,所以我不能给你一个通用的工作解决方案。关于soap调用中的数据,将请求作为POST发送并在$http options.data中传递soap参数【参考方案2】:
晚了两年,但我已经构建了一个 Angular 模块,专门用于在 GitHub 上使用 SOAP Web 服务。
https://github.com/andrewmcgivery/angular-soap
这是一篇关于如何使用它的博客文章: http://mcgivery.com/soap-web-services-angular-ionic/
长话短说,它允许您执行以下操作:
angular.module('myApp', ['angularSoap'])
.factory("testService", ['$soap',function($soap)
var base_url = "http://www.cooldomain.com/SoapTest/webservicedemo.asmx";
return
HelloWorld: function()
return $soap.post(base_url,"HelloWorld");
])
.controller('MainCtrl', function($scope, testService)
testService.HelloWorld().then(function(response)
$scope.response = response;
);
)
【讨论】:
这个question中的soap服务器可以工作吗? @Andrew 我在这条线上遇到错误 angular.module('myApp', ['angularSoap']) Error : Uncaught ReferenceError: angular is not defined 您是否在 Angular 脚本之后包含了 Angular 肥皂脚本? 嗨@AndrewMcGivery,有没有办法改变请求xml中的节点前缀?我需要这些前缀<SOAP-ENV:Envelope><SOAP-ENV:Body>
而不是当前由您的模块生成的 <soap:Envelope><soap:Body>
。谢谢。
@AndrewMcGivery:我正在使用crcind.com/csp/samples/SOAP.Demo.cls,但遇到了 CORS 问题。【参考方案3】:
您可以在没有任何 SOAP wsdl 库的情况下实现这一点。将您的 wsdl 导入 SOAP UI 并复制信封。下面是 AngularJS 中如何处理 SOAP Web 服务的示例。
服务:
app.service('service', function($http)
this.soapService = function(_anydata)
var _url = 'soap_service_endpoint_url';
var soapRequest = '<soapenv:Envelope xmlns:soapenv="http://schemas.xmlsoap.org/soap/envelope/" xmlns:jn=""><soapenv:Header/><soapenv:Body><=== xxx ===></soapenv:Body></soapenv:Envelope>';
var soapAction = '<=== soap action ===>';
var headers =
'SOAPAction': soapAction,
'Content-Type': 'text/xml; charset=utf-8'
;
return $http.post(_url, soapRequest,
"headers": headers
);
);
调用服务并处理 XML 输出。你可以捕获你想要的属性:
service.soapService(data).then(function success(response)
var _dataArr = [];
$(response.data).find('Transaction').each(function()
_dataArr.push(
name: $(this).find('<=== your attributes ===>').text()
);
);
return _dataArr;
, function error(response)
console.log('<==== soap error: ' + response);
return response;
);
【讨论】:
以上是关于AngularJS - 与 AngularJS 模型的 SOAP 服务集成的主要内容,如果未能解决你的问题,请参考以下文章