How to use storage-data in Promise? (IONIC4)

I’m trying to build a dynamic url using values stored with Storage.

The code on the page I need the data looks like this:

this.remotedataservice.getSectionData('invoice')
        .subscribe(data => {
          this.build(data);
        }, err => {
          console.log(err);
        });

Than the code in the service looks like this:

getSectionData(section): Observable<any> {
    this.storage.get('login').then((login) => {
      this.username = login.username;
    });

    let response = this.http.get('https://www.someurl.com/' + section + '/' +  this.username;
    return response;
  }

When I hard-code the variable (this.username) things work just fine, but using the storage-value doesn’t work.
I know there’t time needed to retrieve the data, but I don’t know how to return the function-return-value within the promise.
Lot’s of things I tried (like returning a new Promise etc.) for hours and hours, but can’t get it to work, so hope someone can help.

You should probably have a loot at some tutorials about asynchronous code, promises and Observables. Maybe first you could have a look to the following tutorial:

I get the basics of asynchronous code/Promises and Observables, but the problem here I quess is that ‘getSectionData’ needs a return value which can’t be returned within the Promise …

The “basics of asynchronous” is not correctly implemented in your piece of code that’s why I suggested to have a look to the tutorial respectively username will always be not defined in your get or luckily will be set. I will suggest to firstly fix that

getSectionData(section): Observable<any> {
     this.storage.get('login').then((login) => {
      this.username = login.username;
    });

    let response = this.http.get('https://www.someurl.com/' + section + '/' +  this.username;
    return response;
  }

I have read the tutorial and now understand that the Promise has a local scope. But how do I now get the variable from that scope in the url?
Placing the return in there doesn’t work, but I really do not know how to get the variables out of there in de url-construction and return the http-get-data

Ok so I gonna try to summarize really quick: if you have promises in a function/method, just forget “return a value”, it ain’t gonna work most of the time

what you could do is “return a promise”

I just gonna transform ugly quick and dirty your code

this.remotedataservice.getSectionData('invoice')
        .then(myObservable => {
            myObservable.subscribe((data) => {
               this.build(data);
            });
        }, err => {
          console.log(err);
        });

getSectionData(section): Promise<any> {
   return new Promise<any>((resolve) => {
 this.storage.get('login').then((login) => {
      this.username = login.username;

      let response = this.http.get('https://www.someurl.com/' + section + '/' +  this.username;

     resolve(response);

    });
});
  }

but like I said, quick and dirty

or

this.remotedataservice.getSectionData('invoice')
        .then((data) => {
            this.build(data);
        }, err => {
          console.log(err);
        });

getSectionData(section): Promise<any> {
   return new Promise<any>((resolve) => {
 this.storage.get('login').then((login) => {
      this.username = login.username;

      let response = this.http.get('https://www.someurl.com/' + section + '/' +  this.username;

     response.subscribe((data) => {
        resolve(data);
      });

    });
});
  }

also not again, quick and dirty and no catch at all for errors which should be obviously added too

Thank you so much, got it working now!
Beginning something new can be so hard :wink:

On the other hand, the same code that’s working now, didn’t work at first … than I changed something (because of an error), I received another error, changed it back, and then suddenly it worked without errors …

After a while promises and obersables become really familiar, it takes just a but of time :wink:

Have fun

Fun it was this morning, but now I run into troubles catching errors (401).
In the getData-function I implemented a loadingcontroller. It shows when loading, and dismisses after a successful load, but when I receive an error (ea 401), I don’t know how to pass this error, just like the data, to the getData-function. Only “error here #1?” is shown, while I expected to see “error here #3?” or “error here #4?” so I can dismiss the loadingcontroller and display a message.

getSectionData(section): Promise<any> {
    return new Promise<any>((resolve) => {
      this.storage.get('login').then((login) => {
        let headers = this.getHeaders(login);
        let response = this.http.get("https://" + this.clientDomain + "/rest/" + section + "/index/AuthenticationHeader/" + headers.authentication + "/UsertypeHeader/tenant/DateHeader/" + headers.date);
        response.subscribe((data) => {
          resolve(data);
        }, err => {
          console.log("error here #1?");
        });
      }).catch(function(error) {
         console.log("error here #2?")       
      });
    });
  }
async getData(showLoader) {
    const loading = await this.loadingController.create({
      message: 'Please wait...',
      translucent: false
    });

    await loading.present();

    this.remotedataservice.getSectionData('user')
      .then((data) => {
        console.log("All oke");
        loading.dismiss();
        this.build(data);
      }, err => {
        console.log("error here #3?");
        console.log(err);
      }).catch(function(error) {
        console.log("error here #4?");
     });;
  };

maybe arrows key?

instead of:

.catch(function(error) {
        console.log("error here #4?");
     });

try

.catch((error) => {
        console.log("error here #4?");
     });

not related, you’ve got typings mistakes ;; instead ;

also don’t forget to add the loading.dismiss(); to the error too

also other error, you don’t resolve/reject the promise in your getSectionData function, which isn’t good

quick and dirty you could also try:

getSectionData(section): Promise<any> {
    return new Promise<any>((resolve, reject) => {
      try {
      this.storage.get('login').then((login) => {
        let headers = this.getHeaders(login);
        let response = this.http.get("https://" + this.clientDomain + "/rest/" + section + "/index/AuthenticationHeader/" + headers.authentication + "/UsertypeHeader/tenant/DateHeader/" + headers.date);
        response.subscribe((data) => {
          resolve(data);
        });
      } catch (err) {
        reject(err);
     }  
    });
  }

Too bad, still not showing error #4

  getSectionData(section): Promise<any> {
    return new Promise<any>((resolve, reject) => {
      try {
        this.storage.get('login').then((login) => {
          let headers = this.getHeaders(login);
          let response = this.http.get("https://" + this.clientDomain + "/rest/" + section + "/index/AuthenticationHeader/" + headers.authentication + "/UsertypeHeader/tenant/DateHeader/" + headers.date);
          response.subscribe((data) => {
            resolve(data);
          }, err => {
            console.log("error here #1?");
          });
        }).catch(function(error) {
          console.log("error here #2?")       
        });
      } catch (err) {
        console.log("error here #5?")
        reject(err);
      }
    });
  }

  async getData(showLoader) {
    const loading = await this.loadingController.create({
      message: 'Please wait...',
      translucent: false
    });

    await loading.present();

    try {
      this.remotedataservice.getSectionData('user')
        .then((data) => {
          console.log("OKE");
          loading.dismiss();
          this.build(data);
        }, err => {
          console.log("error here #3?");
          console.log(err);
        }).catch((error) => {
          console.log("error here #4?");
        });
      } catch {
        console.log("error here #6?");
      }
  };

Still only showing “error here#1?”

read my previous msg, a promise should ALWAYS resolve or reject, you should not have a statement which doesn’t end without resolve or reject

therefore in getSectionData err and catch add a reject(err)`

also another times, read my last msg, change your function() into arrows function () =>

Thanks, got it working now, I think I learned something today :wink: … I ended up with this:

getSectionData(section): Promise<any> {
    return new Promise<any>((resolve, reject) => {
      this.storage.get('login').then((login) => {
        let headers = this.getHeaders(login);
        let response = this.http.get("https://" + this.clientDomain + "/rest/" + section + "/index/AuthenticationHeader/" + headers.authentication + "/UsertypeHeader/tenant/DateHeader/" + headers.date);
        response.subscribe((data) => {
          resolve(data);
        }, err => {
          reject(err);
        });
      });
    });
  };
  async getData(showLoader) {
    const loading = await this.loadingController.create({
      message: 'Please wait...',
      translucent: false
    });
    await loading.present();

    this.remotedataservice.getSectionData('user')
      .then((data) => {
        loading.dismiss();
        this.build(data);
      }, err => {
        loading.dismiss();
      });
  };

For people stumbling on this issue, I found this nice dummy-tuturial explaining the basics: https://javebratt.com/wtf-promise/

Congrats, happy to hear you solved it, well done :+1: