部署后带角度的"未捕获错误:[$ injector:unpr]"

Ken*_*ith 97 angularjs

我有一个运行我的dev的机器就好了,但与此错误消息失败(在浏览器控制台)后,我部署一个相当简单的角度应用:

Uncaught Error: [$injector:unpr] http://errors.angularjs.org/undefined/$injector/unpr?p0=tProvider%20%3C-%20t%20%3C-%20%24http%20%3C-%20%24compile

除此之外没有其他消息.它会在页面首次加载时发生.

我正在运行ASP.NET MVC5,Angular 1.2RC3,并通过git推送到Azure.

谷歌搜索没有发现任何有趣的东西.

有什么建议?

编辑:

我正在使用TypeScript,并使用$inject变量定义我的依赖项,例如:

export class DashboardCtrl {

    public static $inject = [
        '$scope',
        '$location',
        'dashboardStorage'
    ];

    constructor(
        private $scope: IDashboardScope,
        private $location: ng.ILocationService,
        private storage: IDashboardStorage) {
    }
}
Run Code Online (Sandbox Code Playgroud)

我认为应该(或意图)绕过局部变量重命名在缩小期间出现的问题并且可能导致此错误.

也就是说,它显然与缩小过程有关,因为当我BundleTable.EnableOptimizations = true在我的开发机器上设置时,我可以重现它.

Stu*_*son 161

如果您按照链接进行操作,它会告诉您错误的结果是$ injector无法解析您的依赖项.这是一个常见的问题,当javascript被缩小/ uglified /无论你为生产做什么.

问题是你有一个控制器;

angular.module("MyApp").controller("MyCtrl", function($scope, $q) {
  // your code
})
Run Code Online (Sandbox Code Playgroud)

缩小变化$scope$q变成随机变量,不会告诉角度注入什么.解决方案是声明您的依赖项如下:

angular.module("MyApp")
  .controller("MyCtrl", ["$scope", "$q", function($scope, $q) {
  // your code
}])
Run Code Online (Sandbox Code Playgroud)

这应该可以解决你的问题.

只是为了重新迭代,我所说的一切都在错误信息提供给你的链接上.

  • 感谢您提供实际访问链接的建议 - 我认为它是一些内部工件,不是为了我的利益.事实证明,我通过`$ inject`公共变量定义了所有依赖项,我相信这相当于你建议的方式(参见http://docs.angularjs.org/guide/di).我会更新我的问题. (2认同)
  • 也就是说,它显然与缩小过程有关,因为当我在我的开发机器上强制ASP.NET MVC缩小(`BundleTable.EnableOptimizations = true;`)时,我可以重现这个问题.继续看. (2认同)
  • @RyanTuck - 换句话说,使用未经编码的代码,Angular可以只查看函数中的变量名称,并对需要注入的内容进行很好的猜测.但是使用缩小的代码,变量名称都是munged,因此它需要一些其他机制 - 一种在代码缩小时不会改变的机制 - 知道要注入什么.这就是$ inject数组和其他机制发挥作用的地方. (2认同)

Mat*_*att 13

我自己也遇到了同样的问题,但我的控制器定义看起来与上面的有点不同.对于像这样定义的控制器:

function MyController($scope, $http) {
    // ...
}
Run Code Online (Sandbox Code Playgroud)

只需在声明后添加一行,指示在实例化控制器时要注入的对象:

function MyController($scope, $http) {
    // ...
}
MyController.$inject = ['$scope', '$http'];
Run Code Online (Sandbox Code Playgroud)

这使它更加安全.


小智 11

当控制器或指令未指定为依赖项和函数的数组时,会发生此问题.例如

angular.module("appName").directive('directiveName', function () {
    return {
        restrict: 'AE',
        templateUrl: 'calender.html',
        controller: function ($scope) {
            $scope.selectThisOption = function () {
                // some code
            };
        }
    };
});
Run Code Online (Sandbox Code Playgroud)

缩小时传递给控制器​​函数的'$ scope'被替换为单个字母变量名.这将使角度无关紧要.为了避免这种情况,将依赖项名称和函数作为数组传递.

angular.module("appName").directive('directiveName', function () {
    return {
        restrict: 'AE',
        templateUrl: 'calender.html'
        controller: ['$scope', function ($scope) {
            $scope.selectThisOption = function () {
                // some code
            };
        }]
    };
});
Run Code Online (Sandbox Code Playgroud)


Sch*_*apz 10

如果你有角度app\resources\directives和其他东西的单独文件,那么你可以像这样禁用你的角度应用程序包的缩小(在你的包配置文件中使用新的Bundle()而不是ScriptBundle()):

bundles.Add(
new Bundle("~/bundles/angular/SomeBundleName").Include(
               "~/Content/js/angular/Pages/Web/MainPage/angularApi.js",
               "~/Content/js/angular/Pages/Web/MainPage/angularApp.js",
               "~/Content/js/angular/Pages/Web/MainPage/angularCtrl.js"));
Run Code Online (Sandbox Code Playgroud)

角度应用程序将出现在未修改的包中.