Tampermonkey / tampermonkey

Tampermonkey is the most popular userscript manager, with over 10 million users. It's available for Chrome, Microsoft Edge, Safari, Opera Next, and Firefox.
GNU General Public License v3.0
4.23k stars 418 forks source link

Multi-value support for GM_getValues, GM_setValues, GM_deleteValues? #2045

Open tophf opened 5 months ago

tophf commented 5 months ago

Maybe something like this?

Ideally I'd like Violentmonkey/Tampermonkey to avoid preloading all storage data at script start when the script doesn't ask for the legacy GM_xxxValue, in which case multi-value support becomes important because of the overhead to process each value individually. When GM.xxxValue functions are implemented as a native asynchronous call it makes sense from a performance viewpoint to allow specifying multiple values in one call, just like it's done in chrome.storage API.

derjanb commented 5 months ago

Makes sense. I'll add support for this in the next BETA version.

cyfung1031 commented 5 months ago

Could there be something "Proxy" ? ( the usage is like localStorage ) So developers do not need to think too much about sync the values along tabs. and don't need getValue and setValue

Option 1

// only one argument. object. the value is the default value if not exist (so this can make sure there is always a default value)
const gmValues = GM_values({
foo: 1,
bar: 2
});

// gmValues is a Proxy
// the values are obtained at each proxy's get

console.log(await gmValues.foo) // 1
gmValues.foo = 3
console.log(await gmValues.foo) // 3

Option 2

// only one argument. object. the value is the default value if not exist (so this can make sure there is always a default value)
const gmValues = await GM.values({
foo: 1,
bar: 2
});
// values are all cached in gmValues.

// gmValues is a Proxy. All values inside will have GM_addEvenListener. 
// the values will be automatically updated, so getter just read the stored cache value.

console.log(gmValues.foo) // 1 (just the cache)
gmValues.foo = 3
console.log(gmValues.foo) // 3 (the GM.setValue might be not completed at this time, but the setter updated the cache value already)

// if it is changed externally, the gmValues.foo will be also updated.
tophf commented 5 months ago

With proxy you can't await the result of setting the value. Either way, it's not related to the idea in this issue, so you should open a new one.

erosman commented 5 months ago

If I may add a word, FM introduced multi-value GM storage option in https://github.com/erosman/support/issues/545 Initially, using a new API but changing to an option for the existing API, which mimics the browser.storage.local.get().

tophf commented 5 months ago

I thought about extending the existing singular functions with the new syntax, but I decided it would encourage authors to use it directly without first checking for typeof GM.getValues === 'function'.

derjanb commented 2 months ago

Fixed at 5.3.6207 (crx|xpi in review)

I've decided against overloading the old API methods, because it would be difficult to detect whether multi-values are supported or not.