I want to move this function to services.js:
News.all().async().then(function(data) {
$scope.news = data['data']['NewsList'];
});
And than call it in controller.js by this command:
$scope.news = News.all();
I try many ways, but them did not work.
Here is my services.js:
.factory('News', function($http) {
function returnNews() {
return {
async: function() {
return $http.get('test.json');
}
};
}
return {
all: function() {
return returnNews();
}
}
});
Well if you call News.all() in the end you will get an object with an async property: {async} and I don't think this is what you want. What you can do is pass a callback to the service:
.factory('News', function($http) {
return {
all: function(callback) {
return $http.get('test.json').then(callback);
}
}
});
and in the controller you have to do:
News.all(function(data){
$scope.news = data
});
Related
I have an AngularJs application working with components and several modules. I created a plunker example to present my problem here.
I have my NavbarComponent where I declared my Controller where I inject my service called NavbarService.
In the NavbarService, I inject a factory resource to make my Rest call, once this call is made I'm trying to made some treatment on the response before returning it back to the controller, in this example I just apply a simple filter on it, but it doesn't work. If I omit my treatment and return only the categories, the code works and you can visualize a list of two.
I can make my treatment in the controller but this is a bad practice 'cause I believe it should be done in the Service, secondly since it's an asynchronous response I must do something like this to make it work, which is really really ugly:
navbarService.getCategories().$promise.then(function (response) {
console.log("controller", response[0].category);
vm.categories = categoryFilter(response[0].category);
}, function (error) {
console.log("an error occured");
});
Can someone please guide me through this, I'm out of solutions. Thank you
Another simple way is to pass a callback function to service from you component like this
'use strict';
angular.module('navbar').component('appNavbar', {
templateUrl: "navbar.template.html",
controller: [ 'navbarService', function appNavbarController(navbarService) {
var vm = this;
navbarService.getCategories(function(data){
// this will be called when service will get the response and filter function has filtered the response
vm.categories = data;
});
}]
});
Now service should be like this
'use strict';
angular.module('navbar').service('navbarService', ['categoryResourceService', 'categoryFilter', function(categoryResourceService, categoryFilter) {
var vm = this;
vm.getCategories = function(callback) {
categoryResourceService.query(function(response) {
console.log("[NavbarService] response:", response);
callback(categoryFilter(response));
}, function(error) {
console.log("[NavbarService] error:", error);
});
//return vm.categories;
}
}]);
Filter will be like this
'use strict';
angular.module('navbar').filter('category', function() {
return function(categories) {
var categoryIds = ['World'];
var result = [];
angular.forEach(categoryIds, function (categoryId) {
angular.forEach(categories, function (category) {
if (category.name == categoryId) {
console.log("Match");
result.push(category);
}
});
});
return result;
};
});
Your filter should be like this and it should be called in transformResponse in $resource query instead of service, i hope this will help you
'use strict';
angular.module('navbar').filter('category', function() {
return function(categories) {
var categoryIds = ['World'];
var result = [];
angular.forEach(categoryIds, function (categoryId) {
angular.forEach(categories, function (category) {
if (category.name == categoryId) {
console.log("Match");
result.push(category);
}
});
});
return result;
};
});
Your categoryResource.service should be like this
angular.module('shared').factory('categoryResourceService',
['$resource','categoryFilter', function($resource, categoryFilter) {
var provider = "categories.json";
var params = {
id: '#id'
};
return $resource(provider, params, {
query: {
isArray: true,
method: 'GET',
params: {},
transformResponse: function(categories) {
var results = categoryFilter(angular.fromJson(categories));
console.log("[categoryResourceService] filtered response:", results);
return results;
}
}
});
}]);
navbar.service should be like this simply
'use strict';
angular.module('navbar')
.service('navbarService', [ 'categoryResourceService', function (categoryResourceService) {
var vm = this;
vm.getCategories = function(){
vm.categories = categoryResourceService.query(function(response){
console.log("[NavbarService] response:", response);
}, function(error){
console.log("[NavbarService] error:", error);
});
return vm.categories;
}
}]);
And components like this
'use strict';
angular.module('navbar').component('appNavbar', {
templateUrl: "navbar.template.html",
controller: [ 'navbarService', function appNavbarController(navbarService) {
var vm = this;
vm.categories = navbarService.getCategories();
}]
});
I want to fetch particular category by id. I have populated dummyjson data using $http method.I am unable to do this. I have pass id from my services to controller but it returns null. Here i my code
service.js:
(function() {
angular.module('myApp')
.factory('registerService', function ($http) {
var category=[];
return {
getAll:function(){
return $http.get('json/dummyJson.json').then(function(response){
category=response.data;
return category;
});
},
getUser:function(category_id)
{
for(var i=0;i<category.length;i++){
console.log(category.length);
if(category[i].id === parseInt(category_id)){
return category[i];
}
}
return null;
}
}
});
})();
controller.js:
(function() {
angular.module('myApp').controller('registrationCtrl1', function ($scope, $stateParams, registerService) {
console.log('inside registerCtrl2');
$scope.categoryName=registerService.getUser($stateParams.category_id);
console.log($stateParams.category_id);
console.log($scope.categoryName);
});
})();
You are assuming that category will have value within getUser, but that won't happen. The only place where category is populated is getAll, but since you are not calling getAll, category is not populated. Chnage your method as below and it will work:
getUser: function(category_id) {
return $http.get('json/dummyJson.json').then(function(response){
category=response.data;
for(var i=0;i<category.length;i++) {
console.log(category.length);
if(category[i].id === parseInt(category_id)){
return category[i];
}
}
return null;
});
}
Since your method returns a promise now you need to handle the promise in a callback in your controller:
angular.module('myApp').controller('registrationCtrl1', function ($scope, $stateParams, registerService) {
console.log('inside registerCtrl2');
registerService.getUser($stateParams.category_id)
.then(function (response) {
$scope.categoryName= response;
console.log($stateParams.category_id);
console.log($scope.categoryName);
});
});
I'm listing users with:
/api/users/
I'd like to list users who are admins by calling:
/api/users/admins
As trivial as it may seem, I can't find a way to do this.
I do not know which programming language you are using, but I'm going to give you an example using PHP Laravel, and AngularJS.
API
Route::get('/api/users', function ()
{
$users = App\User::all();
return $users;
});
Route::get('/api/users/admin', function ()
{
$users = App\User::where('admin', true)->get();
return $users;
});
FRONT
angular.module('app', [])
.service('api', ['$http', function ($http) {
function getUsers() {
return $http.get('/api/users');
}
function getAdminUsers() {
return $http.get('/api/users/admin');
}
this.getUsers = getUsers;
this.getAdminUsers = getAdminUsers;
}])
.controller('UserCtrl', ['$scope', 'api', function ($scope, api) {
$scope.users = [];
$scope.adminUsers = [];
api.getUsers()
.then(function success(response) {
$scope.users = response.data;
}, function error(response) {
});
api.getAdminUsers()
.then(function success(response) {
$scope.adminUsers = response.data;
}, function error(response) {
});
}]);
Sorry about the lack of details in my question. I was actually asking the question about the angular-restmod module.
Here's what I did in the end:
module.factory('CustomMethods', ['restmod', 'RMUtils', function CustomMethodsMixin(restmod, RMUtils) {
return restmod.mixin(function() {
this.define('Model.$customCollection', function(_url, params) {
var original = this;
return this.$collection(params, {
$urlFor: function() {
return RMUtils.joinUrl(original.$url(), _url);
}
});
});
return this;
});
}]);
And expose all my api to it:
restmodProvider.rebase('CustomMethods')
How can I wait with my function till the $http request is finished?
My services.js looks as follows:
var app = angular.module('starter.services', []);
app.factory('Deals', function($http) {
function getDeals() {
$http.get('http://www.domain.com/library/fct.get_deals.php')
.success(function (data) {
var deals = data;
return deals;
})
.error(function(err){
});
}
return {
all: function() {
return getDeals();
},
get: function(keyID) {
//...
}
}
});
My controllers.js looks like:
var app = angular.module('starter.controllers', []);
app.controller('DealCtrl', function($scope, Deals) {
$scope.deals = Deals.all();
console.log($scope.deals);
});
The console.log in my controllers.js file outputs "undefined", but when I output the deals in the getDeals() function it contains the correct array which I get from my server.
What am I doing wrong?
$http and all of the async services in angularjs return a promise object. See promise api.
You need to use then method to assign it to a value in the scope.
So your controller:
app.controller('DealCtrl', function($scope, Deals) {
Deals.all().then(function (deals) {
$scope.deals = deals;
console.log($scope.deals);
});
});
Your service
app.factory('Deals', function($http) {
function getDeals() {
return $http.get('http://www.domain.com/library/fct.get_deals.php')
.success(function (data) {
var deals = data;
return deals;
});
}
return {
all: function() {
return getDeals();
},
get: function(keyID) {
//...
}
}
});
Can i use one service into another angular service? Else what will be the best approach to accomplish the below?
First Service:
var app = angular.module("MyApp", []);
app.service('Service1', function () {
return {
FirstFunction: function () {
return "something";
}
}
});
Second service:
app.service('Service2', function () {
return {
SecondFunction: function () {
//How to use FirstFunction of Service1 ???
}
}
});
Thanks
app.service('Service2', function (Service1) {
return {
SecondFunction: function () {
Service1.FistFunction
}
}
});
As long as service2 doesnt depend on service1 there is no problem.
app.service('Service2', function (Service1) {
return {
SecondFunction: function () {
Service1.FirstFunction();
}
}
});