angularjs add new dependency - javascript

I want to add a new dependency, the 'angular-file-upload' dependency, but what ever I do, my app crashes, I can't understand how it works. What I've got now is:
in app.js
var myApp = angular.module('myApp', ['ui.bootstrap']);
in appController.js
myApp.controller('appCtrl', ['$scope', function ($scope) {
I've got all necessary resource files (angular-file-upload.js) and references to them, I just don't know how to properly inject the new dependency. I'm thinking I only need to edit the two provided lines, or do I have to create a whole new controller, and if so, what should that look like?
It says that my question is a possible duplicate of another, but on the other question it's about injecting dependencies into config() modules, this is not the case here.

Assuming you mean this project: https://github.com/danialfarid/ng-file-upload
then the snytax is like this:
var myApp = angular.module('myApp', ['ui.bootstrap', 'angularFileUpload']);
myApp.controller('appCtrl', ['$scope', 'FileUploader', function ($scope, FileUploader) {
}]);

The example below describes how to inject the stuff you would like to use. It is from here
//inject angular file upload directives and services.
var app = angular.module('fileUpload', ['ngFileUpload']);
app.controller('MyCtrl', ['$scope', 'Upload', function ($scope, Upload) {
^^^^^^^^ ^^^^^^
$scope.$watch('files', function () {
$scope.upload($scope.files);
});
$scope.upload = function (files) {
if (files && files.length) {
for (var i = 0; i < files.length; i++) {
var file = files[i];
Upload.upload({
url: 'upload/url',
fields: {'username': $scope.username},
file: file
}).progress(function (evt) {
var progressPercentage = parseInt(100.0 * evt.loaded / evt.total);
console.log('progress: ' + progressPercentage + '% ' + evt.config.file.name);
}).success(function (data, status, headers, config) {
console.log('file ' + config.file.name + 'uploaded. Response: ' + data);
}).error(function (data, status, headers, config) {
console.log('error status: ' + status);
})
}
}
};
}]);

Add the dependency to the Angular instance
var myApp = angular.module('myApp', ['ui.bootstrap', 'angularFileUpload']);
And add into your controller:
myApp.controller('appCtrl', ['$scope', 'FileUploader', function($scope, FileUploader) {
See the example on their Git page https://github.com/nervgh/angular-file-upload/blob/master/examples/simple/controllers.js

You need following ways.
If you have FileUploader.js file
track the files to your main html page after angular.js script before main.js(app.js)
Then configure it by this way
var myApp = angular.module('myApp', ['ui.bootstrap', 'fileUpload']);
myApp.controller('appCtrl', ['$scope', 'fileUpload', function ($scope, fileUpload) {
// Your code
}]);
If you have any doubt, please see this discussion :- Injecting Dependencies in config() modules - AngularJS

From the angular-file-upload wiki:
Add the dependency in your module declaration, these will be all the angular modules your application needs.
var myApp = angular.module('myApp', ['ui.bootstrap', 'angularFileUpload']);
To use its components in your controller you'll have also to inject FileUploader so you can access its API.
myApp.controller('appCtrl', ['$scope', 'FileUploader', function ($scope, FileUploader) {

You should write it like following:
var myApp = angular.module('myApp', ['ui.bootstrap', 'angular-file-upload']);
That's it. The dependence module should work fine.

You have to add the file to your angular.module:
var myApp = angular.module('myApp', ['ui.bootstrap', 'angular-file-upload']);
And import the file (for example in your index.html):
<script src="yourpath/ui-bootstrap-tpls.js"></script>
<script src="yourpath/angular-file-upload.js"></script>
If you correctly install your dependency, it should works :)

Related

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) {
};
}]);

Using Browserify with Angular JS - - Passing a service into a Controller

As the title suggests I've recently started a new project where I'm using Browserify (and Gulp) to concatenate my Angular JS files (and the Angular sourcefile) into a single file - bundle.js.
I've decided to split my controllers, services and directives into separate files and then "require" them into my app.js file using Browserify like this:
(function () {
'use strict';
require('angular');
var tabCtrl = require('./controllers/tabs'),
dataService = require('./services/');
angular.module("citiToolsApp", [])
.service('dataService', ['$scope', dataService])
.controller('TabController', ['$scope', tabCtrl]);
}());
However when I try to access my service - dataService - from within my Tab Controller like this:
module.exports = function($scope, tabController) {
dataService.getPrograms(function (response) {
console.log(response.data);
});
};
I get an undefined error. I believe I need to pass dataService into the tabController but I'm unsure on the syntax to do this. Can anyone help with this?
Thanks
EDIT
I've also added the contents of my service file for further detail:
module.exports = function($http) {
this.getPrograms = function(callback) {
$http.get('/programs')
.then(callback);
};
};
I've realised my own mistake. I needed to pass in $http rather than $scope. So instead of:
(function () {
'use strict';
require('angular');
var tabCtrl = require('./controllers/tabs'),
dataService = require('./services/');
angular.module("citiToolsApp", [])
.service('dataService', ['$scope', dataService])
.controller('TabController', ['$scope', tabCtrl]);
}());
It should be:
(function () {
'use strict';
require('angular');
var tabCtrl = require('./controllers/tabs'),
dataService = require('./services/');
angular.module("citiToolsApp", [])
.service('dataService', ['$http', dataService])
.controller('TabController', ['$scope', tabCtrl]);
}());

Split controllers into separate files

I had an angular setup that looked like this:
var dashboard = angular.module('Dashboard', ["ngRoute", "highcharts-ng"]);
dashboard.config(function($routeProvider, $locationProvider){
$routeProvider.when('/route1', {
templateUrl: 'route1.html',
controller: 'DefaultCtrl'
});
})
.controller('DefaultCtrl', function($scope, $rootScope, $http, settings){
function($scope, $rootScope, $http, settings){
$http.get("http://admin.gmserver.net/games/all?userId=" + settings.userId).success(function(data){
$scope.games = data;
$rootScope.gameId = "";
$rootScope.gameName = "";
$rootScope.apiName = "";
$rootScope.$broadcast("loaded");
});
}
})
And this worked. I then tried to split them up into multiple files (one for each controller), and now it looks like this:
module file:
angular.module('Dashboard', ["ngRoute", "highcharts-ng"]);
angular.module('Dashboard').config(['$routeProvider', '$locationProvider',
function($routeProvider, $locationProvider){
$routeProvider.when('/route1', {
templateUrl: 'route1.html',
controller: 'DefaultCtrl'
});
}
])
controller file:
angular.module('Dashboard').controller("DefaultCtrl", ['$scope', '$rootScope', '$http', 'settings',
function($scope, $rootScope, $http, settings){
$http.get("http://admin.gmserver.net/games/all?userId=" + settings.userId).success(function(data){
$scope.games = data;
$rootScope.gameId = "";
$rootScope.gameName = "";
$rootScope.apiName = "";
$rootScope.$broadcast("loaded");
});
}
]);
Now when I load the page I get this:
I am loading the files like this:
<script src="http://code.highcharts.com/adapters/standalone-framework.js"></script>
<script src="http://code.highcharts.com/highcharts.js"></script>
<script src="/media/js/highcharts-ng.min.js"></script>
<!-- Begin app code -->
<script src="/admin/Dashboard.js"></script>
<!-- Built with smarty -->
<script>
angular.module('Dashboard').value("settings", {
userId: "{$userId}",
secret: "{$secret}"
});
</script>
<script src="/admin/components/default/DefaultController.js"></script>
<script src="/admin/components/game/GameController.js"></script>
<script src="/admin/components/leaderboard/LeaderboardController.js"></script>
<script src="/admin/components/newsFeed/NewsFeedController.js"></script>
I do notice that commenting out one of the following stops the Aw, Snap error.
DefaultController.js file
Inline JavaScript
highcharts-ng.min.js file
Edit:
I changed the name of the module to my site's name and made the Dashboard a dependency like this:
angular.module('GMServer', ["ngRoute", "highcharts-ng", "Dashboard"]);
angular.module('Dashboard')
This fixes the "Aw, Snap" issue, but now I get this error: https://docs.angularjs.org/error/$injector/nomod?p0=Dashboard
I'm not entirely sure what happens when you call the same angular.module several times but I would avoid it.
You want to save the module globally so then you can reference it in different files instead of calling angular.module('Dashboard') each time:
window.Dashboard = angular.module('Dashboard', ["ngRoute", "highcharts-ng"]);
window.Dashboard.config(['$routeProvider', '$locationProvider',
function($routeProvider, $locationProvider){
$routeProvider.when('/route1', {
templateUrl: 'route1.html',
controller: 'DefaultCtrl'
});
}
])
and
window.Dashboard.controller("DefaultCtrl", ['$scope', '$rootScope', '$http', 'settings',
function($scope, $rootScope, $http, settings){
$http.get("http://admin.gmserver.net/games/all?userId=" + settings.userId).success(function(data){
$scope.games = data;
$rootScope.gameId = "";
$rootScope.gameName = "";
$rootScope.apiName = "";
$rootScope.$broadcast("loaded");
});
}
]);
You'll just need to make sure your <script> tags are included in the correct order.
Avoid polluting the window object though, you may wanna namespace everything under window.App or use someting like requireJS or Browserify.
Edit
It's perfectly safe to retrieve a module like the OP is doing as pointed out #Sunil and documented here

Loading config file in Angular, before everything else

I want to load config file in Angular application, only the first time when application is opened. Then config variables become globally available across the application. Here is what I come up so far in my app.js:
angular
.module('myApp', [
...
])
.run(
[ '$rootScope', '$http',
function ($rootScope, $http) {
$http.get('config/config.json').success(function(data) {
$rootScope.config = data;
});
}
]
)
Here I load the config.js and when I try to use it in my controller like so:
angular.module('myApp')
.controller('MainCtrl', function ($rootScope) {
console.log($rootScope, $rootScope.config);
})
For $rootScope I can see all properties including config, but $rootScope.config returns undefined.
How to load config file on first page load and then make it accessible throughout the app?
Thanks!
As described in Mark Colemans blog post about this, you can get your config and then load the application. Pasting Mark's code for convenience:
var urlToCheck = '/echo/json/';
var myApp = angular.module('myApp', []);
myApp.controller("MyCtrl", ["$scope", "config", function ($scope, config) {
$scope.url = config.url;
}]);
$.ajax({
url: urlToCheck
}).fail(function () {
myApp.constant('config', {
url: '/fail-url'
});
}).done(function () {
myApp.constant('config', {
url: '/done-url'
});
}).always(function () {
angular.bootstrap(document, ['myApp']);
});
You can initialize it to a promise and then access it in the controller when the promise is resolve. reject the promise too.
http://plnkr.co/edit/EIBJhZg80lpeyhkMD3FD
$q.when($rootScope.config).then(function (config) {
console.log($rootScope.config, config);
});

AngularJS Modular Set up

Up until recently, I have been throwing all my function into one large JS file. I am now trying to break these into small modules to make my application more portable per say.
I have my core js file (main.js) with the following code:
var App = angular.module("app", ['ui.bootstrap', 'angularMoment', 'chieffancypants.loadingBar', 'ngAnimate', 'ui.sortable', 'ngSanitize'], function ($interpolateProvider, $httpProvider) {
$interpolateProvider.startSymbol('[[');
$interpolateProvider.endSymbol(']]');
$httpProvider.defaults.transformRequest = function (data) {
if (data === undefined) {
return data;
}
return $.param(data);
};
$httpProvider.defaults.headers.post['Content-Type'] = ''
+ 'application/x-www-form-urlencoded; charset=UTF-8';
$httpProvider.defaults.headers.post['X-Requested-With'] = ''
+ 'XMLHttpRequest';
});
In another file (i.e. blog.module.js), I have the following:
(function(window, angular, undefined) {
'use strict';
angular.module("app", [])
.controller('Blog', ['$scope', function ($scope) {
alert('test');
}]);
});
While the main.js file loads along with all its dependencies, the second one doesn't get loaded. The controller is basically not found. Can anyone give me pointers as to where I may be going wrong.?
Thanks
The sintax in blog.module.js looks like you are trying to create two modules with same name 'app'.
Change your controller module like this
(function(window, angular, undefined) {
'use strict';
angular.module("app")
.controller('Blog', ['$scope', function ($scope) {
alert('test');
}]);
});
I quote you :
App = angular.module("app", ['ui.bootstrap',
...
angular.module("app", [])
You cant redeclare a module you can either reopen it
App = angular.module("app", ['ui.bootstrap',
...
angular.module("app")
or create another one
App = angular.module("app", ['ui.bootstrap', 'app.controller'
...
angular.module("app.controller")

Categories

Resources