Getting the values in response as:
[{
"Pf": "something1",
"label": ""
}, {
"Pf": "something1",
"label": ""
}]
JS
$scope.display = false;
$scope.getPanel = $http({
mode: 'cors',
method: 'GET',
url: '/url/',
headers: {
'Content-Type': 'application/json'
}
}).success(function(response) {
$scope.original = function() {
angular.forEach(response, function(value, key) {
if (value == "something1") {
dispaly = false;
} else if (value == "something2") {
display = false;
} else {
display = true;
}
});
return display;
};
});
HTML
<td>
<img src="image.png" uib-tooltip="{{status}}" ng-show="original()"/>
</td>
not getting key and value from response
First of all, you do have an error in if display writing dispaly instead display.
Secondly, the angular foreach second argument is a function taking as first argument the iterator on your collection. Here, your collection is composed of two object, so on each iteration, value will be an object , for example :
{
"Pf": "something1",
"label": ""
}
So, if you want to test if it is equal to "something1", you have to compare it with value.pf and not value.
You also need to call response.data because response is a structure that stores different informations about your request answer.
To finish, i advice you to store the value display in your scope and bind it on ng-show directive like this :
JS
$scope.display = false;
$http({
mode: 'cors',
method: 'GET',
url: '/url/',
headers: {
'Content-Type': 'application/json'
}
}).success(function(response) {
angular.forEach(response.data, function(value, key) {
if (value.pf == "something1") {
$scope.display= false;
} else if (value.pf == "something2") {
display = false;
} else {
display = true;
}
});
});
HTML
<td>
<img src="image.png" uib-tooltip="{{status}}" ng-show="display"/>
</td>
Hope it helps !
Note that display get overwritten on each loop. Ensure your logic is correct. While display is an $scope variable you need to access this param by using $scope.display instead of display. Your codes should look like this:
View
<div class="container" ng-controller="ApplicationController">
<h1>Output: {{ display }}</h1>
<div ng-show="display">
Now I'm here
</div>
</div>
AngularJS application
var app = angular.module('plunker', []);
app.controller('ApplicationController', function($scope, $http) {
$scope.display = false;
$scope.getPanel = $http({
mode: 'cors',
method: 'GET',
url: './data.json',
headers: {
'Content-Type': 'application/json'
}
}).success(function(response) {
original(response);
});
function original (response) {
angular.forEach(response, function(value, key) {
if (value.Pf == "something1") {
$scope.display = false;
} else if (value.Pf == "something2") {
$scope.display = false;
} else {
$scope.display = true;
}
});
console.log($scope.display);
};
});
--> Demo plnkr
Related
I asked this question before (AngularJS handle calling promise multiple times) and now I have different obstacle. Now I have to get cities list but there is an exception.
Cities can be called multiple times like countries (in my old question) and I have to cache data to prevent multiple calls for same data(cities). Old question's solution can block multiple calls but now I have to let some calls (for new country's cities).
So my question is:
How can I cache cities data to prevent call for same data?
(My function have to catch if call is for new country's cities list or not. if yes: call service and get cities, if not: return cities from cache)
Here is my service:
var cityCache = {};
vm.getCities = function (countryCode) {
if (countryCode!=undefined && !cityCache[countryCode]) {
vm.cityPromise = $http({
method: 'POST',
cache: true,
url: API + '/api/Global/CountryCities',
data: {
"CountryCode": countryCode
}
}).then(function successCallback(response,countryCode) {
if (errorHandler(response.data)) {
console.log("cities come from ajax")
cityCache[response.config.data.CountryCode] = response.data;
console.log(cityCache)
return response.data
}
});
} else {
vm.cityPromise = $timeout(function () {//I use this to get promise object
return cityCache[countryCode]
}, 0)
console.log("cities comes from cache");
}
return vm.cityPromise;
}
Example:
Let's say I am calling getCities function 3 times in the same time. I am watching my network traffic via chrome. I see 3 ajax calls. It's normal. But sometimes, I call for same city. I need to edit my function that can understand if city data is already called before (kind of cache). For example: If i ask function 3 times with this arguments:
1-Give me the cities in Germany,
2-Give me the cities in Ireland,
3-Give me the cities in Germany (again),
It's calling 3 times. But I want 1 call for Germany, 1 call for Ireland. Just 2 calls.
Same answer as your other question, just map to country code to the promise.
Also same as before, consider the error case.
var vm = this;
vm.cityPromises = {};
function getCities(countryCode) {
if (!vm.cityPromises[countryCode]) {
vm.cityPromises[countryCode] = $http({
method: 'POST',
cache: true,
url: API + '/api/Global/Countries',
}).then(function successCallback(response) {
if (errorHandler(response.data)) {
console.log("ajax")
return response.data;
}
});
} else {
console.log("cache")
}
return vm.cityPromises[countryCode];
}
You can use your own promise here. Don't forget injecting the $q service.
var cityCache = {};
vm.getCities = function (countryCode) {
var deferred = $q.defer();
if (countryCode!=undefined && !cityCache[countryCode]) {
vm.cityPromise = $http({
method: 'POST',
cache: true,
url: API + '/api/Global/CountryCities',
data: {
"CountryCode": countryCode
}
}).then(function successCallback(response,countryCode) {
if (errorHandler(response.data)) {
cityCache[response.config.data.CountryCode] = response.data;
deferred.resolve(response.data);
}
else{
deferred.reject();
}
});
}
else {
vm.cityPromise = $timeout(function () {//I use this to get promise object
deferred.resolve(cityCache[countryCode]);
}, 0);
}
return deferred.promise;
}
Try to use the $q service from angular:
updated to prevent multiple call of same city:
FIDDLE
the service:
.service("cityService", function($http, $q, $httpParamSerializerJQLike){
//var callCache = {};
var cityCache = {};
return {
getCities: function(countryCode){
//if(callCache[countryCode] === undefined){
var promise = $q.defer();
// callCache[countryCode] = promise;
//}else{
// console.log("return cached promise!!", callCache[countryCode]);
// return callCache[countryCode].promise;
//}
if (countryCode!=undefined && !cityCache[countryCode]) {
console.log("new city");
var data = $httpParamSerializerJQLike({
json: JSON.stringify({
name: countryCode+Math.random().toString(36).substring(7)
})
});
$http({
method: 'POST',
url:"/echo/json/",
data: data
}).then(function(risp) {
console.log("servicelog",risp.data);
cityCache[countryCode] = risp.data;
var obj = angular.extend({cache: false}, risp.data);
promise.resolve(obj);
//callCache[countryCode].resolve(obj);
//delete callCache[countryCode];
});
}else{
setTimeout(function(){
var obj = angular.extend({cache: true}, cityCache[countryCode]);
promise.resolve(obj);
//callCache[countryCode].resolve(obj)
//delete callCache[countryCode];
}, 1000)
}
return promise.promise;
}
}
});
I solved my problem by creating an object for the promise and many thanks to #Luke Harper for helping me before and now :) His answer is also correct but I must add a bit more code for my app.
If you see any problem in my code, please write to me so that I would edit the answer
So here is my solution:
vm.cityPromise = {};
vm.getCities = function (countryCode) {
vm.cityPromise["cityCache"] = countryCode;
if (!vm.cityPromise[countryCode]) {
if (countryCode != undefined && !cityCache[countryCode]) {
vm.cityPromise[countryCode] = $http({
method: 'POST',
cache: true,
url: API + '/api/Global/CountryCities',
data: {
"CountryCode": countryCode
}
}).then(function successCallback(response, countryCode) {
if (errorHandler(response.data)) {
cityCache[response.config.data.CountryCode] = response.data;
console.log("cities ajax, cityCache", cityCache)
return response.data
}
},function error (response){
console.log ("error:",response)
});
} else {
vm.cityPromise[countryCode] = $timeout(function () {
return cityCache[countryCode]
}, 0)
console.log("getCities cache");
}
}
return vm.cityPromise[countryCode];
}
If i access the link http://localhost/cgi-bin/superCategory.pl?action=GET
I will get this data:
[{"name":"Baby Care","id":"2","image":"/images/categories/baby-care.png"},{"name":" Bread, Bakery & Dairy Products","id":"5","image":"/images/categories/dairy-products.png"},{"name":"Beverages","id":"6","image":"/images/categories/beverages.png"},{"name":"Others","id":"9","image":"/images/categories/others.png"}]
But when i try to get the same data using AngularJS service and controller, I m not getting the data. This is my controller and service code.
sampleApp.factory('SuperCategoryService', ['$http', function ($http){
var req = {
method: 'POST',
url: 'http://localhost/cgi-bin/superCategory.pl',
headers: { 'Content-Type': 'application/x-www-form-urlencoded' },
data: { action: 'GET' }
};
return {
GetSuperCategories: function () {
return $http(req).then(
function(response)
{
if (typeof response === 'object')
{
return response;
}
else
{
alert ('wrong');
}
},
function(response) {
alert ('again worng');
// something went wrong
//return $q.reject(response.data);
});
}
};
}]);
sampleApp.controller('SuperCategoryController', function ($scope,SuperCategoryService) {
$scope.SuperCategories = [];
$scope.GetSuperCategories = function() {
SuperCategoryService.GetSuperCategories().then(
function(d) {
alert (d);
if (d !== undefined) {
alert ('in');
console.log(d);
$scope.SuperCategories = d;
}
else {
alert ('undefined data');
}
},
function(response) {
alert ('error worng');
// something went wrong
//return $q.reject(response.data);
});
};
$scope.GetSuperCategories();
});
though code is reaching to alert ('in'), but nothing is getting assigned to variable $scope.SuperCategories;
Can some one help me what i m doing wrong in assignment.
Your service function is doing $http using .then which is nothing but resolving using chain promise you should get explicit data from object you service will return response.data instead of response
GetSuperCategories: function () {
return $http(req).then(
function(response)
{
var data = response.data;
if (typeof data === 'object')
{
return data ;
}
else
{
alert ('wrong');
}
},
function(response) {
alert ('again worng');
// something went wrong
//return $q.reject(response.data);
});
}
};
I am using a angular $resource like the one below.
angular.module('app')
.factory('data', function ($resource) {
var Con = $resource('/api/data', {}, {
update : {method : 'PUT'}
});
return {
getData : function (user_id, callback) {
return Con.query({user_id : user_id}, function (data) {
cb(data); // (breakpoint) HERE data is not good
}, function (err) {
cb(err);
}).$promise;
}
};
});
This is what I get when a put a breakpoint on data :
[
['w','e','l','c','o','m','e'],
['h','e','l','l','o']
]
howerver, the server sends :
['welcome','hello']
anyone know why the strings get split?
Thank you
You've run into a fun bug with angular's $resource where it cannot handle a raw array of strings; as a workaround, you can do one of three things:
use the $http service instead
send an object-wrapped response via the server eg: { "stuff" : [ "your", "strings" ] }
force the response data into the above format client-side; $resource eg: methodName: {method:'GET', url: "/some/location/returning/array", transformResponse: function (data) {return {list: angular.fromJson(data)} }} and then access it as data.list
See my answer at https://stackoverflow.com/a/22491240/626810
This works for RAW response. This is a slightly different version from the answer above but this is generic and is not only dependent on JSON response. This will basically mutate RAW response to String format. You will need to access $resource promise result as result.responseData
getAPIService() {
return this.$resource(this.apiUrl, {}, {
save: {
method: 'POST',
headers: {
'Accept': 'text/plain, text/xml',
'Content-Type': 'text/xml'
},
transformResponse: function (data) { return { responseData: data.toString() } }
}
});
}
Use $http instead of $resource
getRiskCount: function (Id,Type) {
var deferred = $q.defer();
var resource = $resource(urlResolverFactory.hostUrl() + '/api/getstudentriskcount',
{}, { query: { method: 'GET', isArray: false } }
);
resource.query({ userId: Id,userType: Type }, function (data) {
deferred.resolve(data);
}, function (error) {
deferred.reject(error);
});
return deferred.promise;
}
Result - ['4','5','6','7']
getRiskCount: function (Id,Type) {
var apiUrl = urlResolverFactory.hostUrl() + '/api/getstudentriskcount';
apiUrl += '?userId=' + Id,
apiUrl += '&userType=' + Type;
var deferred = $q.defer();
var promise = $http({
method: 'GET',
url: apiUrl,
}).success(function (data) {
deferred.resolve(data);
}).error(function (data, status) {
deferred.reject(data);
});
return promise;
}
Result - [4567]
Thanks for all your input, but now I have more or less a similar problem, I have the data that needs to be stored in sql-server database, when I try to post it the data does not get written. Is my code structure correct?
self.CurrentDowntimeEvent = {
method: 'POST'
, url: 'someurl/test'
, data: {
DepartmentId: cookie
, CategoryId: -1
, Comment: ""
, DowntimeStart: "2014-07-07T10:00:00"
, DowntimeEnd: null
}
, headers: {'Content-Type':'application/x-www-form-urlencoded; charset=UTF-8'}
}).success(function (data) {
console.log(data);
}).error(function (data) {
});
$http is a service which should be injected into the controller, so you shouldn't need self. to reference it:
self.RecordsSave = function () {
for (var i = 0; i < self.Employees.length; i++) {
var employee = self.Employees[i];
var params = {
CompanyNumber: employee.ClockNumber,
Department: employee.DepartmentID,
Present: employee.Present,
Reason: employee.AbsentCode
};
$http.post(SAVE_EMPLOYEERECORDS, {
params: params
}).success(function (data) {
alert("testing");
});
}
};
I have a function which does a http POST request. The code is specified below. This works fine.
$http({
url: user.update_path,
method: "POST",
data: {user_id: user.id, draft: true}
});
I have another function for http GET and I want to send data to that request. But I don't have that option in get.
$http({
url: user.details_path,
method: "GET",
data: {user_id: user.id}
});
The syntax for http.get is
get(url, config)
An HTTP GET request can't contain data to be posted to the server. However, you can add a query string to the request.
angular.http provides an option for it called params.
$http({
url: user.details_path,
method: "GET",
params: {user_id: user.id}
});
See: http://docs.angularjs.org/api/ng.$http#get and https://docs.angularjs.org/api/ng/service/$http#usage (shows the params param)
You can pass params directly to $http.get() The following works fine
$http.get(user.details_path, {
params: { user_id: user.id }
});
Starting from AngularJS v1.4.8, you can use
get(url, config) as follows:
var data = {
user_id:user.id
};
var config = {
params: data,
headers : {'Accept' : 'application/json'}
};
$http.get(user.details_path, config).then(function(response) {
// process response here..
}, function(response) {
});
Solution for those who are interested in sending params and headers in GET request
$http.get('https://www.your-website.com/api/users.json', {
params: {page: 1, limit: 100, sort: 'name', direction: 'desc'},
headers: {'Authorization': 'Basic QWxhZGRpbjpvcGVuIHNlc2FtZQ=='}
}
)
.then(function(response) {
// Request completed successfully
}, function(x) {
// Request error
});
Complete service example will look like this
var mainApp = angular.module("mainApp", []);
mainApp.service('UserService', function($http, $q){
this.getUsers = function(page = 1, limit = 100, sort = 'id', direction = 'desc') {
var dfrd = $q.defer();
$http.get('https://www.your-website.com/api/users.json',
{
params:{page: page, limit: limit, sort: sort, direction: direction},
headers: {Authorization: 'Basic QWxhZGRpbjpvcGVuIHNlc2FtZQ=='}
}
)
.then(function(response) {
if ( response.data.success == true ) {
} else {
}
}, function(x) {
dfrd.reject(true);
});
return dfrd.promise;
}
});
You can even simply add the parameters to the end of the url:
$http.get('path/to/script.php?param=hello').success(function(data) {
alert(data);
});
Paired with script.php:
<? var_dump($_GET); ?>
Resulting in the following javascript alert:
array(1) {
["param"]=>
string(4) "hello"
}
Here's a complete example of an HTTP GET request with parameters using angular.js in ASP.NET MVC:
CONTROLLER:
public class AngularController : Controller
{
public JsonResult GetFullName(string name, string surname)
{
System.Diagnostics.Debugger.Break();
return Json(new { fullName = String.Format("{0} {1}",name,surname) }, JsonRequestBehavior.AllowGet);
}
}
VIEW:
<script src="https://ajax.googleapis.com/ajax/libs/angularjs/1.3.15/angular.min.js"></script>
<script type="text/javascript">
var myApp = angular.module("app", []);
myApp.controller('controller', function ($scope, $http) {
$scope.GetFullName = function (employee) {
//The url is as follows - ControllerName/ActionName?name=nameValue&surname=surnameValue
$http.get("/Angular/GetFullName?name=" + $scope.name + "&surname=" + $scope.surname).
success(function (data, status, headers, config) {
alert('Your full name is - ' + data.fullName);
}).
error(function (data, status, headers, config) {
alert("An error occurred during the AJAX request");
});
}
});
</script>
<div ng-app="app" ng-controller="controller">
<input type="text" ng-model="name" />
<input type="text" ng-model="surname" />
<input type="button" ng-click="GetFullName()" value="Get Full Name" />
</div>
For sending get request with parameter i use
$http.get('urlPartOne\\'+parameter+'\\urlPartTwo')
By this you can use your own url string