Angular JS服务依赖注入错误

时间:2015-06-10 17:14:32

标签: angularjs angularjs-directive angular-promise angular-resource angular-services

我是角色的新手我一直在尝试对用户名可用性进行异步验证,而我正在进行"无法读取属性' userName'未定义" 这是我的服务代码

webAppServices.factory('services', ['$resource',
function ($resource){
    return{
        users: $resource('http://localhost:8080/api/users',{},{
            get:{method:'GET',isArray:true},
            add:{method:'POST',isArray:false},
            update:{method:'POST',isArray:false}
        }),

       userName:$resource('http://localhost:8080/api/users/check/:username',{},{
            check:{method:'GET',isArray:false}
        })
    };}]);

这是我的指令代码,它传递用于验证的用户名

webAppValidation.directive('checkUsername', ['services',
function ($q, services) {
    return {
        require: "ngModel",
        link: function (scope, elm, attrs, ctrl) {
            ctrl.$asyncValidators.checkUsername = function(modelValue, viewValue){
               //check username
                return ctrl.$isEmpty(modelValue) || services.userName.check({username:modelValue}).
                        then(function resolved(){
                            //username exists, this means validation fails
                            return $q.reject('exists');
                        }, function rejected(){
                            //username does not exists, therefore this validation passes
                            return true;
                        });
            };
        }
    };
}]);

这就是我在Console中获得的内容

TypeError: Cannot read property 'userName' of undefined
at link.ctrl.$asyncValidators.checkUsername (validations.js:56)
at angular.js:24723
at forEach (angular.js:350)
at processAsyncValidators (angular.js:24722)
at NgModelController.$$runValidators (angular.js:24681)
at NgModelController.$$parseAndValidate (angular.js:24819)
at NgModelController.$commitViewValue (angular.js:24787)
at angular.js:24920
at Scope.$get.Scope.$eval (angular.js:15719)
at Scope.$get.Scope.$apply (angular.js:15818)

3 个答案:

答案 0 :(得分:3)

您没有注入webAppValidation.directive('checkUsername', ['$q','services', ... 服务。

webAppServices.factory('usersService', ['$q','$http',

  var endPoint = 'http://localhost:8080/api/user';

  function ($q, $http){
    var _getUsers = function(){
       var deffered = $q.defer();

       $http.get(endpoint)
            .then(
              function(data){ deffered.resolve(data);}),
              function(data){ deffered.reject(data);})
            ).catch(function(error){  $q.reject(error);});

       deffered.promise;

 }
 //...
 //the other methods
 //...
    return{
       getUsers: _getUsers
       //...
    }
;}]);

我会像这样写

$http

虽然$q会返回一个承诺,但最好还是使用then ... undefined返回一个可以遵循承诺规范的对象,这样您的服务用户就不会看到$(".class").style.backgroundPosition = "0px " + (0 - (Math.max(document.documentElement.scrollTop, document.body.scrollTop) / 4)) + "px";

答案 1 :(得分:2)

你的webservice应该公开这些函数,它应该返回将返回一个promise的$resource对象。对于再保险承诺,您需要使用$resource.$promise,以便承诺链将继续。

<强>服务

webAppServices.factory('services', ['$resource',
    function($resource) {
        return {
            users: function() {
                return $resource('http://localhost:8080/api/users', {}, {
                    get: {
                        method: 'GET',
                        isArray: true
                    },
                    add: {
                        method: 'POST',
                        isArray: false
                    },
                    update: {
                        method: 'POST',
                        isArray: false
                    }
                }).$promise; //returning promise
            },

            userName: function() {
                return $resource('http://localhost:8080/api/users/check/:username', {}, {
                    check: {
                        method: 'GET',
                        isArray: false
                    }
                }).$promise; //returning promise
            }
        };
    }
]);

然后在您的服务中注入丢失的$q

webAppValidation.directive('checkUsername', ['$q', 'services',
function ($q, services) {

答案 2 :(得分:0)

感谢您的帮助,它现在正在工作, 我必须在我的验证指令

中注入'$ q'并添加$ promise
webAppValidation.directive('checkUsername', ['$q','services',
function ($q, services) {
    return {
        require: "ngModel",
        link: function (scope, elm, attrs, ctrl) {
            ctrl.$asyncValidators.checkUsername = function(modelValue, viewValue){
               //check username
                return ctrl.$isEmpty(modelValue) || services.userName.check({username:modelValue}).
                        $promise.then(function resolved(){
                            //username exists, this means validation fails
                            return $q.reject('exists');
                        }, function rejected(){
                            //username does not exists, therefore this validation passes
                            return true;
                        });
            };
        }
    };
}]);