최근에 내가 여기 에서 직면하고있는 문제에 대한 자세한 설명을 게시했습니다 . 실제 $http
요청을 보낼 수 없으므로 시간 초과를 사용하여 비동기 동작을 시뮬레이션했습니다. @Gloopy의 도움으로 모델에서보기로 데이터 바인딩이 올바르게 작동합니다.
이제 (로컬에서 테스트 됨) $http
대신 사용 $timeout
하면 비동기 요청이 성공했으며 data
서비스에서 json 응답으로 채워졌습니다. 그러나 내 견해는 업데이트되지 않습니다.
Plunkr 업데이트 여기
답변
원하는 것을 수행하는 Plunk는 다음과 같습니다. http://plnkr.co/edit/TTlbSv?p=preview
아이디어는 약속과 직접 “그런 다음”기능을 사용하여 비동기 적으로 리턴 된 응답을 조작하고 액세스하는 것입니다.
app.factory('myService', function($http) {
var myService = {
async: function() {
// $http returns a promise, which has a then function, which also returns a promise
var promise = $http.get('test.json').then(function (response) {
// The then function here is an opportunity to modify the response
console.log(response);
// The return value gets picked up by the then in the controller.
return response.data;
});
// Return the promise to the controller
return promise;
}
};
return myService;
});
app.controller('MainCtrl', function( myService,$scope) {
// Call the async method and then do stuff with what is returned inside our own then function
myService.async().then(function(d) {
$scope.data = d;
});
});
다음은 요청을 캐시하는 약간 더 복잡한 버전이므로 처음으로 만 만드십시오 ( http://plnkr.co/edit/2yH1F4IMZlMS8QsV9rHv?p=preview ).
app.factory('myService', function($http) {
var promise;
var myService = {
async: function() {
if ( !promise ) {
// $http returns a promise, which has a then function, which also returns a promise
promise = $http.get('test.json').then(function (response) {
// The then function here is an opportunity to modify the response
console.log(response);
// The return value gets picked up by the then in the controller.
return response.data;
});
}
// Return the promise to the controller
return promise;
}
};
return myService;
});
app.controller('MainCtrl', function( myService,$scope) {
$scope.clearData = function() {
$scope.data = {};
};
$scope.getData = function() {
// Call the async method and then do stuff with what is returned inside our own then function
myService.async().then(function(d) {
$scope.data = d;
});
};
});
답변
간단하게하자. 그것은 간단합니다
promise
서비스 반품 (서비스에서 사용할 필요 없음then
)then
컨트롤러에서 사용
데모. http://plnkr.co/edit/cbdG5p?p=preview
var app = angular.module('plunker', []);
app.factory('myService', function($http) {
return {
async: function() {
return $http.get('test.json'); //1. this returns promise
}
};
});
app.controller('MainCtrl', function( myService,$scope) {
myService.async().then(function(d) { //2. so you can use .then()
$scope.data = d;
});
});
답변
비동기식이므로 $scope
ajax 호출이 완료되기 전에 데이터를 가져옵니다.
당신은 사용할 수 있습니다 $q
생성 서비스에 promise
다시 컨트롤러를주고, 컨트롤러는 내 결과를 얻을 수 then()
에 대한 호출 promise
.
당신의 봉사에서
app.factory('myService', function($http, $q) {
var deffered = $q.defer();
var data = [];
var myService = {};
myService.async = function() {
$http.get('test.json')
.success(function (d) {
data = d;
console.log(d);
deffered.resolve();
});
return deffered.promise;
};
myService.data = function() { return data; };
return myService;
});
그런 다음 컨트롤러에서 :
app.controller('MainCtrl', function( myService,$scope) {
myService.async().then(function() {
$scope.data = myService.data();
});
});
답변
tosh shimayama는 해결책이 있지만 $ http가 약속을 반환하고 약속이 가치를 반환 할 수 있다는 사실을 사용하면 단순화 할 수 있습니다.
app.factory('myService', function($http, $q) {
myService.async = function() {
return $http.get('test.json')
.then(function (response) {
var data = reponse.data;
console.log(data);
return data;
});
};
return myService;
});
app.controller('MainCtrl', function( myService,$scope) {
$scope.asyncData = myService.async();
$scope.$watch('asyncData', function(asyncData) {
if(angular.isDefined(asyncData)) {
// Do something with the returned data, angular handle promises fine, you don't have to reassign the value to the scope if you just want to use it with angular directives
}
});
});
커피 스크립트의 작은 데모 : http://plunker.no.de/edit/ksnErx?live=preview
귀하의 plunker가 내 방법으로 업데이트되었습니다 : http://plnkr.co/edit/mwSZGK?p=preview
답변
내가 생각하는 훨씬 더 좋은 방법은 다음과 같습니다.
서비스:
app.service('FruitsManager',function($q){
function getAllFruits(){
var deferred = $q.defer();
...
// somewhere here use: deferred.resolve(awesomeFruits);
...
return deferred.promise;
}
return{
getAllFruits:getAllFruits
}
});
컨트롤러에서 간단히 사용할 수 있습니다.
$scope.fruits = FruitsManager.getAllFruits();
Angular는 자동으로 해결 된 것을에 awesomeFruits
넣습니다 $scope.fruits
.
답변
나는 같은 문제가 있었지만 인터넷에서 서핑을 할 때 $ http가 기본적으로 약속을 되찾았다는 것을 이해했다. 그리고 나서 “data”를 반환 한 후 “then”으로 사용할 수있다. 코드를보십시오 :
app.service('myService', function($http) {
this.getData = function(){
var myResponseData = $http.get('test.json').then(function (response) {
console.log(response);.
return response.data;
});
return myResponseData;
}
});
app.controller('MainCtrl', function( myService, $scope) {
// Call the getData and set the response "data" in your scope.
myService.getData.then(function(myReponseData) {
$scope.data = myReponseData;
});
});
답변
UI를 배열에 바인딩 할 때 길이를 0으로 설정하고 데이터를 배열로 푸시하여 동일한 배열을 직접 업데이트해야합니다.
이 대신 ( data
UI가 알지 못하는 다른 배열 참조를 설정 ) :
myService.async = function() {
$http.get('test.json')
.success(function (d) {
data = d;
});
};
이 시도:
myService.async = function() {
$http.get('test.json')
.success(function (d) {
data.length = 0;
for(var i = 0; i < d.length; i++){
data.push(d[i]);
}
});
};
다음은 새 배열 설정과 비우기 및 기존 배열 추가의 차이점을 보여주는 바이올린 입니다. 나는 당신의 plnkr을 작동시킬 수 없었지만 희망적으로 이것은 당신을 위해 작동합니다!