处理承诺例外最佳实践

时间:2016-09-02 07:50:59

标签: angularjs

我创建了一个小例子,以了解如何使用promises处理异常,特别是我使用过的MVC结构。除了3个已知组件 M odel之外,此结构使用 D ata A ccess O 对象(DAO) , V iew和 C ontroller更加独立于后端的变化。由于DAO中的转换,您可以使用不同的方法从后端检索数据。但我想这对你们来说根本没有新的概念 好吧,我想知道的是:如果MovieInfoService发生异常,代码会跳转到getMovieFailed方法并返回$q.reject(e)。但接下来会发生什么? DAO是否收到了什么以及如何处理? 我对角度中的错误和异常处理的概念非常不熟悉。因此,我不知道如何用promises处理这些问题。你们可以帮助我,并为我提供一些有用的提示,技巧或建议如何处理这些问题,以便在用户视图中显示这些问题通知他?实际上即使alert()也足够了 - 我只需要理解使用promises处理异常的基本思想/概念

以下是我的一些示例代码:

app.controller('MainController', ['$scope', 'MovieInfoDAO', function ($scope, MovieInfoDAO)
{
    var vm = this;
    vm.movie = {};

    MovieInfoDAO.getMovie()
    .then(function(data){
        vm.movie = data;
    }); 

    activate();

    //////////

    function activate() {
        return getMovieDetails().then(function(){
            console.log('Starting Movie Search');
        });
    }

    function getMovieDetails() {
        return MovieInfoDAO.getMovie().then(function(data) {
            vm.movie = data;
            return vm.movie;
        }
    }
}]);

app.service("MovieInfoDAO", ['$q', 'MovieInfoService', function($q, MovieInfoService)
{
    this.getMovie = function()
    {
        return MovieInfoService.getMovie().then(function(returnData){
            var arrInfoItems = [];
            for(var i = 0, length = returnData.length; i < length; i++){
                var item = new MovieInfoModel(returnData[i]);
                arrInfoItems.push(item);
            }
            return arrInfoItems;
        });
    };
}]);

app.service('MovieInfoService', ['$http', '$q', function($http, $q) {   

    this.getMovie = function()
    {
        return $http({
            method: "GET",
            data: { },
            url: "http://www.omdbapi.com/?t=Interstellar&y=&plot=short&r=json"
        })
        .then(getMovieCompleted);
        .catch(getMovieFailed);
    };

    function getMovieCompleted(response) {
        return response.data;
    }

    function getMovieFailed(e) {
        var newMessage = 'Failed to retrieve Infos from the Server';
        if (e.data $$ e.data.description) {
            newMessage = newMessage + '\n' + e.data.description;
        }
        e.data.description = newMessage;
        return $q.reject(e);
    }

    return this;

}]);

function MovieInfoModel(arrParameter){
    Model.call(this);

    this.title = arrParameter.Title;

    this.actors = arrParameter.Actors;

    this.plot = arrParameter.Plot;

    this.constructor(arrParameter);
}

HTML

<div>
    <h1>{{Main.movie.title}}</h1>
    <span>{{Main.movie.plot}}</span>
    <br/>
    <h3>Actors:</h3>
    <span>{{Main.movie.actors}}</span>
</div>

2 个答案:

答案 0 :(得分:2)

我总是为封装$ http服务的ajax调用创建我的服务。在这种服务中,我们可以为所有请求创建一个错误处理程序它可以创建许多错误类型并检查http响应代码,如404,500。一些简短的例子它看起来如何,我只添加了get方法:

&#13;
&#13;
var app=angular.module('app', []);

app.service('$myAjax', function($http) {
    this.get = function (url,success,error) {
        
       return $http.get(url).then(function(response){
       
         if (response.data.status===1)//status is example success code sended from server in every response
         return success(response.data);
         else{
         
            //here error handler for all requests
            console.log("Something is wrong our data has no success on true."); 
           
            //error callback
            return error(response.data);
         }
         
       },function(response){
       
         //this code will run if response has different code than 200
         //here error handler for all requests
         console.log("Something is very wrong. We have different then 200 http code"); 
         
         //error callback
         return error(response.data);
         
       });

    }
});

//TEST

app.controller("Test",function($myAjax){

  $myAjax.get('http://jsfiddle.net/echo/jsonp/',function(response){
  
    //here success
    return 1;
    
  },function(response){
  
    //here error
    return 0;
    
  }).then(function(data){

       console.log("I am next promise chain"); 
       console.log("Data from callbacks:"+data); 
  });

       
});
&#13;
<script src="https://ajax.googleapis.com/ajax/libs/angularjs/1.2.23/angular.min.js"></script>

<div ng-app="app">
  
  <div ng-controller="Test">
  </div>
</div> 
&#13;
&#13;
&#13;

当数据在1上没有status参数时,即使http代码为200,我也会显示错误,这是第二个内部错误处理主张。感谢该参数我们可以发送许多状态信息并为它们创建回调。状态2可以表示 - 没有权利,状态3 - 没有数据等。

答案 1 :(得分:1)

如果您的意图是返回arrInfoItems中的数组MovieInfoDAO.getMovie()而不是

return arrInfoItems;

使用承诺,例如

app.service("MovieInfoDAO", ['$q', 'MovieInfoService', function($q, MovieInfoService)
{
    this.getMovie = function()
    {
        var def = $q.defer();

        MovieInfoService.getMovie()
           .then(function(returnData){
               var arrInfoItems = [];
               for(var i = 0, length = returnData.length; i < length; i++){
                   var item = new MovieInfoModel(returnData[i]);
                   arrInfoItems.push(item);
               }
               def.resolve(arrInfoItems);
            }, def.reject);

        return def.promise;
    };
}]);

用法

app.controller('MainController', ['$scope', 'MovieInfoDAO', function ($scope, MovieInfoDAO)
{
    var vm = this;
    vm.movie = {};

    MovieInfoDAO.getMovie()
    .then(function(data){
        vm.movie = data;
    }, function(error){
        // Handle error here, can be placed in a vm.error variable
    }); 

}]);