Javascript angularjs.then()不';t工作(然后不是一个函数)

Javascript angularjs.then()不';t工作(然后不是一个函数),javascript,angularjs,service,factory,Javascript,Angularjs,Service,Factory,我在使用AngularJS(v1.3.15)和AngularRoute为游戏想法开发一个简单的GUI时遇到了一个小问题。 无论如何,对于注册,我想在输入用户名时预先检查用户名的可用性。我设置了一个$watch,调用工厂服务以获得$http.post答案,但在我的控制器中,我得到了错误“fwMainService.checkusernameavability(…)。then不是一个函数”。 我检查了每一个拼写,语法和逻辑(顺便说一句,我是新来的)。 其他所有工厂功能都按预期工作 是因为checkU

我在使用AngularJS(v1.3.15)和AngularRoute为游戏想法开发一个简单的GUI时遇到了一个小问题。 无论如何,对于注册,我想在输入用户名时预先检查用户名的可用性。我设置了一个$watch,调用工厂服务以获得$http.post答案,但在我的控制器中,我得到了错误“fwMainService.checkusernameavability(…)。then不是一个函数”。 我检查了每一个拼写,语法和逻辑(顺便说一句,我是新来的)。 其他所有工厂功能都按预期工作

是因为checkUsernameAvailability()应该返回承诺,而不是字符串吗

有什么想法吗?提前谢谢

我的工厂:

"use strict";

fwApp.factory('fwMainService', function ($http) {

var mFac = {};

mFac.checkUsernameAvailability = function (username) {
    if(username != '') {
        if(username.length >= 3) {
            $http.post('api/user/usernameInUse.php', {newUser: username})
            /* returns '1' if in use, '0' if free */
            .success(function (res) {
                if(res == '1') { // Username in use
                    return 'In Use!';
                } else if(res == '0') {
                    return 'Free!';
                }
            })
            .error(function (error) {
                console.log("username check error: ", error);
            });
        } else {
            return 'Username too short!';
        }
    } else {
        return ''; // if empty, do not check
    }
};

[...]

// Public API
return {
    checkUsernameAvailability: function (username) {
        return mFac.checkUsernameAvailability(username);
},
[...]
我的控制器:

"use strict";    

fwApp.controller('IndexCtrl', 
         ['$scope', '$http', '$timeout', '$location', 'fwMainService', 
function ( $scope,   $http,   $timeout,   $location,   fwMainService) {

/* username input field model = newUser.username */
$scope.$watch("newUser.username", function (newValue, oldValue) {
    if(angular.equals(newValue, oldValue)) {
        return;
    }
    fwMainService.checkUsernameAvailability(newValue).then(function (res) {
        console.log("return", res.data);
        $scope.newUserMsg = res.data; // Setting infobox to "Free!" or "In Use!"
    }, function (error) {
        console.log("username check Error:", error);
    });

});

[...]
编辑#1:我添加了一个JSFIDLE:
也许有人让它工作起来了……

JSFIDLE需要一些调整才能工作,但一般来说,您需要做的是:

  • 在mFac.checkUsernameAvailability函数中,需要返回$http.post()结果
  • 你需要向工厂注入$q
  • 不返回res.data,只返回res
  • 在所有返回字符串的情况下,返回$q.when(str)(其中str是字符串)。这将确保函数的所有存在路径都返回一个承诺(然后在所有情况下都可以调用)

尝试此返回检查UsernameAvailability(用户名);在您的工厂更换退货mFac.checkUsernameAvailability(用户名);通过返回检查UsernameAvailability(用户名);(我不确定这个解决方案,但你可以尝试)否定,我得到错误:checkUsernameAvailability没有定义,thx Though你能做一个代码笔吗,所以我可以尝试帮助你:)请原谅我的无知,但什么是代码笔?像plunker或JSFIDLE这样的东西?为什么需要注入$q?我没有在函数中使用多个$http请求,因此您可以使用$q.when()将返回的字符串包装成承诺。我在您的基础上创建了一个工作的JSFIDLE:据我所知,工厂函数必须返回一个承诺,对吗?因此,如果它应该返回一个字符串,那么必须使用$q.when()将该字符串转换为承诺,对吗?