Debugging Unknown provider in minified angular javascript

JavascriptAngularjs

Javascript Problem Overview


I'm having a hard time trying to pinpoint which, of the very many, methods I have in my angular app that would be causing the error:

Uncaught Error: [$injector:unpr] Unknown provider: nProvider <- n

This only happens once the javascript has been bundled & minified by ASP.Net.

I have ensured that all the controllers, and any other DI, is using the minification-safe method, I.E My controllers/service etc are using the method:

appControllers.controller('myCtrl', ['$scope', function($scope){
        //......
}]);

I've gone through every JS file in our app - there are a lot... and can't find anything that violates this way of injecting dependencies - though there must be one somewhere...

Is there a better way to pinpoint which method could be causing this error?

Thanks

Javascript Solutions


Solution 1 - Javascript

For anyone else struggling with this problem, I found an easier solution. If you pull open your developer console (on chrome) and add a breakpoint where angular throws the error:

angular throwing an error

Then, on the stack trace on the right, click on the first "invoke" you see. This will take you to the invoke function, where the first parameter is the function angular is trying to inject:

I was able to inspect the function

I then did a search through my code for a function that looked like that one (in this case grep "\.onload" -R public), and found 8 places to check.

I hope this helps!

Solution 2 - Javascript

For anybody reading this, using Angular 1.3

You can now use Angular's ng-strict-di check like this:

<div ng-app="some-angular-app" ng-strict-di>
  ...
</div>

This will give you an appropriate error message if you didn't load your dependencies using the array syntax.

Solution 3 - Javascript

I had the same problem and I found a solution that could be helpful for the rest. What I propose is basically what I saw in the comments and docs. If you are using Angular 1.3.0 or above, you can use this:

<html ng-app="myApp" ng-strict-di>
   <body>
      I can add: {{ 1 + 2 }}.
      <script src="angular.js"></script>
    </body>
</html>

In my case, I have everything within a file app.js so the only thing I need to do for finding my DI problems is to add this little code at the end:

angular.bootstrap(document, ['myApp'], {
  strictDi: true
});

It's better documented in Angular Docs

I hope that helps. Good luck!

Solution 4 - Javascript

As mentioned in the comments, These are the steps I took to try and find my JS error.

If there is another, easier, solution, please feel free to post it and I may mark it as accepted.


Trying to debug minified code is a nightmare.

What I eventually did was copy my minified javascript, directly from the inspector in Chrome.

I then pasted the JS into http://www.jspretty.com/ - I had tried http://jsbeautifier.org/ but found their site froze with such large JS code.

Once it was 'pretty-fied' I created a test.js file in my solution and pasted the, now easier to read code, into it.

Quick step to comment out the @script tag in my _layout and add a link to the test.js file and I was ready to debug a now, far easier to read, chunk of Javascript.

It is still pretty awkward to traverse the call stack, though now you can see actual methods it makes it far less impossible.

Solution 5 - Javascript

Something that helped me solve this (finally!) was actually already in the angular docs! If you add the ng-strict-di attribute to your code wherever you define your ng-app, angular will throw a strict warning so you can more easily see what's going on in development mode. I wish that was the default!

See the argument list at the bottom of the ngApp docs.

https://docs.angularjs.org/api/ng/directive/ngApp

Solution 6 - Javascript

The way this works for me is the following:

  1. have two test specification html files (unit test) minimized and plain

  2. make sure the bundling of the files are in the same order as the plain spec file (JS script reference)

  3. make sure to explicitly declare all dependencies (array or $inject declares see http://www.ozkary.com/2015/11/angularjs-minimized-file-unknown-provider.html)

When there is a mistake on the unit test (miminized reference) file, I can compare and make sure the reference of the files is in the correct order as the working file.

hope that help.

Solution 7 - Javascript

I had the similar issue and used lots of time to investigate and figured out it was the Chrome extension Batarang that was injecting the bad code and error in Angular looked exactly the same. It's really a pity it's so hard to find what exactly is causing the problem.

Solution 8 - Javascript

I had the similiar issue too. The solution is exacly the answer from ozkary point 3, that is to make sure to explicitly declare all dependencies including "resolve" part of your route.

Below is my code.

when('/contact/:id', {
      controller: 'contactCtrl',
      templateUrl: 'assets/partials/contact.html',
      resolve: {
         contact: ['ContactService', '$route', function(ContactService, $route) {
            return ContactService.getContactDetail($route.current.params.id);
         }]
      }
})

Solution 9 - Javascript

For those who's bootstrapping their angularjs app.

angular.bootstrap(body, ['app'], { strictDi: true });

Don't forget to debug in non minified code and you should be able to figure out pretty quickly the malformed dependency injection.

The malformed injection is usually formatted like this :

...
.run([ function(ServiceInjected){
...

But should look more like this

...
.run(['ServiceInjected', function(ServiceInjected){
...   

This is tested in angularjs 1.7.2

Attributions

All content for this solution is sourced from the original question on Stackoverflow.

The content on this page is licensed under the Attribution-ShareAlike 4.0 International (CC BY-SA 4.0) license.

Content TypeOriginal AuthorOriginal Content on Stackoverflow
QuestionDarren WainwrightView Question on Stackoverflow
Solution 1 - JavascriptyourdeveloperfriendView Answer on Stackoverflow
Solution 2 - JavascriptMax SchulzeView Answer on Stackoverflow
Solution 3 - JavascriptJesús SobrinoView Answer on Stackoverflow
Solution 4 - JavascriptDarren WainwrightView Answer on Stackoverflow
Solution 5 - JavascriptWhitelancerView Answer on Stackoverflow
Solution 6 - JavascriptozkaryView Answer on Stackoverflow
Solution 7 - JavascriptIlya ChernomordikView Answer on Stackoverflow
Solution 8 - JavascriptAjang RView Answer on Stackoverflow
Solution 9 - JavascriptMark OdeyView Answer on Stackoverflow