AngularJS:在控制器中注入工厂时,工厂始终未定义

3

我正在尝试一个地址簿Angular应用程序的简单示例。我有一个工厂返回一组记录,它在列表视图中使用List控制器显示。

angular.module('abModule', ['ngRoute'])
.factory('AddressBook', function() {
    var address_book = [
        {
            "id": 1,
            "first_name": "John",
            "last_name": "Doe",
            "age": 29
        },
        {
            "id": 2,
            "first_name": "Anna",
            "last_name": " Smith",
            "age": 24
        },
        {
            "id": 3,
            "first_name": "Peter",
            "last_name": " Jones",
            "age": 39
        }
    ];
    alert('inside factory function');
    return {
        get: function() {
            return address_book
        }
    };
})
.config(function($routeProvider) {
    $routeProvider
    .when('/', {
        controller:'list_controller',
        templateUrl:'list.html'
    })
    .when('/add', {
        controller:'add_controller',
        templateUrl:'add.html'
    })
    .otherwise({
        redirectTo:'/'
    });          
})
.controller('list_controller',['$scope', function ($scope, AddressBook) {
    $scope.address_book = AddressBook;
}])
.controller('add_controller',['$scope', function ($scope,AddressBook) {
    //$scope.entry = {};
    $scope.save = function() {
        AddressBook.set(
            {
                "id": $scope.address_book.length +1,
                "first_name":$scope.entry.firt_name,
                "last_name":$scope.entry.last_name,
                "age":$scope.entry.age
            }
        );
    };
}]);

'list_controller' 中的 'AddressBook' 总是未定义。你有什么想法是哪里出了问题吗?非常感谢您的任何帮助。


你的地址簿没有设置函数。 - Narek Mamikonyan
3个回答

7

您没有为 DI 注释 AddressBook

.controller('list_controller',['$scope', function ($scope, AddressBook) {
    $scope.address_book = AddressBook;
}])

should be:

.controller('list_controller',['$scope', 'AddressBook', function ($scope, AddressBook) {
    $scope.address_book = AddressBook;
}])

同样适用于另一个控制器。

2
另一种方法是使用$inject声明您的依赖项,这些依赖项按照与函数参数相同的顺序使用,如下所示。它有助于在代码缩小后注入正确的服务。
var App = angular.module('myApp',[]);
App.controller('myCtrl',myCtrl);

//inject your dependencies;
myCtrl.$inject = ["$scope", "AddressBook","anotherService"] // 

function myCtrl($scope,AddressBook,anotherService){
.....
}

注意:服务名称在缩小后将被重命名,可能会导致您的应用程序出现故障。

这帮助我找到了我的问题。我的 $inject 看起来像 PostsController.$inject = [ 'postsService', logger ]; 其中 'logger' 没有被定义。事实证明,排除引号也会引发 ReferenceError。 - Matt Wagner

2

在工厂变量中始终得到未定义的另一个可能原因是将声明的依赖项错误地映射到函数参数列表。例如:

var loginCtrl = loginModule.controller("loginController", 
    ['$scope', '$window', 'notificationMessage',
    function ($scope, $window, serverDataConvertor, notificationMessage) {

    // notificationMessage is undefined because serverDataConvertor factory is not a declared dependency

    // controller logic comes here
}

不幸的是,Angular没有发出任何警告或错误,这可能非常令人沮丧,特别是当依赖列表很长时。


谢谢你。我刚刚浪费了20分钟的时间感到沮丧,而这篇文章帮助了我。 - Hen
@HenryLin - 是的,我也遇到了同样的问题,所以我想提供这个答案。幸运的是,在后续版本(Angular 2、Angular 4)中,依赖声明已经得到了改进。 - Alexei - check Codidact
我大约一个月前刚开始在一家小公司工作。他们正在使用AngularJS。然而,他们没有任何升级计划。我意识到,当AngularJS在未来几年失去支持时,这可能会成为问题。也许我可以说服他们现在改变比以后好! - Hen

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接