I store some keys in cache using angularJs cachefactory
myApp.factory('SomeCache', function ($cacheFactory) {
return $cacheFactory('someCache', {
capacity: 10 // optional - turns the cache into LRU cache
});
});
in the code :
SomeCache.put(key, value);
I see all the keys and values in the console.
The problem is , when i redirect to another page, not in my webSite ( e.c www.ebay.com)
and the i come back the cache object is empty,
I needd to preserve the data on the page.
Any idea ?
ishay
The behaviour you see with $cacheFactory is expected. The AngularJS-Cache does not persist between page refreshes. See also: Angularjs: date expiration for $cacheFactory
What you need to use to persist data between page refreshes is localStorage or sessionStorage as explained on this site: DOM Storage guide
You should use the excellent ngStorage module.
Related
I have some variables in angular controller. I have there if user is logged in and other details . When i am refreshing my page using f5 all my variables are reloading and i am getting in log in page, but before refresh i was already logged in and my variable isUserLoggedIn was true but after refresh it is false , false is this variables default value, I am declaring it in Controller .How can I save all my variables ( current point of angular controller ) and continue with my saved point after refresh ?
You can use the browsers local storage(HTML5) and store your data.
E.g:
to write:
$window.localStorage['sample-key'] = 'sample-data;
to read:
var data = $window.localStorage['sample-key']
There are many libraries available for this, you can check this one:
https://github.com/grevory/angular-local-storage
Right now, I have a factory which loads a JSON file.
angular.module("app").factory("RolesFactory", ['$http', '$q', function($http, $q) {
var d = $q.defer();
$http.get('events.json').success(function(data) {
d.resolve(data);
});
return d.promise;
}]);
And then I call this factory when I need the contents of events.json with this controller:
App.controller('rolesCtrl', ['$scope', 'RolesFactory', function($scope, RolesFactory) {
RolesFactory.then(function(roleData){
$scope.roles = roleData.roles;
});
}]);
All good, but whenever I need to use this data. Isn't it refetching the contents of events.json? Meaning: is Angular reloading the file over and over again? I was hoping to load the file once and call it by a global variable or something.
When my app loads initially, I want it to load and store the contens of events.json -- and then I'd like my app to be able to use this data whenever/wherever.
Is this possible?
As AngularJS is a stateless framework, you have only a few options here, all of which are some kind of client-side caching:
Use localStorage to store your data. Once the data is fetched, you can just save it to localStorage using localStorage.setItem after Stringifying the JSON. You'll need to re-parse the JSON the next time you use it though, so if this is a giant JSON, this is not the best idea
Use sessionStorage to store your data. This is exactly the same as #1, but you will lose data upon termination of session,i.e. closing your browser.
Trust the JSON to be cached in your browser. This is most likely the case. Static assets are by default cached by most modern browsers. So, the second time your factory requests the JSON, the resource isn't actually fetched from the server. It is merely pulled from the browser's cache.
NOTE: The way to check this is to see what the HTTP status code for your resource is, in Chrome's Developer Tools Network tab. If the status says 304 that means it has been pulled from cache.
So I have a simple factory that creates cache object
.factory('jsonCache',function($cacheFactory){
console.log("Creating cache");
return $cacheFactory('weatherCache');
});
I'm then calling that cache object inside my controller like so by passing it in like so. But for some reason the data is not persistent. Every time I reload the page, the cache is empty again.
Any ideas? Did I miss something?
.controller('citiesListCtrl',function($scope,$http,$filter,jsonCache){
jsonCache.get('weatherCache');
console.log(jsonCache); <----- EMPTY
$http.get(url)
.then(function(response) {
jsonCache.put('weatherCache', response.data.records);
console.log(jsonCache); <--- HAS DATA
});
)}
The data is not persistent for very good reason: $cacheFactory cache is nothing but a thin wrapper around plain JS object.
You can check the source to make sure that the service does nothing but simple LRU algorithm.
For data persistence use persistent storage (probably angular-local-storage or angular-localForage). angular-cache is an another replacement for built-in $cacheFactory that supports persistence.
I am using Angular's default $http cache in one of my services. When the user navigates from a view to another one (I am using ui-router), the cache invalidates and all of the items will be removed from it. I want to not invalidate the cache in the whole lifetime of my application.
EDIT:
For example, this factory does not return cached result after navigating to another route and it calls the server api to get the result:
cardModule.factory("myFactory", function ($http) {
return {
getAll: function () {
return $http.get("all", { cache: true })
}
}
});
How to prevent default cache from removing items from itself after a route change?
I found the source of the problem. It was my own fault. I had a code somewhere that clears the cache after the state change. There is no problem with default angular $http cache.
I would leave this as a comment but I don't have enough points yet..
Could you try some form of memoisation? In other words, have a model on the scope, then, if the model is undefined, trigger the $http call? Something like:
var ctrl = this;
ctrl.product = undefined; // or null
if (ctrl.product === undefined) { // or null
$http.get(...).then(function(resp) {
ctrl.product = resp.data;
};
};
This way the model gets initialized, and called just once. A possible downside would be that the if statement may make this inefficient.
I have not tested this, just throwing the idea out there. I am also very interested in this problem.
That should not be related to ui-router or $http. Here are a few things you need to confirm:
Is your server (which is serving your resources) is setting the cache header or not
Make sure you are not using Ctrl + F5 to refresh the page
If you are using Chrome browser, make sure a setting Disable cache is unchecked
I'm attempting to use angular-cache v4.2:
angular-cache
I am unable to get it storing between page refreshes.
I tried to create a codepen, but didn't get very far as I have been unable to inject the module on there. codepen.
angular.module('myApp', ['angular-cache'])
.config(function (CacheFactoryProvider) {
angular.extend(CacheFactoryProvider.defaults, { maxAge: 15 * 60 * 1000 });
})
However, even when I get it to create caches, it loses the cache when the page is refreshed - I have tried the three different storage types and haven't been able to get any working on chrome version 39.
Answer with the help of Shehryar's comment. See:
codepen
// To add to local storage
localStorageService.set('localStorageKey','Now this!');
// Read that value back
$scope.value = localStorageService.get('localStorageKey');
Using the angular local storage module, this example will store the cache create after a page refresh. It is also possible to add in
localStorageService.clearAll();
and then refresh the page to remove the initial value.