vueでchrome extensionを開発する#
Chrome拡張の機能#
公式ドキュメント: Extensions - Chrome Developers
サンプル集: GitHub - GoogleChrome/chrome-extensions-samples: Chrome Extensions Samples
Manifest V2 と V3について#
Chrome extensionで現在利用できる仕様はManifest V2
とManifest V3
がある
Manifest V2
は近々廃止される予定なので新規でextensionを作る場合はManifest V3
を利用する
chrome extensionについて調べるとmanifestv2の情報が混在してるので注意
機能#
大きく分けて
- ポップアップ画面
- オプション画面
- Service worker(ブラウザ画面などを対象とした処理に対する処理)
がある
CRX JSを利用してプロジェクトを作成する#
環境構築#
Create a project | CRXJS Vite Plugin
npm init vite@latest
Need to install the following packages:
create-vite@4.2.0
Ok to proceed? (y) y
✔ Project name: … vite-project
✔ Select a framework: › Vue
✔ Select a variant: › TypeScriptcd
cd vite-project
npm i @crxjs/vite-plugin@beta -D
公式に従ってmanifest.jsonを作成する
{
"manifest_version": 3,
"name": "CRXJS Vue Vite Example",
"version": "1.0.0",
"action": { "default_popup": "index.html" }
}
vite.configをの内容を以下に変更
import { defineConfig } from 'vite'
import vue from '@vitejs/plugin-vue'
import { crx } from '@crxjs/vite-plugin'
import manifest from './manifest.json' assert { type: 'json' }
export default defineConfig({
plugins: [
vue(),
crx({ manifest }),
],
})
Cannot find module './manifest.json'. Consider using '--resolveJsonModule' to import module with '.json' extension.ts(2732)
のエラーが出る。tsconfig.jsonの resolveJsonModule
をtrueにしても解決しないため、jsonのimportでなく変数としてmanifestを定義する
import { defineConfig } from 'vite'
import vue from '@vitejs/plugin-vue'
import { crx, ManifestV3Export } from '@crxjs/vite-plugin'
import { resolve } from 'path'
const manifest: ManifestV3Export = {
manifest_version: 3,
name: "CRXJS Vue Vite Example",
version: "1.0.0",
action: {default_popup: "index.html"}
}
export default defineConfig({
plugins: [
vue(),
crx({ manifest }),
]
})
npm run dev
を実行してローカルで以下の画面が出る
chromeでchrome://extensions/
を開く
Finderから vite-project/dist
フォルダを画面にドラッグドロップするとchrome拡張が追加される
拡張機能欄からクリックすると、ポップアップで先ほどの画面が開く
ポップアップ#
distフォルダ内にポップアップ用のhtmlsrc/pages/popup/index.html
を作成するため以下の設定をする
manifest.jsonの action でポップアップページで参照するhtmlを指定
{
"action": {
"default_popup": "src/pages/popup/index.html"
}
}
npm install @types/node -D
を実行後
vite.configの内容を以下に変更
import { defineConfig } from 'vite'
import vue from '@vitejs/plugin-vue'
import { crx } from '@crxjs/vite-plugin'
import { resolve } from 'path'
import manifest from './manifest.json' assert { type: 'json' } // Node >=17
export default defineConfig({
plugins: [
vue(),
crx({ manifest }),
],
build: {
rollupOptions: {
input: {
popup: resolve(__dirname, 'src/pages/popup/index.html'),
},
},
}
})
src/pages/popupフォルダを作り以下を追加する。
App.vue
<script setup lang="ts">
import HelloWorld from '../../components/HelloWorld.vue';
</script>
<template>
<HelloWorld msg="popup page" />
</template>
index.html
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8" />
<meta name="viewport" content="width=device-width, initial-scale=1.0" />
<title>chrome extension template</title>
</head>
<body>
<div id="app"></div>
<script type="module" src="./main.ts"></script>
</body>
</html>
main.ts
import { createApp } from 'vue'
import App from './App.vue'
createApp(App).mount('`#app')`
これでビルド時にdist/src/pages/popup/index.htmlが作成される
npm run devを再実行後、リロードしてポップアップ内に以下の画面が出ればOK
オプションページ#
ポップアップと同様の手順で作成する
vite.configに静的html作成の設定を追加
import { defineConfig } from 'vite'
import vue from '@vitejs/plugin-vue'
import { crx } from '@crxjs/vite-plugin'
import { resolve } from 'path'
import manifest from './manifest.json' assert { type: 'json' }
export default defineConfig({
plugins: [
vue(),
crx({ manifest }),
],
build: {
rollupOptions: {
input: {
popup: resolve(__dirname, 'src/pages/popup/index.html'),
option: resolve(__dirname, 'src/pages/option/index.html'),
},
},
}
})
src/pages/option配下にApp.vue,index.html,main.tsを作成する。
App.vue
<script setup lang="ts">
import HelloWorld from '../../components/HelloWorld.vue';
</script>
<template>
<HelloWorld msg="option page" />
</template>
index.html
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8" />
<meta name="viewport" content="width=device-width, initial-scale=1.0" />
<title>chrome extension template</title>
</head>
<body>
<div id="app"></div>
<script type="module" src="./main.ts"></script>
</body>
</html>
main.ts
import { createApp } from 'vue'
import App from './App.vue'
createApp(App).mount('`#app')`
manifest.jsonにoptions_page項目を追加
{
"manifest_version": 3,
"name": "CRXJS Vue Vite Example",
"version": "1.0.0",
"action": { "default_popup": "src/pages/popup/index.html" },
"options_page": "src/pages/option/index.html"
}
npm run devを再実行し、リロード後右クリックからオプションを選択して画面が開けばOK
Service Worker#
完成時#
npm run buildでdistファイルを作成し、chromeにドラッグドロップ
Link#
- https://www.memory-lovers.blog/entry/2022/11/22/163000
- Create a project | CRXJS Vite Plugin
- [Building for Production | Vite](https://vitejs.dev/guide/build.html
#multi-page-app)
- vite-plugin-mpa/main.ts at main · IndexXuan/vite-plugin-mpa · GitHub
- Chrome拡張機能を作ってみる | 2. 登場人物編 - くらげになりたい。
- 【Vue3+TypeScript+Vuetify+Vite】動的なテーマの切り替え - Qiita