Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Add API to allow origin to purge all storage #4

Open
inexorabletash opened this issue May 26, 2015 · 16 comments
Open

Add API to allow origin to purge all storage #4

inexorabletash opened this issue May 26, 2015 · 16 comments

Comments

@inexorabletash
Copy link
Member

@inexorabletash inexorabletash commented May 26, 2015

This has come up a few times. Use cases include just getting back to a known state for testing, after a major revision across storage types, recovering from XSS, etc.

@annevk
Copy link
Member

@annevk annevk commented Jun 9, 2015

Purge a box, essentially?

@inexorabletash
Copy link
Member Author

@inexorabletash inexorabletash commented Jun 14, 2015

Yep, as long as it could apply to the "default" box.

The behavior of APIs using a purged box need to be defined, and when the storage is actually freed.

@annevk
Copy link
Member

@annevk annevk commented Jun 15, 2015

I guess purging should basically make all existing databases/stores disappear and all writing operations to them fail. You'll need to create new ones. Not sure if existing specifications deal with that possibility though.

@annevk
Copy link
Member

@annevk annevk commented Aug 10, 2015

We could define navigator.storage.purge() which returns a promise that fulfills with undefined when done.

What happens if you write to the box meanwhile?

@wanderview and @jakearchibald might be interested in this.

@annevk
Copy link
Member

@annevk annevk commented Aug 10, 2015

The other question is what we should do about network storage which is not really partitioned nicely like site storage is.

@inexorabletash
Copy link
Member Author

@inexorabletash inexorabletash commented Aug 10, 2015

cc: @slightlyoff too

"network storage" = http (etc) cache? (just making sure I understand)

Also:

  • would this force-close handles (e.g. IDB connections, Caches) or wait until they were released?
  • how does this interplay with other storage types' async management operations (e.g. a queue of pending database deletes/upgrades) - may be more complex for the default box since the default box magically resurrects on use without an explicit open

(not expecting answers, just throwing out design points we'll need to consider here)

@annevk
Copy link
Member

@annevk annevk commented Aug 10, 2015

Yes, "network storage" is HTTP cache and cookies. "site storage" is all APIs (what the Storage Standard lets you make persistent). "credential storage" (not listed at the moment) is user credentials. They appear to be all distinct in browsers at the moment.

@annevk
Copy link
Member

@annevk annevk commented Mar 31, 2016

@wanderview @jakearchibald what would the implications be for the Cache API here? @inexorabletash same for IDB? Would you need some kind of hook or should I directly call some cleanup algorithm in the respecting specifications?

@annevk annevk added the later label Mar 31, 2016
@jakearchibald
Copy link

@jakearchibald jakearchibald commented Mar 31, 2016

I'm guessing this is to replace http://w3c.github.io/webappsec-clear-site-data/#dom-api?

We could define navigator.storage.purge() which returns a promise that fulfills with undefined when done.
What happens if you write to the box meanwhile?

The purge operation could create a new default box then mark the old one for deletion. Anything which creates a new storage connection would operate on the new box, even if the old box hasn't been fully dispatched.

No strong opinions on hook vs algorithm to call. Maybe an algorithm would make it easier to purge specific types of storage?

Happy for any pending operations to reject, and any additional operation to also reject. We could do this by reading state on the box, and if it's "redundant", throw.

@annevk
Copy link
Member

@annevk annevk commented Mar 31, 2016

Hmm yeah, I forgot @mikewest already took a stab at this. It would be effectively that API, but actually defined, since it seems like it isn't defined currently.

@annevk
Copy link
Member

@annevk annevk commented Mar 31, 2016

Replacing the box sounds rather clean. So basically all storage APIs would need to be written in a way that they grab a box and for the length of time they hold onto it, they'll not be affected by clear().

@jakearchibald
Copy link

@jakearchibald jakearchibald commented Mar 31, 2016

Yeah, so the box would be grabbed on cache.open() or indexedDB.open.

they'll not be affected by clear().

Well… they should start rejecting on interaction with that box, right? A redundant state on the box would also be a good way to represent things like storage becoming disconnected (eg sd card removed).

@annevk
Copy link
Member

@annevk annevk commented Mar 31, 2016

Yeah I guess there should maybe some state there. Would love to hear from @inexorabletash what he thinks about this approach.

@annevk annevk removed the later label Mar 31, 2016
@inexorabletash
Copy link
Member Author

@inexorabletash inexorabletash commented Mar 31, 2016

IMHO, the easiest thing as far as IDB is concerned is to force-close all the connections, which is what Chrome does if the user manually deletes data. That's what @mikewest has in the header-based approach spec (on my recommendation, I think...). That prevents any new operations from starting (as above), but also terminates any in flight (so yes, need state). Agreed with @jakearchibald that this also also seems necessary in the "sd card removed" scenario where we can't pretend the data is still there but will go away after all handles are closed, and I don't think we want to have two different models. Which means I think I agree with the direction this is trending.

Also, @mikewest was looking forward to hooks in Storage for his header to talk to, so hopefully he's seeing these pings...

@annevk
Copy link
Member

@annevk annevk commented Mar 31, 2016

@inexorabletash okay, so we give box an associated state which is either "open" or "closed". When you invoke clear() it asynchronously marks the origin's box as closed and then replaces it with a new open box (whose mode is the same). It also invokes the "box close steps" which other specifications can hook into.

We should probably enumerate the other specifications since it will be observable in what order the box close steps run for each of them. So maybe each specification defines some cleanup steps that I reference from here.

And I also make sure that not just clear() can invoke these steps, but the header can too. Might be easier for that header to simply live in HTML though since I assume we only want it for navigations?

@othermaciej
Copy link

@othermaciej othermaciej commented Jun 14, 2020

Under partitioning, this would have to be limited to storage within the current partition, or it would create a vulnerability similar to privacycg/storage-partitioning#11

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Development

No branches or pull requests

4 participants