Persistence of data in AngularJS

1

I have an app mounted, which is structured as follows:

Menú

 - Sección 1
 - Sección 2
 - Sección 3

Each of the sections is a view, which loads the data of an API, which is executed when accessing each of the views.

My question is, is there any way with AngularJS to keep the data even if we change our view? That is, when accessing section 2 from 1, the one does not lose the data when you return to it and you do not have to consult the API again.

I am looking to be able to upload the data only once, if not then I have to make calls every time I enter a view.

If there is a better way to do it, do not hesitate to tell me.

EDIT 1

Right now I have it like this:

app.controller('IncidenciasCtrl', ['$scope', '$cookies', 'serviceDatosApi', function($scope, $cookies, serviceDatosApi) {
  'use strict';

  serviceDatosApi.devuelveIncidencias("gttp://192.168.1.1/llamadaAPI")
    .then(function(datos){

        $scope.incidencias = datos.data;

    });

}]);


app.service('serviceDatosApi', ['$http', function ($http) {

    this.devuelveIncidencias = function(url) {
      return $http.get(url);
    } 

}]);
    
asked by Diego 20.01.2017 в 17:33
source

2 answers

2

New answer

Promises maintain their status once they have been fulfilled, this means that if you re-invoke then on a promise that has already been fulfilled, it will invoke the callback with the result of the promise. That is to say, the promise already stores the result obtained by you !, what remains to be done is to store the promise.

The service remains like this:

app.service('svc', ['$http',
  function($http) {
    this.promiseCache = null;
    this.getData = function(url) {
      return this.promiseCache || (this.promiseCache = $http.get(url));
    }
  }
]);

Now the problem with this is that once Promise is resolved , you will not be able to obtain new URLs or voluntarily reload the same URL. To overcome this problem, I'll give you an example: use an arrangement for the chache by URL and with the option to download any URL.

app.service('svc', ['$http',
  function($http) {
    this.promiseCache = [];
    this.getData = function(url, reload) {
      // si se pone reload = true, se borra la cache y vuelve a empezar 
      if (reload) {  delete this.promiseCache[url] }

       // si la promise esta en la chache, retorna la promise o lanza el get
      return this.promiseCache[url] || (this.promiseCache[url] = $http.get(url));
    }
  }
]);

Complete example: (you can check by the console that the XHR request is launched only once)

var app = angular.module('app', []);

app.service('svc', ['$http',
  function($http) {
    this.promiseCache = null;
    this.getData = function(url) {
      return this.promiseCache || (this.promiseCache = $http.get(url));
    }
  }
]);

app.controller('ctrl', ['$scope', 'svc',
  function($scope, svc) {
    
    $scope.reload = function() {
      svc.getData('http://ipinfo.io/8.8.8.8/json')
        .then(function(datos) {
          $scope.datos = datos.data
        });
    }
    
    // lo invocamos la primera vez. 
    $scope.reload();
  }
]);
<script src="https://ajax.googleapis.com/ajax/libs/angularjs/1.2.23/angular.min.js"></script>
<div ng-app="app" ng-controller="ctrl">
  <pre>
{{datos | json}}
<a style="cursor: pointer" ng-click="reload()">Recargar</a>
</pre>
</div>

Original answer

  

Is there any way with AngularJS to keep the data even if we change our view?

Assuming that the data is in a controller (and that is why it is lost when you change your view, since it changes the controller) what you can do is use a Service.

A service is a singleton that is born the first time it is injected and then, in subsequent injections, the same instance of the service will always be injected to all subsequent users (controllers) of the service itself.

This makes it a good tool to share information throughout the life cycle of the web app and has the advantage that with F5, when the web app is reloaded, the service is reconstructed and the data is lost.

There are many built-in services like: $interval , $http , $location and others. And you can make your own.

var app = angular.module('miApp', []);

app.service('datos', ['$http', function ($http) {
    // aqui dentro, this es la instancia del service.
    // por lo que todo lo que almacenes aqui, sera compartido entre todos los 
    // contraladores que injectan el servicio.

    this.unMetodo = function(url) {
       return $http.get(url); // este es un ejemplo de funcion del servicio
    } 
}]);

Then in the controller what you must do is to inject the service (in all the contoladores)

// fijate que injectamos DATOS
app.controller('controlador1', ['$scope', 'datos', function ($scope, datos) {

   // aqui dentro 'datos' es el 'this' del servicio datos. 
   // si haces algo como esto se refleja en todos los usuarios del servicio
   datos['algo'] = 'valor';
}]);

In another controller

// fijate que injectamos DATOS
app.controller('controlador2', ['$scope', 'datos', function ($scope, datos) {

   // aqui dentro 'datos' tambien es el 'this' del servicio datos. 
   // este controlador tiene el valor de datos['algo'] 
   // (siempre y cuando se alla ejecutado primero el codigo del otro controller)
   console.log(  datos['algo']  );
}]);

Using this technique it is very easy to share resources / data between controllers and between the views.

    
answered by 20.01.2017 / 18:01
source
1

Well, there are many ways to do what you want, and those are:

  • LocalStorage
  • WebSQL - SQLite
  • IndexDB

I know the first two because I've worked with them, the last one I put on the list, I've never worked it, but it exists.

It all depends on what amount of information fences to store, but when you see that you have developed an application, I recommend using SQLite or WebSQL.

The difference between one and another, is that WebSQL does not depend on any plugin or add-on to use either in the browser or already compiled the apk, while, the SQLite, only works on the device through a complement, in your case you work with angular, I do not know how advanced you are, I recommend you use Ionic Framework, I do not know if you know it but it would help you a lot.

    
answered by 20.01.2017 в 17:51