我是Angularjs的新手并尝试创建一个远程服务(位于" http://dev.testmyserver2"),以便在各种应用程序中使用(位于" http://dev.testmyserver &#34)
。此服务使用Colfusion和Oracle数据库检索有关用户的各种数据。当我直接在浏览器中启动应用程序时,它非常有效。然而,当我试图从另一个应用程序调用此服务的功能(在工厂中定义)时(由于在此应用程序的主模块中调用的依赖项),http GET在OPTIONS中被修改(在firebug中可见)而我不能检索数据(http请求的状态代码为O)。正确调用该函数(警报"函数正确调用"或者正确调用此函数的console.log),但没有检索到该人的数据。
我认为它是跨域问题。但我不知道如何解决它。
这里有一些代码:
远程服务,包含从数据库中检索数据的功能:
MODULE - appRemoteService.js:
var app=angular.module('RemoteService', ['ngRoute', 'ui.bootstrap']);
app.config(function($routeProvider, $httpProvider, ngDialogProvider){
// disable IE ajax request caching
$httpProvider.defaults.cache = false;
if (!$httpProvider.defaults.headers.get) {
$httpProvider.defaults.headers.get = {};
}
$httpProvider.defaults.headers.get['If-Modified-Since'] = '0';
// Create the routes
$routeProvider.when('/home',
{
templateUrl: 'template/allPersons.html',
controller: 'ctrlPersons'
})
.when('/documentation',
{
templateUrl: 'template/documentation.html',
controller: 'ctrlDocumentation'
})
.otherwise({redirectTo:'/home'});
});
app.controller('ctrlPersons', function ($scope, FactoryRemoteService){
FactoryRemoteService.getUserFromLogin("test").success(function(personInfo){
alert(personInfo["VALUES"][0]["FIRSTNAME"]);
});
});
FACTORY - appFactoryRemoteService.js:
app.factory('FactoryRemoteService', function($http){
var factory={};
factory.getUserFromLogin=function(uid){
Alert("Function correctly called");
return $http.get('http://dev.testmyserver2/myapp.cfc?method=getUserFromLogin&login=' + uid);
};
return factory;
})
我的申请:
MAIN FILE - index.html:
<title>My app</title>
<link rel="stylesheet" href="lib/css/bootstrap-3.1.1/css/bootstrap.min.css">
<link rel="stylesheet" href="lib/css/bootstrap-3.1.1/css/bootstrap-theme.min.css">
<link rel="stylesheet" href="css/styles.css" rel="stylesheet">
<link rel="stylesheet" href="css/select.css" rel="stylesheet">
</head>
<body>
<div class="container">
<div class="spacer navbar">
<h1 class="nav nav-pills navbar-left">MY APP</h1>
<ul class="nav nav-pills navbar-right" data-ng-controller="NavbarController">
<li data-ng-class="{'active':getClass('/all-contacts')}"><a href="#/all-contacts">All contacts</a></li>
<li data-ng-class="{'active':getClass('/add-contacts')}"><a href="#/add-contacts">Add contacts</a></li>
</ul>
</div>
<ng-view></ng-view>
</div>
<script src="lib/js/angular.min.js"></script>
<script src="lib/js/angular-route.min.js"></script>
<script src="lib/js/angular-sanitize.min.js"></script>
<script src="lib/js/bootstrap.min.js"></script>
<script src="lib/js/jquery.min.js"></script>
<script src="lib/js/ui-bootstrap-tpls-0.11.0.min.js"></script>
<script src="app/app.js"></script>
<script src="app/appService.js"></script>
<script src="http://dev.testmyserver2/app/appRemoteService.js"></script>
<script src="http://dev.testmyserver2/app/appFactoryRemoteService.js"></script>
</body>
MODULE - app.js:
var app=angular.module('ContactsApp', ['ngRoute', 'ui.bootstrap', 'RemoteService']);
// register the interceptor as a service
app.factory('HttpInterceptor', ['$q', '$rootScope', function($q, $rootScope) {
return {
// On request success
request : function(config) {
// Return the config or wrap it in a promise if blank.
return config || $q.when(config);
},
// On request failure
requestError : function(rejection) {
//console.log(rejection); // Contains the data about the error on the request.
// Return the promise rejection.
return $q.reject(rejection);
},
// On response success
response : function(response) {
//console.log(response); // Contains the data from the response.
// Return the response or promise.
return response || $q.when(response);
},
// On response failure
responseError : function(rejection) {
//console.log(rejection); // Contains the data about the error.
//Check whether the intercept param is set in the config array.
//If the intercept param is missing or set to true, we display a modal containing the error
if (typeof rejection.config.intercept === 'undefined' || rejection.config.intercept)
{
//emitting an event to draw a modal using angular bootstrap
$rootScope.$emit('errorModal', rejection.data);
}
// Return the promise rejection.
return $q.reject(rejection);
}
};
}]);
app.config(function($routeProvider, $httpProvider){
// disable IE ajax request caching
$httpProvider.defaults.cache = false;
if (!$httpProvider.defaults.headers.get) {
$httpProvider.defaults.headers.get = {};
}
$httpProvider.defaults.headers.get['If-Modified-Since'] = '0';
// Add the interceptor to the $httpProvider to intercept http calls
$httpProvider.interceptors.push('HttpInterceptor');
$routeProvider.when('/all-contacts',
{
templateUrl: 'template/allContacts.html',
controller: 'ctrlContacts'
})
.when('/view-contacts/:contactId',
{
templateUrl: 'template/viewContact.html',
controller: 'ctrlViewContacts'
})
.otherwise({redirectTo:'/all-contacts'});
});
app.controller('NavbarController', function($scope, $location){
$scope.getClass=function(path){
if($location.path().substr(0,path.length) == path){
return true;
}else{
return false;
}
}
});
app.controller('ctrlViewContacts', function ($scope, $routeParams, RemoteServiceFactory){
$scope.contact = null;
// CALL OF THE REMOTE SERVICE
RemoteServiceFactory.getUserFromLogin("test")
.success(function(personInfo){
alert(personInfo["VALUES"][0]["FIRSTNAME"]);
})
.error(function(personInfo, status){
alert(status);
});
});
在各种论坛上进行了几次搜索后,我测试了一些解决方案,但问题始终存在。
例如我试图添加:
//Enable cross domain calls
$httpProvider.defaults.useXDomain = true;
//Remove the header used to identify ajax call that would prevent CORS from working
delete $httpProvider.defaults.headers.common['X-Requested-With'];
或者
//Reset headers to avoid OPTIONS request (aka preflight)
$httpProvider.defaults.headers.common = {};
$httpProvider.defaults.headers.post = {};
$httpProvider.defaults.headers.put = {};
$httpProvider.defaults.headers.patch = {};
您能帮我找一个解决方案来解决这个问题吗?
非常感谢您的回复
答案 0 :(得分:0)
对于遇到相同问题的人,我使用XDomain第三方库找到了解决方案。您必须在服务所在的远程服务器上实现proxy.html文件,并在主应用程序的脚本标记中调用该文件。