|
1 | | -import type { RsbuildPlugin } from "@rsbuild/core"; |
2 | | -import { makeManifest } from "./manifest/make-manifest.js"; |
| 1 | +import * as fs from "node:fs"; |
| 2 | +import path from "node:path"; |
| 3 | +import { type RsbuildPlugin, rspack } from "@rsbuild/core"; |
| 4 | +import { createJiti } from "jiti"; |
| 5 | +import ManifestParser from "./manifest/parser.js"; |
3 | 6 |
|
4 | 7 | interface Options { |
5 | | - manifest: chrome.runtime.ManifestV3; |
| 8 | + manifestPath: string; |
6 | 9 | } |
7 | 10 |
|
8 | | -export const pluginWebExtension = ({ manifest }: Options): RsbuildPlugin => ({ |
9 | | - name: "rsbuild:plugin-web-extension", |
| 11 | +const pluginName = "rsbuild:plugin-web-extension"; |
| 12 | + |
| 13 | +export const pluginWebExtension = ({ |
| 14 | + manifestPath, |
| 15 | +}: Options): RsbuildPlugin => ({ |
| 16 | + name: pluginName, |
10 | 17 | setup: async (api) => { |
| 18 | + const jiti = createJiti(api.context.rootPath, { moduleCache: false }); |
| 19 | + |
| 20 | + const manifestSourcePath = path.resolve(api.context.rootPath, manifestPath); |
| 21 | + if (!fs.existsSync(manifestSourcePath)) { |
| 22 | + throw new Error(`${pluginName}: Failed to read ${manifestSourcePath}`); |
| 23 | + } |
| 24 | + |
| 25 | + const manifestModule = jiti(manifestSourcePath); |
| 26 | + const manifest = manifestModule.default || manifestModule.manifest; |
| 27 | + |
11 | 28 | const htmlEntryPoints = Object.entries({ |
12 | 29 | popup: manifest.action?.default_popup, |
13 | 30 | devtools: manifest.devtools_page, |
@@ -60,13 +77,39 @@ export const pluginWebExtension = ({ manifest }: Options): RsbuildPlugin => ({ |
60 | 77 | }, |
61 | 78 | }, |
62 | 79 | dev: { |
63 | | - writeToDisk: true |
64 | | - } |
| 80 | + writeToDisk: true, |
| 81 | + }, |
65 | 82 | }); |
66 | 83 | }); |
67 | 84 |
|
68 | | - api.onAfterBuild(() => { |
69 | | - makeManifest(manifest, api.context.distPath); |
| 85 | + api.onAfterCreateCompiler(({ compiler }) => { |
| 86 | + if (!(compiler instanceof rspack.Compiler)) { |
| 87 | + return; |
| 88 | + } |
| 89 | + |
| 90 | + compiler.hooks.thisCompilation.tap(pluginName, (compilation) => { |
| 91 | + compilation.hooks.processAssets.tap( |
| 92 | + { |
| 93 | + name: pluginName, |
| 94 | + stage: compiler.webpack.Compilation.PROCESS_ASSETS_STAGE_ADDITIONAL, |
| 95 | + }, |
| 96 | + () => { |
| 97 | + compilation.fileDependencies.add(manifestSourcePath); |
| 98 | + |
| 99 | + const updatedManifestModule = jiti(manifestPath); |
| 100 | + const manifest = |
| 101 | + updatedManifestModule.default || updatedManifestModule.manifest; |
| 102 | + const content = ManifestParser.convertManifestToString(manifest); |
| 103 | + |
| 104 | + const { RawSource } = compiler.webpack.sources; |
| 105 | + |
| 106 | + const source = new RawSource(content); |
| 107 | + const outputFilename = "manifest.json"; |
| 108 | + |
| 109 | + compilation.emitAsset(outputFilename, source); |
| 110 | + } |
| 111 | + ); |
| 112 | + }); |
70 | 113 | }); |
71 | 114 | }, |
72 | 115 | }); |
0 commit comments