はじめに
Chrome拡張機能を開発する際によく使う、便利なテクニックやコードスニペットを機能別にまとめました。Manifest V3に対応済みです。開発中の辞書や逆引きリファレンスとしてご活用ください。
ローカルストレージ(chrome.storage.local)へのデータの保存・取得
拡張機能内でデータを永続化したい場合に使用します。localStorage と異なり、非同期で動作し、Service Worker内でも利用できます。
準備:manifest.jsonに権限を追加
"permissions": ["storage"],
実装例
// データを保存する
async function saveData(key, value) {
await chrome.storage.local.set({ [key]: value });
}
// データを取得する
async function getData(key) {
const result = await chrome.storage.local.get([key]);
return result[key];
}
// 使用例
await saveData('userSetting', { theme: 'dark' });
const settings = await getData('userSetting');
console.log(settings); // { theme: 'dark' }
メッセージング(sendMessage, onMessage)
Content Script, Service Worker, Popupなど、拡張機能の異なるコンポーネント間でデータを送受信するための仕組みです。
実装例:Service Worker → アクティブタブのContent Script
// 送信側 (Service Worker)
async function sendMessageToActiveTab(message) {
const [tab] = await chrome.tabs.query({
active: true,
currentWindow: true,
});
if (tab?.id) {
const response = await chrome.tabs.sendMessage(tab.id, message);
console.log(response);
}
}
sendMessageToActiveTab({ type: 'GREETING', text: 'Hello!' });
実装例:Popup/Content Script → Service Worker
// 送信側 (PopupやContent Scriptなど)
async function sendMessageToBackground(message) {
const response = await chrome.runtime.sendMessage(message);
console.log(response);
}
sendMessageToBackground({ type: 'FETCH_DATA' });
実装例:メッセージ受信
// 受信側 (Service WorkerやContent Script)
chrome.runtime.onMessage.addListener((message, sender, sendResponse) => {
if (message.type === 'GREETING') {
console.log(message.text);
sendResponse({ reply: 'Hi there!' });
} else if (message.type === 'FETCH_DATA') {
// 何らかの処理
sendResponse({ status: 'OK' });
}
// 非同期でsendResponseを呼ぶ場合はtrueを返す必要がある
return true;
});
サイドパネル(chrome.sidePanel)の表示
ブラウザの横にUIパネルを表示する機能です。
準備:manifest.jsonに権限を追加
"permissions": ["sidePanel"],
実装例:アイコンクリックでサイドパネルを開く
// 拡張機能のインストール時に設定
chrome.runtime.onInstalled.addListener(() => {
// アイコンクリックでサイドパネルを開くように設定
chrome.sidePanel
.setPanelBehavior({ openPanelOnActionClick: true })
.catch((error) => console.error(error));
});
コンテキストメニュー(右クリックメニュー)への項目追加
ブラウザの右クリックメニューに独自の項目を追加できます。
準備:manifest.jsonに権限を追加
"permissions": ["contextMenus"],
実装例
// 拡張機能のインストール時にコンテキストメニューを作成
chrome.runtime.onInstalled.addListener(() => {
chrome.contextMenus.create({
id: "my-context-menu-item",
title: "選択したテキストを検索",
contexts: ["selection"], // テキスト選択時にのみ表示
});
});
// メニューがクリックされたときのイベント
chrome.contextMenus.onClicked.addListener((info, tab) => {
if (info.menuItemId === "my-context-menu-item" && info.selectionText) {
// 選択されたテキストを使って何か処理を行う
console.log(`Selected text: ${info.selectionText}`);
}
});
拡張機能内のファイルへのアクセス
拡張機能に同梱した画像やHTMLファイルなどに、Content ScriptやWebページからアクセスするための設定です。
準備:manifest.jsonに設定を追加
imgフォルダ内の全ファイルに、すべてのウェブサイトからアクセスを許可する例です。
"web_accessible_resources": [
{
"resources": ["img/*"],
"matches": ["<all_urls>"]
}
],
実装例:ファイルのURLを取得
// 'img/logo.png'のURLを取得
const logoUrl = chrome.runtime.getURL("img/logo.png");
// <img>要素を作成してページに挿入する例
const image = document.createElement('img');
image.src = logoUrl;
document.body.appendChild(image);
拡張機能アイコン(chrome.action)のクリックイベント
拡張機能のアイコンがクリックされたことを検知します。注意点として、manifest.jsonで"action": { "default_popup": "popup.html" } のようにポップアップを指定している場合、onClickedイベントは発火しません。
準備:manifest.jsonに設定を追加
"action": {}
実装例
chrome.action.onClicked.addListener((tab) => {
// アイコンがクリックされたタブの情報が`tab`に入る
console.log("Icon clicked on tab:", tab.id);
// 例:クリックされたタブでスクリプトを実行する
// chrome.scripting.executeScript(...)
});
ファイルのダウンロード(chrome.downloads)
URLを指定してファイルをユーザーのPCにダウンロードさせます。
準備:manifest.jsonに権限を追加
"permissions": ["downloads"],
実装例
async function downloadImage(imageUrl) {
await chrome.downloads.download({
url: imageUrl,
filename: 'image.png' // オプション:保存するファイル名を指定
});
}
デスクトップ通知(chrome.notifications)の表示
ユーザーに情報を知らせるためのデスクトップ通知を作成します。
準備:manifest.jsonに権限を追加
"permissions": ["notifications"],
実装例
function showNotification(title, message) {
chrome.notifications.create({
type: "basic",
iconUrl: chrome.runtime.getURL("img/icon128.png"), // 拡張機能内のアイコンを指定
title: title,
message: message,
priority: 0,
});
}
showNotification("タスク完了", "ファイルの処理が完了しました。");
定期的な処理の実行(chrome.alarms)
Service Workerがスリープ状態でも、指定した時間や間隔でイベントを発火させることができます。定期的なデータ取得などに便利です。
準備:manifest.jsonに権限を追加
"permissions": ["alarms"],
実装例
// 15分ごとに 'fetch-data-alarm' という名前のアラームを設定
chrome.alarms.create('fetch-data-alarm', {
periodInMinutes: 15,
});
// アラームイベントを監視
chrome.alarms.onAlarm.addListener((alarm) => {
if (alarm.name === 'fetch-data-alarm') {
// 定期的に実行したい処理をここに書く
console.log("定期処理を実行します。");
}
});
その他の便利なスニペット
現在アクティブなタブを更新
async function reloadActiveTab() {
const [tab] = await chrome.tabs.query({
active: true,
currentWindow: true,
});
if (tab?.id) {
await chrome.tabs.reload(tab.id);
}
}
オプションページを開く
manifest.jsonでオプションページが設定されている必要があります。
async function openOptions() {
await chrome.runtime.openOptionsPage();
}
拡張機能アイコンにバッジを表示
未読件数などを表示するのに便利です。Service WorkerやPopupで動作します。
function updateBadge(count) {
// textは文字列である必要がある
chrome.action.setBadgeText({ text: String(count) });
// バッジの色も設定可能
chrome.action.setBadgeBackgroundColor({ color: '#FF0000' });
}
インストール・アップデート時の処理
拡張機能がインストールまたはアップデートされた直後に一度だけ処理を実行します。初期設定の保存などに利用できます。
chrome.runtime.onInstalled.addListener((details) => {
if (details.reason === 'install') {
console.log('拡張機能がインストールされました。');
// 初期設定を保存するなどの処理
} else if (details.reason === 'update') {
console.log('拡張機能がアップデートされました。');
}
});
最後に
GoQSystemでは一緒に働いてくれる仲間を募集中です!
ご興味がある方は以下リンクよりご確認ください。