cyrilletuzi / angular-async-local-storage

Efficient client-side storage for Angular: simple API + performance + Observables + validation
MIT License
676 stars 68 forks source link

IndexedDB restricted in cross-origin iframes in Safari #42

Closed feldmarv closed 6 years ago

feldmarv commented 6 years ago

Hey there We get errors about IndexedDB in Safari as well as Mobile Safari but only when using iFrames.

SecurityError: IDBFactory.open() called in an invalid security context

Is it possible to use localStorage for such use cases as fallback. In our implementation its used like this:

  constructor(
    protected storage: LocalStorage,
  ) 

  private updateLocalStorage(lsName: string, lsValue: any) {
    this.storage.removeItem(lsName)
      .subscribe(
        () => {
          this.storage.setItem(lsName, lsValue)
            .subscribe( () => {}, () => {} );
        },
        () => {}
      );
  }

Thanks in Advance

cyrilletuzi commented 6 years ago

@feldmarv Is the iframe in HTTP while the app is in HTTPS?

feldmarv commented 6 years ago

@cyrilletuzi both urls are using https here an example: https://dev.my.calenso.com/book/braincept

Angular6 widget works for Chrome, Firefox, IE but throws SecurityError in Safari.

cyrilletuzi commented 6 years ago

After investigation, unfortunately it is a Safari restriction/issue. Details can be found here: dfahlander/Dexie.js#565. An useful detail is cross-origin iframes have IndexedDb restricted in Safari, but not same-origin iframes.

Even it's another problem, from the lib side, it's the same technical problem as in #26: IndexedDb is asynchronous and providers can't be asynchronous in Angular.

I'll change the title of the issue for documentation and mark it as "won't fix" as it's a Safari issue, but I'll investigate if the lib can introduce an option to automatically and/or manually force the usage of localStorage in such scenarios.

@feldmarv Could you first test in the iframe that localStorage is not restricted and works well? Otherwise there no need investigating an alternative.

feldmarv commented 6 years ago

@cyrilletuzi thanks for the fast feedback. I also have found the issue on Dixie.js. I really would like to test the usage of localStorage but I do not know how to use this fallback in our angular project. How can this be tested?

cyrilletuzi commented 6 years ago

@feldmarv Inside the iframe code in your AppComponent (or anywhere else):

localStorage.setItem('color', 'red');
console.log(localStorage.getItem('color')); // should log 'red'
cyrilletuzi commented 6 years ago

@feldmarv Can you test with v6.1.0-beta.0? npm install @ngx-pwa/local-storage@6.1.0-beta.0

cyrilletuzi commented 6 years ago

@feldmarv Damn, it means the error callback is not invoked... I added another way to catch the error in beta.1, can you try? npm install @ngx-pwa/local-storage@6.1.0-beta.1

feldmarv commented 6 years ago

@cyrilletuzi Just tried, and still callback not invoked.

cyrilletuzi commented 6 years ago

@feldmarv Thanks. I'll do my own tests later to see if there is a problem in the workaround I tried or if it's an uncatchable error in Safari.

cyrilletuzi commented 6 years ago

@feldmarv Are you sure you did the test well? I reproduced the issue, and indeed beta.0 didn't fix the issue, but beta.1 does. Can you try again with a clean install (removing node_modules and so on...)?

Once your confirm, I will be able to release the fix in stable.

cyrilletuzi commented 6 years ago

Fixed in 6.1. Feel free to comment if there is still a problem.