I'm trying to define a service with methods that I can call from a module in AngularJS.
This is my first attempt at using AngularJS.
Maybe this isn't a good way to do it, but I thought that I could put some helper methods into a service that could be then reusable.
But I'm finding that the UrlHelperService isn't available from the module.
I've tried to simplify and extract just the skeleton of the three files being used:
app.js
angular.module('myApp', ['ngRoute', 'myMod', 'UrlHelperService']);
urls.js
var serv = angular.module('UrlHelperService', []);
serv.service( "UrlHelperService",
function aaMethod( ) {
this.urlHelp = function( url, aa ) {
return url;
}
}
);
module.js
var module = angular.module( "myMod", [] );
module.factory(
"myMod",
[ "$http", "$q", "UrlHelperService",
function myModFactory( $http, $q, UrlHelperService) {
// UrlHelperService isn't available here. Why?
return;
}]);
Well, if you want to use UrlHelperService with myMod you need to declare it as a dependency in myMod (as you do in myApp).
var module = angular.module( "myMod", [
"UrlHelperService"
]);
module.factory(
"myMod", [
"$http",
"$q",
"UrlHelperService",
function myModFactory( $http, $q, UrlHelperService) {
// UrlHelperService isn't available here. Why?
return;
}
]);
But it could possibly be even simpler. You are creating a myMod module and a myMod service (.factory is similar to .service), why?
Anyway, you're absolutely right to putting these helper function in a service you can reuse. It doesn't have top be on its own module though. Perhaps a simpler approach would be good enough. For example:
angular
.module('myApp', [
'ngRoute'
])
.factory('UrlHelperService', [
function UrlHelperService() {
return {
urlHelp: function(url, aa) {
return url;
}
};
}
]);
Here you have your app (its own module) and a service available to everyone else inside myApp. Sometime a separate module for some services etc is better, sometimes a service inside your main module is good enough.
Related
I currently have 3 angularjs modules, each of which are (roughly) like so:
(function () {
var generalApp = angular.module('general-app', []);
generalApp.controller("NewsletterSignup.Controller", ["$scope", "$http", NewsletterSignupControllerFunction]);
}());
where NewsletterSignupControllerFunction is a global variable that is a reference to a function, eg:
var NewsletterSignupControllerFunction = function ($scope, $http) { ... };
Rather than use a global variable to share logic between the three modules, what is the simplest way to inject NewsletterSignupControllerFunction into each of the modules so I can use it to create the controllers? I have tried various approaches, none of which I can get to work.
One approach is to define a common module with the controller:
common.js
(function () {
angular.module('common', [])
.controller("NewsletterSignup.Controller",
["$scope", "$http", NewsletterSignupControllerFunction]
)
function NewsletterSignupControllerFunction ($scope,$http) {
//code ...
}
}());
Use that common module as a dependency:
angular.module("myApp",['common'])
For more information, see
AngularJS angular.module API Reference
I'm trying to inject my factory into my controller and I'm getting this error from AngularJS:
Error: $injector:unpr Unknown Provider
I have looked through almost all of the questions on here and still cannot find a solution to my problem. I believe my controller and factory and declared correctly and the injection is correct but it looks like this isn't the case.
My factory code is as follows:
var app = angular.module('test', []);
app.factory('processingFactory', function () {
var factory = {};
factory.newTest = function() {
console.log("TEST");
}
return factory;
});
This is then injected into the controller which looks like this:
angular.module("test", ["angularModalService", "anguFixedHeaderTable",
'angular-loading-bar', "ngResource", "agGrid",
'ui.tree']).controller("dashboardController", [
"$scope",
"$timeout",
"$http",
"$window",
"$interval",
"$resource",
"ModalService",
"$filter",
'$q',
'processingFactory',
function($scope, $timeout, $http, $window, $interval, $resource,
ModalService, $filter, $q, processingFactory) {
//other code removed
$scope.newWorkorder = processingFactory.newWorkorder;
}
]);
This function is called through a button click on the web page. All of the files needed are in script tags on this html page. I am fairly new to angular so this could be a simple error or something I am not aware of.
Calling angular.module with an array as the second argument declares a module, which can only happen for any given module name. You are declaring the module twice (once in your controller code, and again in your factory code).
Try changing the first part of your factory code to:
var app = angular.module('test');
If you are doing the same thing elsewhere in the app you will need to remove the second argument there too, so that there is only one module declaration in the whole app.
if there are any dependencies for your module "test" why do not you have them declared in the first line itself like:
var app = angular.module("test", ["angularModalService", "anguFixedHeaderTable",
'angular-loading-bar', "ngResource", "agGrid",
'ui.tree']);
Then declare your controller like::
app.controler(...)
Things should work fine.
I'm new to angular and have the following code.
angular.module('MyApp')
.controller('loginController', ['$scope', '$http', 'conditionalDependency',
function ($scope, $http, conditionalDependency{
}
I would like to have conditionalDependency loaded conditionally. Something like this
if(true)
{
//add conditionalDependency
}
How can this be done. I've seen this post . However, my requirement is that I have the dependency specified in function
Thanks in advance.
Not quite clear as to why you would have to have it in a named function like in your example but...
If you need conditional dependencies, I would suggest taking a look at the following:
Conditional injection of a service in AngularJS
I've used this method in a couple niche scenarios and it works quite well.
EXAMPLE:
angular.module('myApp').controller('loginController',
['$injector', '$scope', '$http',
function($injector, $scope, $http) {
var service;
if (something) {
service = $injector.get('myService');
}
});
You can use it even without injecting injector in your controller
if(something){
var injector = angular.element(document).injector();
var myService = injector.get('myService')
}
Use:
angular.injector().get('conditionalDep');
You can inject $injector once to your file and call $injector.get('dep');
Whenever I do this:
app.controller('hangmanController', ['$scope', 'wordnickAPIService', function ($scope, wordnickAPIService) {
I get this:
[$injector:unpr] Unknown provider: wordnickAPIServiceProvider <- wordnickAPIService
I read through This discussion on the topic, but didn't see an answer that applied. I am sure it is something simple or trivial that I am missing, but, jeez, if Angular isn't giving me fits trying to piece it all together.
Relevant HTML:
<body ng-app="angularHangmanApp" ng-controller="hangmanController">
My controller:
'use strict';
var app = angular.module('angularHangmanApp', []);
app.controller('hangmanController', ['$scope', 'wordnickAPIService', function ($scope, wordnickAPIService) {
[...]variable declarations[...]
var wordListURL = 'http://long_url_that_returns_some_json';
$scope.wordList = wordnickAPIService.get(wordListURL);
}]);
My factory:
'use strict';
var app = angular.module('angularHangmanApp', []);
app.factory('wordnickAPIService', ['$http', function($http) {
return {
get: function(url) {
return $http.get(url);
},
post: function(url) {
return $http.post(url);
},
};
}]);
The problem is that you are creating multiple modules with the same name.
To create a module in angular you use:
var app = angular.module('angularHangmanApp', []);
Then to get That module somewhere else you just type:
var app = angular.module('angularHangmanApp');
No extra []...
Also make sure you declare the service before trying to call it.
In your factory and your controller, you are actually redefining the app module.
Instead of saying
var app = angular.module('angularHangmanApp', []);
say
var app = angular.module('angularHangmanApp');
Use the first style of invocation only once in your application (maybe just app.js). All other references should use the second style invocation, otherwise, you're constantly redefining the angular app and losing all of the controllers, factories, directives declared previously.
I'm having trouble managing my app. I would like to separate my controllers on several files. I read Brian's Ford blog ( http://briantford.com/blog/huuuuuge-angular-apps.html ) but I cannot quite understand how should I do it.
On my controller.js file I had something like this :
function loginCtrl($scope){
....
}
function landingCtrl($scope){
...
}
And the only way I found to separate controller per file is to do this:
app.js:
var musicApp = angular.module('musicApp', []);
controller1.js:
musicApp.controller('loginController', ['$scope', loginCtrl],function loginCtrl($scope){
....
});
controller2.js:
musicApp.controller('landingCtrl', ['$scope', landingCtrl],function landingCtrl($scope){
....
});
Is there a better way to do this?
I'm using a similar way as below:
Main.js
angular.module('app', []);
FooCtrl.js
angular.module("app").controller("FooCtrl", [
"$scope", function($scope) {
}
]);
Another way adopted by google is:
# init empty Object
var docsApp = {
controller: {},
directive: {},
serviceFactory: {}
};
# FooCtrl.js
docsApp.controller.FooCtrl = ['$scope', function($scope){}]
# BarCtrl.js
docsApp.controller.BarCtrl = ['$scope', function($scope){}]
... add services
... directives
# bootstrap angular
angular.module('docsApp', ['...']).
config(...).
factory(docsApp.serviceFactory).
directive(docsApp.directive).
controller(docsApp.controller);
Take a look at this js from google angularjs tutorial: http://docs.angularjs.org/js/docs.js
You can achieve this in multiple ways.
one file for all your controllers using "."
musicApp.controller('loginController', ['$scope', loginCtrl,function loginCtrl($scope){
....
}]).controller('landingCtrl', ['$scope', landingCtrl,function landingCtrl($scope){
....
}]);
just remember to include the function inside the injected paramenters array.
or one controller for each file.
just need to include every js file with whatever method you are using (script tag, requirejs, etc.)
I have something similar:
main_router.js:
var myApp = angular.module('theApp', ['controllers'])...
var controllers = angular.module('controllers', []);
some_controller.js:
controllers.controller('SomeCtrl', ['$scope',
function ($scope) { ... }
]);