How do you setup default stored variables?


(Wesley Branton) #1

I’m making a webextension that will have an options page with 1 checkbox. In the browser action that I have developed, it looks for a variable in storage that will be either true or false. By default, when the user first installs the program, I want the variable to be set to true, but I can’t find out how to do that without the user going to the options page manually and checking the box.

Is there a way to put objects into storage automatically after the user installs the addon? My addon won’t work properly unless the default is set to true.

I have tried adding an if statement that checks to see if the user has any objects in the addon storage and that seems to work when the user opens the options page first, but adding the same code to my actual browser action didn’t have the same results.


#2

Take a look at the runtime API. You could register a listener with the runtime.onInstalled event and use it to initialize all your preferences/options.


#3

I have a set if default options. At the start of the background script I check if my ‘options’ object exists in storage, and if not create and store it.


(Niklas Gollenstede) #4

There is actually no need to write default values to the storage. This works without unneccesarry storage writes:

const defaultValue = true; // if you ever decide to change the default,
// it will apply to all users who never berthrered to change the value,
// which is probably what you want

const { myValue = defaultValue, } = (await browser.storage.get('myValue'));
// if myValue was stored, it holds that value, otherwise it is the default value
// no need to write it back!

(Wesley Branton) #6

Ok, it was working perfectly and then I changed some code outside of the background.js which isn’t even related to the storage and I keep getting browser.runtime.onInstalled is undefined in the browser console.

function handleInstalled(details) {`
	if (details.reason == 'install') {
		browser.storage.local.set({
			setting: {
				displayroll: true,
				set12coin: false
			},
			roll: {
				d00001: 50*0.01,
				d00005: 40*0.05,
				d00010: 50*0.1,
				d00025: 40*0.25,
				d00100: 25*1,
				d00200: 25*2
			},
			count: {
				d00001: 0,
				d00005: 0,
				d00010: 0,
				d00025: 0,
				d00100: 0,
				d00200: 0,
				d00500: 0,
				d01000: 0,
				d02000: 0,
				d05000: 0,
				d10000: 0
			}
		});
	}
}

browser.runtime.onInstalled.addListener(handleInstalled);

It was working so well and I just can’t figure out what happened. Help!


(Wesley Branton) #7

That won’t work because the settings are accessed across like 5 different scripts, so it would require defining a default value on each script, which is a lot more work when it comes to future updates.


#8

Except for the last character in the first line (`), your code does work.

If that wasn’t the cause for your issue, execute the “web-ext lint” command to see if that will find a problem.


(Wesley Branton) #9

The character was only added when I posted here. It isn’t in my code. I haven’t done a lot of troubleshooting on my extensions, so how do I enter in the web-ext lint command? Through the Firefox debugger tool?


#10

“web-ext” itself is a node module you can use to run, build (xpi) and verify (lint) your Addon code. So you first need to install node.js. See here for more details: https://github.com/mozilla/web-ext

Once you have it set up properly, open a console, move into your addon’s root folder and execute “web-ext lint”. It should be easier if you had an IDE (e.g. Komodo Edit) that allows you to save and easily execute these kind of commands.

But I can’t tell if that will point out what your problem is. Still, it should be worth a try.


(Wesley Branton) #11

Ok wait a minute…
Looked at the Mozilla documentation on the .onInstalled listener and it says it doesn’t work for temporary addons, which is how I’m testing the addon. I feel that’s likely the issue because if I comment away the function for the listener and just leave the code within, it works perfectly find though.

How am I supposed to test it? I can’t just take a stab in the dark and hope it works. Tried zipping and changing to a XPI file and loading it into Firefox, but it says it’s corrupt, likely because Firefox doesn’t accept unsigned addons anymore.


(Wesley Branton) #12

Nevermind, there was a typo in my applications key in the manifest, that’s why it wouldn’t install on Firefox. Everything is working perfectly.

To everyone in this thread, thanks for your help.


#13

Is it possible that storage will get cleared? Is there a way that the user can do that?

If so you may want to restore them.


(Wesley Branton) #14

From some Google searching, there doesn’t seem to be an easy way to remove a specific addon’s data without uninstalling it. I’m sure that there is a way, but is there really a reason that someone would want to do that?

Interesting thought though.


(Niklas Gollenstede) #15

I’m pretty sure it get’s cleared when the user removes the extension and adds it again, but that should fire another install event.

And the user can of course delete the corresponding .json file in the profile folder.

@wbranton So, yah, pretty much what you said.


#16

Well, if it can happen -deliberately or accidentally - my method will handle it. I hope.


#17

The Developer Edition still does, at least if you set “about:config/xpinstall.signatures.required” to true.

It looks like the storage data will be placed inside “[profile]/browser-extension-data/[addon-id]/storage.js”; that is if you use “browser.storage.local.set” to write your data. But that file won’t get deleted if you remove your addon; it’s contents will merely be set to “{}”. If you use “browser.storage.sync.set”, the data is written to the “[profile]/storage-sync.sqlite” database file.

The onInstalled method seems to be the better option: It will be executed only once (during installation) and allows you to easily update/change the default value (only one location) if the previous one is no longer supported for whatever reason.

And if the user starts tampering with his profile, then he should better know what he is doing. There is only so much we can do as Addon devs.


(Niklas Gollenstede) #18

Generally, yes. The only thing is that a) you can generally delete every file in the profile folder without breaking anything (obvously you loose state), and b) the user might not delete the file himself. Ic could be done by some stupid cleanup tool.

allows you to easily update/change the default value

That would require additional logic to know if a value is user-set or not.

only one location

You can also include the same file in multiple pages. The one location thing is not really an argument …

But as long as it works, do whatever you think is best!