Angularjs : can i inject dependency in app dynamically - javascript

I have defined drawerApp on my js . On click of button i am loading partial and there require js file. I need to inject some loaded js into my current drawerApp is there any way to inject in app?
Currentlt config. is as below.
JavaScript:
drawerApp.config([ '$interpolateProvider','$controllerProvider','$compileProvider', '$filterProvider', '$provide',
function ($interpolateProvider,$controllerProvider,$compileProvider, $filterProvider, $provide) {
$interpolateProvider.startSymbol('{[{');
$interpolateProvider.endSymbol('}]}');
drawerApp.register =
{
controller: $controllerProvider.register,
directive: $compileProvider.directive,
filter: $filterProvider.register,
factory: $provide.factory,
service: $provide.service
};
}]);

Related

How I can run two controllers via two routing?

I have two modules, where two routes:
angular
.module('lang', ['ngRoute'])
.config('lang', ['$routeProvider', config])
.controller('lang', lang);
function config(route){
route.when('/:lang/:page', {
template : '',
controller : lang
})
}
and route for guide module:
angular
.module('guide', ['ngRoute'])
.config('guide', ['$routeProvider', config])
.controller('guide', guide);
function config(route){
route.when('/:lang/guide', {
template : '/view/guide.html',
controller : guide
})
}
But the second controller not run. How can I run two controllers using two routes?
ng-route using for SPA applications.
If you want to navigate to different pages in your application, but you also want the application to be a SPA (Single Page Application), with no page reloading, you can use the ngRoute module.
Therefore you need to define main module, config routes there and inject dependencies. Example:
var app = angular.module('app',['ngRoute', 'firstModule', 'secondModule']);
var configFunction = function($routeProvider){
$routeProvider
.when('/:lang/:page', {
templateUrl: '/view/guide.html',
controller : 'FirstCtrl'
})
.when('/:lang/guide', {
templateUrl: '/view/guide2.html',
controller: 'SecondCtrl'
})
configFunction.$inject = ['$routeProvider'];
app.config(configFunction);
app.config(['$locationProvider',
function ($locationProvider) {
$locationProvider.hashPrefix('');
}]);
And this is your injected controllers :
var app = angular.module('firstModule', []);
app.controller('FirstCtrl',function(){});
var app = angular.module('secondModule', []);
app.controller('SecondCtrl',function(){});
Be aware regarding syntax. Check syntax for Angular version you use.

Dependency injection hell, what is expected?

I'm trying to separate components into several files for a simple application but angular's dependency injector is giving me headaches and I don't really know what is expected.
Unknown provider: servicesProvider <- services <- maincontroller
Is the error I'm getting.
app.js
//Application definition with injected dependencies
var app = angular.module('leadcapacity', ['services', 'utils', 'customfilters', 'controllers']);
services.js
var services = angular.module('services', []);
services.service('xrmservice',
[
'$http', function($http) {
var oDataUrl = Xrm.Page.context.getClientUrl() + '/XRMServices/2011/OrganizationData.svc/';
var service = {};
service.query = function(entitySet, query) {
return $http.get(oDataUrl + entitySet + '?' + query);
};
return service;
}
]);
controllers.js
var ctrls = angular.module('controllers', ['utils', 'services']);
ctrls.controller('maincontroller',
function ($scope, services, utils) {
};
});
And the include order in index.html
<script src="service.js"></script>
<script src="controllers.js"></script>
<script src="app.js"></script>
Looks fine to me. I know this is perhaps not the best way to organize things, but getting a "Hello world" first would be nice.
Thanks.
Error message appearing in console clearly says that, services
dependency isn't exists in the module.
You have injected incorrect service name in maincontroller controller factory function, basically you were trying to to inject services(module name) instead of xrmservice(service name)
function ($scope, services, utils) {
should be
function ($scope, xrmservice, utils) {
Additional
Do follow Inline Array annotation of DI, as you were already used the same in your xrmservice service JS file, so that in future you don't need to go back and change that when you face javascript minification related issues.
Controller
ctrls.controller('maincontroller', [ '$scope', 'xrmservice', 'utils',
function ($scope, xrmservice, utils) {
//code goes here
//....
};
}]);
Although you have injected them into the module, you need to give them to the function so you can use the injected modules
ctrls.controller('maincontroller',
['$scope', 'services', 'utils', function ($scope, services, utils) {
};
}]);

AngularJs directive not working/visible

I'm just getting started with AngularJs. And I'm trying to implement a login directive. But I don't see the output? I've no errors in my console.
My application structure:
(index.html is not visible)
login.directive.js :
(function() {
'use strict';
angular
.module('lnjapp.login',[])
.directive('login', login);
function login() {
var directive = {
template: '<p>test</p>',
//restrict: 'E',
Controller: LoginController,
controllerAs: 'vm'
};
return directive;
}
})();
app.js :
(function () {
'use strict';
angular.module('lnjapp', ['ngRoute', 'ngCookies', 'angular.filter','lnjapp.login','lnjapp.config'])
.constant('GLOBALS', {
url:'http://domain.dev/api/v1/'
});
$(document).ready(function() {
$.material.init();
});
})();
app/pages/login.html:
<login></login>
--EDIT--
login.controller.js:
(function() {
'use strict';
angular.module('lnjapp.login',[])
.controller('LoginController', LoginController);
function LoginController()
{}
})();
route-config.js:
angular
.module('lnjapp.config',[])
.config(config);
function config($routeProvider) {
$routeProvider
.when('/', {
templateUrl: '/app/pages/login.html'
});
}
What am I doing wrong here?
You are creating your lnjapp.login twice, once in login.directive.js and again in login.controller.js. The second time the module is created, it overwrites the first, and whatever was created in the first file will no longer be accessible.
You should always only create a module once, and get the already created module to add additional features in all other cases.
Set (create): angular.module('lnjapp.login',[])
Get (consume): angular.module('lnjapp.login')
For more info and other best practices, see John Papa's excellent Angular Style Guide.

Angular JS - Folder structure issue - controllers.js

I have the folder structure as in the image.
And I have 2 controllers in 2 different folders. And it seems they 2 gets conflicted and the first controller pages are not working if I include the 2nd controller in index.html as below. Only if I remove the second controller the first one works.
index.html
<script src="1_reportingEntities/controller.js"></script>
<script src="2_dataCollections/controller.js"></script>
Folder structure
Updated:
Here are the 2 controllers and both have the same file name in different folders.
controller.js
'use strict';
var mdmApp = angular.module('mdmApp', ['ngRoute', 'ngResource', 'ngMessages', 'ui.grid', 'ui.grid.pagination',
'ui.grid.moveColumns', 'ui.grid.resizeColumns', 'ui.grid.selection', 'ui.grid.autoResize',
'ui.grid.cellNav', 'ui.grid.exporter', '720kb.datepicker','angularjs-dropdown-multiselect']);
mdmApp.config(function($routeProvider) {
$routeProvider.when('/', {
templateUrl : '1_reportingEntities/listEntities.html',
controller : "listController"
})
.when('/list', {
templateUrl : '1_reportingEntities/listEntities.html',
controller : "listController"
})
controller.js
'use strict';
var mdmApp = angular.module('mdmApp', ['ngRoute', 'ngResource', 'ngMessages', 'ui.grid', 'ui.grid.pagination',
'ui.grid.moveColumns', 'ui.grid.resizeColumns', 'ui.grid.selection', 'ui.grid.autoResize',
'ui.grid.cellNav', 'ui.grid.exporter', '720kb.datepicker','angularjs-dropdown-multiselect']);
mdmApp.config(function($routeProvider) {
$routeProvider.when('/dataCollection', {
templateUrl : '2_dataCollections/dataCollection.html',
controller : "dataCollectionController"
})
.when('/reportTypeEntityList/:id', {
templateUrl : '2_dataCollections/reportTypeEntityList.html',
controller : 'reportListController',
resolve : {
formType : function() {
return 'REPORTTYPEENTITYLIST';
}
}
})
Your problem is you are declaring the same module twice.
When you register a module you add the second argument for dependencies.
Then to reference the same module you leave out dependencies, and only use the name.
Create module (setter):
angular.module('myApp', []);
Reference module (getter):
angular.module('myApp').controller('...;
You are basically wiping out the first module (and controller) when you add the same module declaration again

All AngularJS Controllers Not Loading with LazyLoad

I am trying to lazy load my controllers for my AngularJS app I built along side with requireJS. I have created a custom "lazyLoad" library that creates a resolve object in app.config() routes (also I am using ui-router). If I code the state (without my library) to look like so it works
define(['angular', 'lazyLoader', 'uiRouter'], function(angular, lazyLoader, uiRouter){
var app = angular.module('myApp', ['ui.router']);
app.config(function ($stateProvider, $urlRouterProvider, $controllerProvider, $compileProvider, $filterProvider, $provide) {
window.lazy = {
controller: $controllerProvider.register,
directive: $compileProvider.directive,
filter: $filterProvider.register,
factory: $provide.factory,
service: $provide.service
};
$urlRouterProvider.otherwise('/');
$stateProvider
.state('campaigns', {
url:'/campaigns',
views: {
"top-nav" : {
templateUrl: 'views/home/top-nav.html',
resolve : {
load : ['$q', '$rootScope', function($q, $rootScope){
var d = $q.defer();
require(['../app/controllers/header-controller'], function() {
$rootScope.$apply(function(){
d.resolve();
});
});
return d.promise;
}]
}
},
"fullpage": {
templateUrl: 'views/home/index.html',
resolve : {
load : ['$q', '$rootScope', function($q, $rootScope){
var d = $q.defer();
require(['../app/controllers/home-controller'], function() {
$rootScope.$apply(function(){
d.resolve();
});
});
return d.promise;
}]
}
//controller: 'home-controller'
}
}
});
});
return app;
});
If I attempt to replace the resolve object with my library function it looks would look like this:
define(['angular', 'lazyLoader', 'uiRouter'], function(angular, lazyLoader, uiRouter){
and
.state('home', lazyLoader.route({
url:'/',
views: {
"top-nav" : {
templateUrl: 'views/home/top-nav.html',
controllerUrl: '../app/controllers/header-controller'
},
"fullpage": {
templateUrl: 'views/home/index.html',
controllerUrl: '../app/controllers/home-controller'
}
}
}));
lazyLoader.js
define(function () {
'use strict';
function LazyLoader() {}
LazyLoader.prototype.route = function(config){
var controllerPath;
if(config && config.views){
var singleView = Object.keys(config.views);
for(var i in singleView){
var viewName = singleView[i];
controllerPath = config.views[viewName].controllerUrl;
delete config.views.controllerUrl;
config.views[viewName].resolve = {
load : ['$q', '$rootScope', function($q, $rootScope){
var d = $q.defer();
require([controllerPath], function() {
$rootScope.$apply(function(){
d.resolve();
});
});
return d.promise;
}]
};
}
}
return config;
}
return new LazyLoader();
});
Example Controller
define(['app/module'], function (module) {
lazy.controller('header-controller', ['$scope', function ($scope) {
// stuff here
}]);
});
On a side note I plan on implementing something better than attaching lazy variable to window.
When I code the router like the first example it works. When I use my lazyLoader the one of the two views loads it's controller, the second view's controller's file is started to load (console.logs at the beginning show this) but it cannot resolve "module" in the example above.
link to error: AngularJS Error
Again this issue only happens when using my lazyloader which is producing the same resolve object that I have hard coded in for the version that works.
I have searched high and low and there are a lot of resources out there but I could not find anything that addressed this issue.
Any advice is appreciated!
You are taking too much pain to do lazy loading of controllers & services. There is simple approach to lazy load files with ocLazyLoad. This article might help you resolve the same issue.
https://routerabbit.com/blog/convert-angularjs-yeoman-spa-lazyload/
What you should do is
Add a reference of ocLayzLoad & updated JS files’ reference to load on demand from app.js or .html file of their views.
`bower install oclazyload --save-dev`
Now load the module ‘oc.lazyLoad’ in application. Update app.js file
angular
.module('helloWorldApp', [
'ngCookies',
'ngResource',
'ngRoute',
'ngSanitize',
'oc.lazyLoad',
])
Load JS file by adding reference of JS in .html file
<div oc-lazy-load="['scripts/controllers/about.js', 'scripts/services/helloservice.js']">
<div ng-controller="AboutCtrl as about">
Your html goes here
</div>
</div>
If you using Grunt, update Gruntfile to uglyfy, renamed file name & update references in the final .html or .js file.
On the 'myApp' module definition, shouldn't you be returning app variable instead of myApp?
And to avoid exposing lazy to window, you could define it as a property of app variable, this way when you define new functions, you require app first and you can use it:
app.js:
app.lazy = {
controller: $controllerProvider.register,
directive: $compileProvider.register,
filter: $filterProvider.register,
factory: $provide.factory,
service: $provide.service
};
...
return app;
controller.js:
define(['app'], function (app) {
app.lazy.controller('header-controller', ['$scope', function ($scope) {
// stuff here
}]);
});

Categories

Resources