js1.js
app.controller('test1Controller',
function($scope,$http,$ngBootbox,$location,CRUDService,NotificationService,constants,ngWizard) {
$scope.fun1 = function(){
$http.get(context+"/back/demande/rest/test1").success(function(data, status) {
$scope.dto = data;
});
};
});
js2.js
app.controller('test2Controller',
function($scope,$http,$ngBootbox,$location,CRUDService,NotificationService,constants,ngWizard) {
$scope.fun2 = function(){
$http.get(context+"/back/demande/rest/test2").success(function(data, status) {
$scope.dto = data;
});
};
});
How can I call fun1 => js1.js in js2.js?
First, you need to move your function to angular.js service instance.
Then you need to inject this service to your controllers, like NotificationService.
Then you can call in different controllers.
app.service('myHttpService', ['$http', function($http) {
this.getData = function(context, endpoint) {
return $http.get(context+"/back/demande/rest/" + endpoint);
};
}]
// do not forget to use injector if you don't have ngAnnotate
app.controller('test2Controller', function($scope, $http, $ngBootbox, $location, CRUDService, NotificationService, constants, ngWizard, myHttpService) {
$scope.dto = null;
$scope.fun2 = function(){
myHttpService.getData(context, 'test1')
.then(function(data, status) {
$scope.dto = data;
});
};
});
Related
After trying some solutions like this: Aborting ngResource using a promise object I'm unable to cancel a request made with $resource.
My last try was with this:
Controller:
angular.module('theApp')
.controller('homeController', function ($q, foodTypeFactory) {
var vm = this;
vm.testButton = function () {
vm.aborter = $q.defer();
foodTypeFactory(vm.aborter).getTest({}, function (data) {
console.log(data);
});
};
vm.cancelButton = function () {
vm.aborter.resolve();
}
});
foodTypeFactory:
angular.module('theApp')
.factory('foodTypeFactory', function ($resource, BACKEND_API) {
return function (aborter) {
return $resource(BACKEND_API + '/api/foodtypes/:id', {id: '#id'}, {
getTest: {
timeout: aborter.promise
}
});
}
});
Once the request is made it completes even if I try to cancel it.
I'm using Angular 1.6.2 with angular-resource 1.6.2.
What am I doing wrong?
What i Can suggest to you is to use an http interceptor .. the you can stop a request... somthing like this:
1) create a file like (auth.interceptor.js:
"use strict";
angular
.module("demo")
.factory('authInterceptorService', ['$q', '$location', 'localStorageService',
function ($q, $location, localStorageService) {
// Public Method
return {
request: function (config) {
config.headers = config.headers || {};
if(!MYCONDITION){ //<-- you can here your logic to test if conitnue request flow or not
return; //<-- TERMINATE IT ..
}else{
return config; //<-- CONTINUE WITH NORMAL REQUEST
}
}
};
}]);
2) in your app.config.js file:
$httpProvider.interceptors.push("authInterceptorService");
Then in ALL your request (via $http or via $resource) this logic is apply ... here you can also put the injection of the Bearer Token if you need it
Hope it help you
Finally I found a solution!
From angular 1.5 $resource can be cancelled with $cancelRequest().
In my case:
Controller:
angular.module('theApp')
.controller('homeController', function (foodTypeFactory) {
var vm = this;
vm.testButton = function () {
vm.onGoingRequest = foodTypeFactory.getTest({}, function (data) {
console.log(data);
});
};
vm.cancelButton = function () {
vm.onGoingRequest.$cancelRequest();
}
});
foodTypeFactory:
angular.module('theApp')
.factory('foodTypeFactory', function ($resource, BACKEND_API) {
return $resource(BACKEND_API + '/api/foodtypes/:id', {id: '#id'}, {
getTest: {
cancellable: true
}
});
});
In my voting app I'm just updating a simple ng-repeat with calls to my API to create, and delete polls. I had this working perfectly when all of my $http calls were in my controller but when I try to modularize my code with a service it doesn't update properly.
I don't fully understand promises, but I did some searches on here to see if that would work, but I didn't make any progress..
Service:
/* global app */
app.factory("pollsService", ["$http", function($http){
return {
get: $http.get('api/polls').success(function(data) {return data;}),
deletePoll: function(id, cb) {
$http.delete('/api/polls/' + id)
.success(function(results) {
cb(results);
})
.error(function(err) {
throw err;
});
},
createPoll: function(formData, cb) {
$http.post('/api/polls', formData)
.success(function(results) {
cb(results);
})
.error(function(err){
throw err;
});
}
}
}]);
Controller:
/* global app */
app.controller("mainController", ["$scope", "pollsService", function($scope, pollsService){
$scope.formData = {};
pollsService.get
.success(function(results){
$scope.polls = results;
})
.error(function(err){
alert(err);
})
$scope.removePoll = function(id) {
pollsService.deletePoll(id, function(results){
$scope.polls = results;
})
}
$scope.createPoll = function() {
pollsService.createPoll($scope.formData, function(results){
$scope.polls = results;
$scope.formData = {};
})
}
}]);
My calls still work but I have to refresh the browser to get my updated data when I click on the newly created poll, or delete a poll.
Any help would be much appreciated!
I would suggest using service structure instead of factory. Also why don't you use $resource service? It could be solved easily with this approach:
/* global app */
angular.service("pollsService", function($resource){
this.get = get;
this.deletePoll = deletePoll;
this.createPoll = createPoll;
function get(){
return $resource('api/polls', {}).query().$promise;
}
function deletePoll(params){
return $resource.delete('/api/polls/:id', {id: params.id}).remove().$promise;
}
function createPoll(formData){
return $resource.post('/api/polls', {}).save(formData).$promise
}
})
---- CTRL
app.controller("mainController", ["$scope", "pollsService", function($scope, pollsService){
$scope.formData = {};
pollsService.get().then(function(data){
$scope.polls = results;
}, function(error){
})
$scope.removePoll = function(id) {
pollsService.deletePoll({id: id}).then(function(results){
$scope.polls = results;
}, function(error){
// error here
})
}
$scope.createPoll = function() {
pollsService.createPoll($scope.formData).then(function(data){
$scope.polls = results;
$scope.formData = {};
}, function(error){
});
}
}]);
in order for ng-repeat to update the existing view with your new data - you will need to add $scope.$apply(); after the data has been updated.
Hope this helps.
I did pretty simple plunker to show my problem. The problem is I have variable and I want to populate this variable with initial app loading, I did angular services for this purpose, but for some reason angular services doesn't fire inside controller. Where is my mistake?
app.controller('MainCtrl', function($scope, optService) {
$scope.priority = [];
var exeService = function() {
console.log('function fired')
// this is firing
optService.myOptions(function (result) {
console.log('service fired')
// this is not firing
angular.forEach(result, function(value) {
$scope.priority.push({value: value.name, label: value.name});
});
});
}
exeService()
console.log($scope.priority)
// shows an empty array
});
services
(function () {
angular.module("app").factory("optService", ["$http", "$rootScope", "$q", "$log",
function ($http, $rootScope, $q, $log) {
var clearApi = "test.json";
function myOptions () {
return $http.get(clearApi)
.then(function (response) {
console.log(response.data)
// shows an array
return response.data;
});
}
return {
myOptions: myOptions
}
}])
}());
You should do the service declaration like that:
app.controller('MainCtrl', ['$scope', 'optService', function($scope, optService) {
and in the controller
optService.myOptions().then(function (result) {
console.log('service fired')
angular.forEach(result, function(value) {
$scope.priority.push({value: value.name, label: value.name});
});
});
I am mostly a PHP coder and have VERY VERY limited dealing with jquery.
I am showing a banner ad based upon the end users' location. I'm using a AngularJS script to return the users zip code: http://jsfiddle.net/kL50yeek/21/
I'm using the follow ajax code to load the right banner ad based upon the zip provided:
<div id="adspaceNetwork_sponsored_bank"></div>
<script>
$('#adspaceNetwork_sponsored_bank').load("https://ia.lc/~creative/?
zip=02481");
</script>
You can see the code demo here: https://jsfiddle.net/cdLw0c48/22/
How do I pass the zipCode Var to the ajax load request?
This doesn't work: $('#adspaceNetwork_sponsored_bank').load('https://ia.lc/~creative/?zip='+zipCode);
I've update your jsfiddle here with angularjs bindings:
Here is your updated controller:
app.controller('MainCtrl', ['$scope', '$http', '$sce', 'ZipCodeLookupSvc',
function($scope, $http, $sce, ZipCodeLookupSvc) {
$scope.zipCode = null;
$scope.message = 'Finding zip code...';
ZipCodeLookupSvc.lookup().then(function(zipCode) {
$scope.zipCode = zipCode;
$http.get('https://ia.lc/~creative/?zip='+zipCode).success(function(res) {
$scope.banner = $sce.trustAsHtml(res);
});
}, function(err) {
$scope.message = err;
});
}]);
After we get the zipCode via ZipCodeLookupSvc, we use a $http.get call to fetch the banner, and set it as $scope.banner for use in your html code.
I updated your code and transferred the load call.
app.controller('MainCtrl', ['$scope', 'ZipCodeLookupSvc', function($scope, ZipCodeLookupSvc) {
$scope.zipCode = null;
$scope.message = 'Finding zip code...';
ZipCodeLookupSvc.lookup().then(function(zipCode) {
$scope.zipCode = zipCode;
$('#adspaceNetwork_sponsored_bank').load('https://ia.lc/~creative/?zip=' + zipCode);
}, function(err) {
$scope.message = err;
});
}]);
There are multiple problems in your handling of promises
(function (angular) {
'use strict';
var app = angular.module('MyApp', []);
app.factory('GeolocationSvc', ['$q', '$window', function ($q, $window) {
return function () {
var deferred = $q.defer();
if (!$window.navigator) {
deferred.reject(new Error('Geolocation is not supported'));
} else {
$window.navigator.geolocation.getCurrentPosition(function (position) {
deferred.resolve({
lat: position.coords.latitude,
lng: position.coords.longitude
});
}, deferred.reject);
}
return deferred.promise;
};
}]);
app.factory('ZipCodeLookupSvc', ['$q', '$http', 'GeolocationSvc', function ($q, $http, GeolocationSvc) {
var MAPS_ENDPOINT = 'https://maps.google.com/maps/api/geocode/json?latlng={POSITION}&sensor=false';
return {
urlForLatLng: function (lat, lng) {
return MAPS_ENDPOINT.replace('{POSITION}', lat + ',' + lng);
},
lookupByLatLng: function (lat, lng) {
var deferred = $q.defer();
var url = this.urlForLatLng(lat, lng);
$http.get(url).success(function (response) {
// hacky
var zipCode;
angular.forEach(response.results, function (result) {
if (result.types[0] === 'postal_code') {
zipCode = result.address_components[0].short_name;
}
});
deferred.resolve(zipCode);
}).error(deferred.reject.bind(deferred));
return deferred.promise;
},
lookup: function () {
var deferred = $q.defer();
var self = this;
GeolocationSvc().then(function (position) {
self.lookupByLatLng(position.lat, position.lng).then(function (zipCode) {
console.log('p')
deferred.resolve(zipCode);
}, deferred.reject.bind(deferred))
}, deferred.reject.bind(deferred));
return deferred.promise;
}
};
}]);
app.controller('MainCtrl', ['$scope', 'ZipCodeLookupSvc', function ($scope, ZipCodeLookupSvc) {
$scope.zipCode = null;
$scope.message = 'Finding zip code...';
ZipCodeLookupSvc.lookup().then(function (zipCode) {
$scope.zipCode = zipCode;
console.log(zipCode)
$('#adspaceNetwork_sponsored_bank').load('https://ia.lc/~creative/?zip=' + $scope.zipCode);
}, function (err) {
$scope.message = err;
});
}]);
})(angular);
Demo: Fiddle
This is the code of one controller from my application, in the User page.
app.controller('UserCtrl', ['$scope', '$http', function ($scope, $http) {
$http.get('/Users/GetUsers').success(function (data) {
$scope.data = data;
});
this.search = function () {
$http.post('/Users/SearchUser', $scope.search).success(function (data) {
$scope.data = data;
});
}
this.delete = function() {....}
}]);
On another page, the Permission page, I create a controller with the same logic
app.controller('PerCtrl', ['$scope', '$http', function ($scope, $http) {
$http.get('/Permission/GetPermissions').success(function (data) {
$scope.data= data;
});
this.search = function () {
$http.post('/Permission/SearchPermission', $scope.search).success(function (data) {
$scope.data = data;
});
}
this.delete = function() {....}
}]);
As you can see, the only different is the URL. How can I reuse the logic from a controller to another?
That is exactly what services are for.
So instead of:
$http.get('/Permission/GetPermissions').success(function (data) {
$scope.data= data;
});
You'd call something like:
permissionsService.get().then(function (data) {
$scope.data= data;
});
And:
this.search = function () {
$http.post('/Permission/SearchPermission', $scope.search).success(function (data) {
$scope.data = data;
});
}
Replaced with something like:
this.search = function () {
searchService.search().then(function (data) {
$scope.data = data;
});
}
etc...
Generally, all server calls should be in services anyway, so there's a great opportunity to improve your code and learn how to do it right.