2016-02-23 33 views
-1

我已经阅读了How do I return the response from an asynchronous call?这个问题的答案但是我不确定我是否理解,我认为我的问题有点不同。我改变我的服务是这样的:如何在angularjs服务中返回异步调用的响应?

.service('CommonService',['$firebase', function($firebase){ 

var username; 

function onComplete(result){ 
    username = result; 
}; 

var getData = function(){ 

    var ref = new Firebase("https://instafame.firebaseio.com"); 

    ref.onAuth(function(authData){ 
     var userid = authData.uid; 
     console.log(userid); 

     var newref = new Firebase("https://instafame.firebaseio.com/users/" + userid) 

     newref.once("value", function(snapshot) { 
      var data = snapshot.val() 
      newUsername = data.username; 
      callback(newUsername); 

     }) 
    }); 
    }; 

    return{ 
     getUsername: function(){ 
      getData(onComplete); 
      return username;} 
    }; 
}]) 

在我的控制器I存储变量userCommonService的回报:

var user = CommonService.getUsername(); 
console.log(user); 

的问题是,控制台仍返回“未定义” 。我试图根据这些建议更改代码,但它没有运行。我该怎么办?

在此先感谢

+1

你有所有这些回调,试图完成不可能的事情。 –

+2

使'getData'和'getUsername'返回一个承诺,而不是回调。 – Bergi

+0

@Bergi我很无知,你可以在代码中更明确吗? – Radames

回答

1

异步/等待

我们需要提供一种方式来等待您的请求作出回应。我们可以使用async/await来做到这一点,并让我们做出承诺,以解决我们正在检索的价值;

.service('CommonService',['$firebase', function($firebase){ 

var username; 
var getData = function(){  //declare this function as an async 

    return new Promise((resolve, reject) => { 

     var ref = new Firebase("https://instafame.firebaseio.com"); 

     ref.onAuth(function(authData){ 
      var userid = authData.uid; 
      console.log(userid); 

      var newref = new Firebase("https://instafame.firebaseio.com/users/" + userid) 

      newref.once("value", function(snapshot) { 
       var data = snapshot.val() 
       newUsername = data.username; 
       !!newUsername 
        ? 
       resolve(newUsername) 
        : 
       reject('Error: No username found'); 
      }) 

     }); 
    }; 
}; 

    return{ 
     getUsername: async function(){ 
      username = await getData(); //await will pause execution of the code here until getData() returns a value. 
      return username; 
     } 
    }; 
}]) 
+0

你不需要声明'getData'为'async' - 它已经明确地返回一个新的Promise - 但是你需要在使用'await'的'getUsername'函数中这样做,以便它返回一个promise好。 – Bergi

+0

当前,如果不首先声明包含函数作为异步函数,我们不能使用await。这可能会在即将到来的ECMA更新中发生变化,但在此之前,我们需要等待异步。 也可以将getUsername方法缩短为 'getUsername:function(){ return await getData(); }' – Rex

+0

是的,正好。而你的代码不遵循这些规则 - 包含'await'的函数没有声明'async' – Bergi