angular js未知提供商

时间:2012-09-09 12:59:28

标签: angularjs

我正在尝试“自定义”mongolab示例以适合我自己的REST API。现在我遇到了这个错误,我不确定我做错了什么:

Error: Unknown provider: ProductProvider <- Product
    at Error (unknown source)
    at http://localhost:3000/js/vendor/angular.min.js:28:395
    at Object.c [as get] (http://localhost:3000/js/vendor/angular.min.js:26:180)
    at http://localhost:3000/js/vendor/angular.min.js:28:476
    at c (http://localhost:3000/js/vendor/angular.min.js:26:180)
    at d (http://localhost:3000/js/vendor/angular.min.js:26:314)

这是我的控制者:

function ProductListCtrl($scope, Product) {
  $scope.products = Product.query();
}

这是模块:

angular.module('productServices', ['ngResource']).
    factory('Product', ['$resource', function($resource){
      var Product = $resource('/api/products/:id', {  }, {
        update: { method: 'PUT' }
      });

      return Product;
    }]);

30 个答案:

答案 0 :(得分:129)

您的代码看起来不错,实际上它在复制时可以正常工作(除了调用本身)粘贴到示例jsFiddle:http://jsfiddle.net/VGaWD/

很难说没有看到更完整的例子会发生什么,但我希望上面的jsFiddle会有所帮助。 我怀疑您没有使用'productServices'模块初始化您的应用。它会产生同样的错误,我们可以在另一个jsFiddle中看到这个:http://jsfiddle.net/a69nX/1/

如果您打算使用AngularJS和MongoLab ,我建议使用现有的适配器用于$ resource和MongoLab https://github.com/pkozlowski-opensource/angularjs-mongolab 它减轻了使用MongoLab的大部分痛苦,你可以在这里看到它:http://jsfiddle.net/pkozlowski_opensource/DP4Rh/ 免责声明!我正在维护这个适配器(基于AngularJS示例编写),所以我显然有偏见。

答案 1 :(得分:39)

我收到了该错误,因为我将错误的参数传递给工厂定义。我有:

myModule.factory('myService', function($scope, $http)...

当我删除$scope并将工厂定义更改为:

时,它有效
myModule.factory('myService', function( $http)...

如果您需要注入$scope,请使用:

myModule.factory('myService', function($rootScope, $http)...

答案 2 :(得分:32)

我遇到了类似的问题。 错误说同样的问题,试图用pkozlowski.opensource和Ben G的答案解决它,这两个都是正确和好的答案。

我的问题确实与同样的错误有所不同:

在我的HTML代码中我有这样的初始化...

<html ng-app>

再往下一点,我试着做这样的事情:

<div id="cartView" ng-app="myApp" ng-controller="CartCtrl">

我摆脱了第一个...然后它起作用了......显然你不能初始化ng-app两次或更多次。很公平。

我完全忘记了第一个“ng-app”并且总是感到沮丧。也许这会帮助别人... ...

答案 3 :(得分:25)

确保您的主app.js包含其所依赖的服务。例如:

/* App Module */
angular.module('myApp', ['productServices']). 
.....

答案 4 :(得分:17)

pkozlowski的答案是正确的,但为了防止其他人发生这种情况,我错误地创建了两次相同的模块后出现了同样的错误;第二个定义是覆盖第一个的提供者:

我通过

创建了模块
angular.module('MyService'...
).factory(...);

然后在同一个文件中进一步向下:

angular.module('MyService'...
).value('version','0.1');

这样做的正确方法是:

angular.module('MyService'...
).factory(...).value('version','0.1');

答案 5 :(得分:11)

就我而言,我已经定义了一个新的提供商,比如xyz

angular.module('test')
.provider('xyz', function () {
    ....
});

当您要配置上述提供商时,您需要为其添加Provider字符串 - >&gt; xyz变为xyzProvider

例如:

angular.module('App', ['test'])
.config(function (xyzProvider) {
     // do something with xyzProvider....
});

如果您在没有'Provider'字符串的情况下注入上述提供者,您将在OP中收到类似的错误。

答案 6 :(得分:8)

在JS文件的末尾关闭我的工厂函数

}());

而不是

{{1}}

答案 7 :(得分:4)

我花了太长时间才追查。确保你在指令中迷你控制器。

.directive('my_directive', ['injected_item', function (injected_item){

  return {

    controller: ['DO_IT_HERE_TOO', function(DO_IT_HERE_TOO){

    }]
  }
}

希望有所帮助

答案 8 :(得分:4)

为了在这里添加我自己的经验,我试图将服务注入我的一个模块配置功能。我最终找到的文档中的这一段解释了为什么不起作用:

  

在应用程序引导期间,在Angular创建所有服务之前,它会配置并实例化所有提供程序。我们称之为应用程序生命周期的配置阶段。在此阶段,服务无法访问,因为尚未创建服务。

意思是你可以将提供者注入module.config(...)函数,但是你不能注入服务,因为你需要等到module.run(...),或者暴露你可以注入的提供者到module.config

答案 9 :(得分:4)

对我来说,这个错误是由运行我的角度应用程序的缩小版本引起的。 Angular docs提出了解决这个问题的方法。以下是描述该问题的相关引文,您可以在文档中找到建议的解决方案here

  

关于缩小的注释   由于Angular将控制器的依赖关系从参数名称推断到控制器的构造函数,如果你要缩小PhoneListCtrl控制器的JavaScript代码,它的所有函数参数也将被缩小,并且依赖注入器将无法识别服务正确。

答案 10 :(得分:3)

由于这是目前Google上“angularjs unknown provider”的最佳结果,这是另一个问题。使用Jasmine进行单元测试时,请确保在beforeEach()函数中包含此语句:

module('moduleName'); 

否则你会在测试中遇到同样的错误。

答案 11 :(得分:3)

另一种情况会发生此错误,如果您的服务是在单独的javascript文件中定义的,请确保您引用它!是的,我知道,菜鸟错了。

答案 12 :(得分:1)

在我的例子中,我使用匿名函数作为角度模块的包装器,如下所示:

(function () {
var app = angular.module('myModule', []);
...
})();

关闭括号后,我忘了通过再次打开和关闭括号来调用匿名函数。

答案 13 :(得分:1)

对我来说,问题是延迟加载;我加载了我的控制器和服务,所以它们在页面加载(和Angular初始化)时不可用。我用ui-if标签做了这个,但那是无关紧要的。 解决方案是加载具有页面加载的服务。

答案 14 :(得分:1)

我遇到的问题是,我创建了一些引用该服务的新javascript文件,但Chrome只看到旧版本。 CTRL + F5为我修复了它。

答案 15 :(得分:1)

这是另一种可能出现此错误的情况:

如果您使用Sublime Text 2和angular插件,它将生成这样的存根

angular.module('utils', [])
.factory('utilFactory', [''
    function() {
        return {

        }
    }
]);

注意空白&#39; &#39;作为&#39; utilFactory&#39;之后数组的第一个元素。串。如果您没有任何依赖关系,请将其删除,如下所示:

angular.module('utils', [])
.factory('utilFactory', [
    function() {
        return {

        }
    }
]);

答案 16 :(得分:1)

我忘了注入完全保留我服务的文件。请记住在初始化应用模块时执行此操作:

angular.module('myApp', ['myApp.services', ... ]);

答案 17 :(得分:1)

由于此问题是google的最高结果,我将在列表中添加另一个可能的内容。

如果您使用的模块在依赖注入包装器上出现故障,它将提供相同的结果。例如copy&amp;来自互联网的粘贴模块可能依赖于underscore.js并试图注入&#39; _&#39;在di包装中。如果您的项目依赖项提供程序中不存在下划线,那么当您的控制器尝试引用模块的工厂时,它将获得未知的提供程序&#39;在浏览器的控制台日志中为您的工厂。

答案 18 :(得分:0)

上述答案中没有一个对我有用,也许我做错了,但作为初学者,我们的工作是什么。

我正在div初始化控制器以获得列表:

 <div ng-controller="CategoryController" ng-init="initialize()">

然后使用$routeProvider将URL映射到同一个控制器。一旦我删除了ng-init控制器使用该路由。

答案 19 :(得分:0)

创建新工厂并在组件中使用它后出现此错误,但我没有检查该组件的规格

  

所以如果您的(规格)测试文件失败

     

您需要添加beforeEach(module('YouNewServiceModule'));

答案 20 :(得分:0)

我今天面临类似的问题,问题非常小

 app.directive('removeFriend', function($scope) {
return {
    restrict: 'E',
    templateUrl: 'removeFriend.html',
    controller: function($scope) {
        $scope.removing = false;
        $scope.startRemove = function() {
            $scope.removing = true;
        }
        $scope.cancelRemove = function() {
            $scope.removing = false;
        }
        $scope.removeFriend = function(friend) {
            var idx = $scope.user.friends.indexOf(friend)
            if (idx > -1) {
                $scope.user.friends.splice(idx, 1);
            }
        }
    }
}
});

如果您观察到上面的块,在第一行中您会看到我错误地注入了$ scope。 我删除了不必要的依赖项以解决问题。

 app.directive('removeFriend', function() {
return {
    restrict: 'E',
    templateUrl: 'removeFriend.html',
    controller: function($scope) {
        $scope.removing = false;
        $scope.startRemove = function() {
            $scope.removing = true;
        }
        $scope.cancelRemove = function() {
            $scope.removing = false;
        }
        $scope.removeFriend = function(friend) {
            var idx = $scope.user.friends.indexOf(friend)
            if (idx > -1) {
                $scope.user.friends.splice(idx, 1);
            }
        }
    }
}
});

答案 21 :(得分:0)

我有同样的问题。我使用$('body').attr("ng-app", 'MyApp')而不是<body ng-app="MyApp">来修复此问题。

因为我做了

angular.element(document).ready(function () {        
    angular.bootstrap(document, [App.Config.Settings.AppName]);
})

用于架构要求。

答案 22 :(得分:0)

在我的Ruby on Rails应用程序中,我做了以下事情:

rake assets:precompile

这是在'开发'环境中完成的,该环境缩小了Angular.js并将其包含在/public/assets/application.js文件中。

删除/public/assets/*文件解决了我的问题。

答案 23 :(得分:0)

我的情景可能有点模糊,但它可能会导致同样的错误,有人可能会遇到它,所以:

当使用$ controller服务来实例化一个新的控制器(因为它是第一个注入参数时期望'$ scope')我将新控制器的本地范围传递给$ controller()函数的第二个参数。这导致Angular试图调用一个不存在的$ scope服务(但是,有一段时间,我实际上认为我有一些如何从Angular的缓存中删除'$ scope'服务) 。解决方案是将本地范围包装在locals对象中:

// Bad:
$controller('myController', newScope);

// Good:
$controller('myController, {$scope: newScope});

答案 24 :(得分:0)

又一种可能性。

我有unknown Provider <- <- nameOfMyService。该错误是由以下语法引起的:

module.factory(['', function() { ... }]);

Angular正在寻找''依赖。

答案 25 :(得分:0)

我的问题在于Yeoman,使用(大写):

yo angular:factory Test

制作文件(未大写):

app/scripts/services/test.js

但index.html文件包含(大写):

<script src="scripts/services/Test.js"></script>

希望这有助于某人。

答案 26 :(得分:0)

在处理了这个错误后,我可以用自己的案例支持这个答案列表。

它同时简单而且愚蠢(对于像我这样的初学者可能不傻,但对于专家来说也是如此),对angular.min.js的脚本引用必须是你的脚本列表中的第一个。 html页面。

这有效:

<script src="Scripts/angular.min.js"></script>
<script src="MyScripts/MyCartController.js"></script>
<script src="MyScripts/MyShoppingModule.js"></script>

这不是:

<script src="MyScripts/MyCartController.js"></script>
<script src="MyScripts/MyShoppingModule.js"></script>
<script src="Scripts/angular.min.js"></script>

关于angular.min.js。

的注意事项

希望它能帮到任何人! :)

答案 27 :(得分:0)

在使用Grunt编译项目时,我遇到了与angular-mocks(ngMockE2E)相关的“未知提供程序”错误。问题是角度模拟不能缩小,所以我不得不从缩小文件列表中删除它。

答案 28 :(得分:-1)

我的案子是狡猾的打字

myApp.factory('Notify',funtion(){

功能有'c'!

答案 29 :(得分:-1)

另一个'陷阱':我在注入$ timeout时遇到此错误,并且花了几分钟才意识到我在数组值中有空格。这不起作用:

angular.module('myapp',[].
  controller('myCtrl', ['$scope', '$timeout ', 
    function ($scope, $timeout){
      //controller logic
    }
  ]);

发布以防万一其他人有这样的愚蠢错误。