generated from Daydreamer-riri/starter-lib
-
-
Notifications
You must be signed in to change notification settings - Fork 8
/
assets.ts
90 lines (80 loc) · 2.32 KB
/
assets.ts
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
import type { RouteRecord } from '../types'
import type { Manifest, SSRManifest } from './build'
export const DYNAMIC_IMPORT_REGEX = /import\("([^)]+)"\)/g
export enum AssetType {
style = 'style',
script = 'script',
image = 'image',
font = 'font',
}
interface CollectAssetsOpts {
routes: RouteRecord[]
locationArg: string
base: string
serverManifest: Manifest
manifest: Manifest
ssrManifest: SSRManifest
}
export async function collectAssets({
routes,
locationArg,
base,
serverManifest,
manifest,
ssrManifest,
}: CollectAssetsOpts) {
const { matchRoutes } = await import('react-router-dom')
const matches = matchRoutes([...routes], locationArg, base)
const routeEntries = matches?.map(item => item.route.entry).filter(Boolean) as string[] ?? []
const dynamicImports = new Set<string>()
matches?.forEach(item => {
let lazyStr = ''
if (item.route.lazy) {
lazyStr += item.route.lazy.toString()
}
// @ts-expect-error lazy
if (item.route.Component?._payload?._result) {
// @ts-expect-error lazy
lazyStr += item.route.Component._payload._result.toString()
}
const match = lazyStr.matchAll(DYNAMIC_IMPORT_REGEX)
for (const m of match) {
dynamicImports.add(m[1].split('/').at(-1) ?? '')
}
})
const entries = new Set<string>()
routeEntries.forEach(e => entries.add(e))
const manifestEntries = [...Object.entries(serverManifest)]
dynamicImports.forEach(name => {
const result = manifestEntries.find(([_, value]) => value.file.endsWith(name))
if (result) {
entries.add(result[0])
}
})
const modules = collectModulesForEntries(manifest, entries)
const assets = new Set<string>()
Array.from(modules).forEach(id => {
const files = ssrManifest[id] || []
files.forEach(file => {
assets.add(file)
})
})
return assets
}
function collectModulesForEntries(manifest: Manifest, entries: Set<string> | undefined) {
const mods = new Set<string>()
if (!entries)
return mods
for (const entry of entries)
collectModules(manifest, entry, mods)
return mods
}
function collectModules(manifest: Manifest, entry: string | undefined, mods = new Set<string>()) {
if (!entry)
return mods
mods.add(entry)
manifest[entry]?.dynamicImports?.forEach(item => {
collectModules(manifest, item, mods)
})
return mods
}