目的
Chrome Extension の HelloWorld のような簡単なプログラムで storage からのデータ取得をテストします。
Chrome Extension のファイル構成
browser-extension-storage/
│-- manifest.jsoon ....... Browser Extensionの設定ファイル
│-- content_scripts.js ... HTMLページで実行するMainプログラム
│-- options.js ..... Storage の変更をするプログラム
│-- options.html ... Storage の変更をするためのUI
│-- constants.js ... Storage に保管する変数処理のプログラム
それぞれのファイル内容の説明は、後で説明をしますがここでは manifest.json の内容を記載します。
{
"manifest_version": 3,
"name": "Hello World Storage Extension",
"version": "2025.5.25",
"description": "Hello World Storage Extension.",
"content_scripts": [
{
"matches": ["https://qiita.com/*"],
"js": ["content_scripts.js"]
}
],
"web_accessible_resources": [
{
"matches": ["https://qiita.com/*"],
"resources": ["constants.js"]
}
],
"options_page": "options.html",
"permissions": ["storage"]
}
Main ページを動作させるのに content_scripts を指定し、storage 処理をするためにpermissionが必要になります。
即時実行関数式
storage から取得したデータを使用するのに、取得を待つ(await)ので、即時実行関数で async処理をさせます。
content_scripts.js の以下の部分
var constants = "";
(async () => {
console.log("Content script initializing...");
constants = await import(chrome.runtime.getURL("constants.js"));
await constants.init();
console.log("Message from constants.getMessage() : " + constants.getMessage());
})();
動的インポート
上のコードで使用されていますが、content_scripts.js では import が使用できないので、動的importでの処理になっています。constants.jsに役割を分けるために使用しました。manifest.json の "web_accessible_resources" を指定する必要があります。
オプションページ
Storage への変数保管や変更にBrowser Extensionの options_page を使用します。manifest.json に指定します。
/*
* Local variables
*/
import * as constants from "./constants.js";
var message;
/*
* Code executed when js is loaded.
* Load timing is defined in the html.
*/
(async () => {
console.log("Options js initializing...");
await constants.init();
message = document.getElementById("message");
message.value = constants.getMessage();
message.addEventListener("change", () => {
constants.setMessageToStorage(message.value);
});
})();
動的import の必要はない事、options.jsの初期化の処理がoptions.htmlの読み込み状況に依存する場合にはHTMLの記述とあわせて調整します。今回は処理するHTMLの記述の後にscriptを書きました。これ以外だと
- scriptでdefer
<script type="module" src="options.js" defer></script> - js 側で document.addEventListener("DOMContentLoaded, () => {...
とする様です。
<!DOCTYPE html>
<html>
<head>
<title>Hello World Storage Extension Options</title>
</head>
<body>
<h1>Hello World Storage Extension Options</h1>
<label for="message">Message</label>
<input type="text" id="message">
<script type="module" src="options.js"></script>
<hr />
<br />
The changes will be automatically saved.
</body>
</html>
変数用スクリプト
変数を管理するスクリプトを作成して、管理がいろいろなソースコードに分散しないように考慮します。気をつけた点は
- Setter, Getterを用意する
- Storageからの Getter は asyncにして取得待ちができるようにする
です。以下のようなコードになりました。関数は export しましたが、制限をしてもいいかもしれません。
/*
* Constants and variables of Chrome extension
*/
const DEFAULT_message="Hello World";
var message=DEFAULT_message;
/*
* Funtion to initialize variables
*/
export async function init() {
message = await getMessageFromStorage() || DEFAULT_message;
console.log("constants.init message : " + message);
}
/*
* Setter of message. async is not required.
*/
export function setMessageToStorage(msg) {
message = msg;
chrome.storage.local.set({ "message" : msg }, () => {
console.log("constants.setMessageToStorage message : " + msg)
});
}
export function setMessage(msg) {
message = msg;
}
/*
* Getter of message. async is required to gete from the storage.
*/
export async function getMessageFromStorage() {
return new Promise((resolve) => {
chrome.storage.local.get("message", (result) => {
console.log("constants.getMessageFromStorage message : " + result.message);
resolve(result.message);
});
});
}
export function getMessage() {
return message;
}
Storage変更の検知
Browser Extensionの再起動をしなくてもStorage変更後の値でどうさするように content_scripts.jsを更新します。以下のような Event Listenerを記載しました。
chrome.storage.onChanged.addListener((changes, areaName) => {
console.log(`Storage area "${areaName}" changed.`);
for (let [key, { oldValue, newValue }] of Object.entries(changes)) {
console.log(`Key "${key}" changed from "${oldValue}" to "${newValue}".`);
}
(async () => {
await constants.init();
console.log("Message from constants.getMessage() : " + constants.getMessage());
})();
});
検知した値をデバッグ目的で出力し、そのままの値は使用せずに constants の初期化をすることでデータを更新するようにしました。
サンプルの実行結果
初期化時の BrowserのF12で確認できるコンソール
オプションページから更新したときのF12コンソール
Storage からのデータを取得して、動作できているのが確認できます。
まとめ
Browser Extensionを構成するファイルとその内容を説明しました。コードを各際には各処理とファイルの連携を考慮するので1つのファイルのみの処理のみを考えることはないです。動作するサンプルをもとに自分のアプリケーションでの処理を考えることになるかと思います。
参考

