vite-plugin-build-version-file 0.1.17 → 0.2.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/README.md +346 -40
- package/dist/client.cjs +32 -109
- package/dist/client.d.cts +7 -3
- package/dist/client.d.ts +7 -3
- package/dist/client.mjs +30 -108
- package/dist/index.cjs +262 -1
- package/dist/index.d.cts +2 -0
- package/dist/index.d.ts +2 -0
- package/dist/index.mjs +262 -1
- package/package.json +9 -10
package/dist/client.cjs
CHANGED
|
@@ -20,123 +20,46 @@ var __toCommonJS = (mod) => __copyProps(__defProp({}, "__esModule", { value: tru
|
|
|
20
20
|
// src/client.ts
|
|
21
21
|
var client_exports = {};
|
|
22
22
|
__export(client_exports, {
|
|
23
|
-
clearUrlCache: () => clearUrlCache
|
|
23
|
+
clearUrlCache: () => clearUrlCache,
|
|
24
|
+
redirectToLoading: () => redirectToLoading
|
|
24
25
|
});
|
|
25
26
|
module.exports = __toCommonJS(client_exports);
|
|
26
|
-
var
|
|
27
|
-
|
|
28
|
-
|
|
29
|
-
var IFRAME_TIMEOUT = 5e3;
|
|
30
|
-
var DEFAULT_REFRESH_TIME = 5;
|
|
31
|
-
function showLoading(time) {
|
|
32
|
-
document.getElementById(LOADING_ID)?.remove();
|
|
33
|
-
const loading = document.createElement("div");
|
|
34
|
-
const spinner = document.createElement("div");
|
|
35
|
-
const text = document.createElement("div");
|
|
36
|
-
const deadline = Date.now() + time * 1e3;
|
|
37
|
-
loading.id = LOADING_ID;
|
|
38
|
-
loading.style.cssText = "position:fixed;inset:0;z-index:2147483647;display:flex;flex-direction:column;align-items:center;justify-content:center;background:rgba(0,0,0,.65);color:#fff;font:14px/1.5 sans-serif;";
|
|
39
|
-
spinner.style.cssText = "width:36px;height:36px;margin-bottom:16px;border:3px solid rgba(255,255,255,.35);border-top-color:#fff;border-radius:50%;animation:vite-build-version-loading .8s linear infinite;";
|
|
40
|
-
text.textContent = `\u8BF7\u7A0D\u7B49\uFF0C\u6B63\u5728\u68C0\u6D4B\u66F4\u65B0...\uFF08${Math.ceil(time)}\u79D2\uFF09`;
|
|
41
|
-
const style = document.createElement("style");
|
|
42
|
-
style.textContent = "@keyframes vite-build-version-loading{to{transform:rotate(360deg)}}";
|
|
43
|
-
loading.append(style, spinner, text);
|
|
44
|
-
document.documentElement.appendChild(loading);
|
|
45
|
-
const countdown = window.setInterval(() => {
|
|
46
|
-
const seconds = Math.max(0, Math.ceil((deadline - Date.now()) / 1e3));
|
|
47
|
-
text.textContent = `\u8BF7\u7A0D\u7B49\uFF0C\u6B63\u5728\u68C0\u6D4B\u66F4\u65B0...\uFF08${seconds}\u79D2\uFF09`;
|
|
48
|
-
}, 1e3);
|
|
49
|
-
return () => {
|
|
50
|
-
window.clearInterval(countdown);
|
|
51
|
-
loading.remove();
|
|
52
|
-
};
|
|
27
|
+
var DEFAULT_LOADING_FILENAME = "loading.html";
|
|
28
|
+
function createRandomParamKey() {
|
|
29
|
+
return Math.random().toString(36).slice(2);
|
|
53
30
|
}
|
|
54
|
-
function
|
|
55
|
-
const
|
|
56
|
-
|
|
57
|
-
|
|
58
|
-
targetUrl.searchParams.set(
|
|
59
|
-
CACHE_BUST_PARAM,
|
|
60
|
-
`${Date.now()}-${Math.random().toString(36).slice(2)}`
|
|
31
|
+
function createLoadingUrl(options) {
|
|
32
|
+
const loadingUrl = new URL(
|
|
33
|
+
options.filename ?? DEFAULT_LOADING_FILENAME,
|
|
34
|
+
window.location.href
|
|
61
35
|
);
|
|
62
|
-
|
|
63
|
-
|
|
64
|
-
|
|
65
|
-
|
|
66
|
-
|
|
67
|
-
|
|
68
|
-
|
|
36
|
+
const defaultUrl = window.location.origin + window.location.pathname;
|
|
37
|
+
const indexUrl = defaultUrl.endsWith("/") ? `${defaultUrl}index.html` : `${defaultUrl}/index.html`;
|
|
38
|
+
const urls = options.urls && options.urls.length > 0 ? options.urls : [defaultUrl, indexUrl];
|
|
39
|
+
const payload = {
|
|
40
|
+
urls,
|
|
41
|
+
redirectUrl: options.redirectUrl ?? window.location.href
|
|
42
|
+
};
|
|
43
|
+
if (options.time !== void 0) {
|
|
44
|
+
payload.time = options.time;
|
|
69
45
|
}
|
|
70
|
-
|
|
71
|
-
|
|
72
|
-
}
|
|
73
|
-
|
|
74
|
-
|
|
75
|
-
|
|
76
|
-
|
|
77
|
-
|
|
78
|
-
const complete = () => {
|
|
79
|
-
if (completed) {
|
|
80
|
-
return;
|
|
81
|
-
}
|
|
82
|
-
completed = true;
|
|
83
|
-
window.clearTimeout(timeout);
|
|
84
|
-
resolve();
|
|
85
|
-
};
|
|
86
|
-
const timeout = window.setTimeout(complete, IFRAME_TIMEOUT);
|
|
87
|
-
iframe.hidden = true;
|
|
88
|
-
iframe.id = IFRAME_ID;
|
|
89
|
-
iframe.addEventListener("load", complete, { once: true });
|
|
90
|
-
iframe.addEventListener("error", complete, { once: true });
|
|
91
|
-
iframe.src = url;
|
|
92
|
-
document.documentElement.appendChild(iframe);
|
|
93
|
-
});
|
|
46
|
+
if (options.times !== void 0) {
|
|
47
|
+
payload.times = options.times;
|
|
48
|
+
}
|
|
49
|
+
if (options.title) {
|
|
50
|
+
payload.title = options.title;
|
|
51
|
+
}
|
|
52
|
+
loadingUrl.searchParams.set(createRandomParamKey(), JSON.stringify(payload));
|
|
53
|
+
return loadingUrl.href;
|
|
94
54
|
}
|
|
95
|
-
|
|
96
|
-
|
|
97
|
-
console.info(`[vite-plugin-build-version] Clear cache for ${targetUrl}`);
|
|
98
|
-
await Promise.allSettled([
|
|
99
|
-
fetch(createCacheBustedUrl(targetUrl), { cache: "no-store" }).then(
|
|
100
|
-
(response) => response.arrayBuffer()
|
|
101
|
-
),
|
|
102
|
-
fetch(targetUrl, { cache: "reload" }).then(
|
|
103
|
-
(response) => response.arrayBuffer()
|
|
104
|
-
)
|
|
105
|
-
]);
|
|
106
|
-
await loadIframe(createCacheBustedUrl(targetUrl));
|
|
55
|
+
function redirectToLoading(options = {}) {
|
|
56
|
+
window.location.href = createLoadingUrl(options);
|
|
107
57
|
}
|
|
108
|
-
|
|
109
|
-
|
|
110
|
-
const urls = options.urls ?? [defaultUrl, createIndexUrl(defaultUrl)];
|
|
111
|
-
const configuredTime = options.time;
|
|
112
|
-
const time = typeof configuredTime === "number" && Number.isFinite(configuredTime) && configuredTime > 0 ? configuredTime : DEFAULT_REFRESH_TIME;
|
|
113
|
-
const redirectUrl = new URL(
|
|
114
|
-
options.redirectUrl ?? urls[0] ?? defaultUrl,
|
|
115
|
-
window.location.href
|
|
116
|
-
).href;
|
|
117
|
-
const hideLoading = showLoading(time);
|
|
118
|
-
let refreshTimeout = 0;
|
|
119
|
-
try {
|
|
120
|
-
await Promise.race([
|
|
121
|
-
(async () => {
|
|
122
|
-
for (const url of urls) {
|
|
123
|
-
try {
|
|
124
|
-
await clearTargetUrlCache(url);
|
|
125
|
-
} catch {
|
|
126
|
-
}
|
|
127
|
-
}
|
|
128
|
-
})(),
|
|
129
|
-
new Promise((resolve) => {
|
|
130
|
-
refreshTimeout = window.setTimeout(resolve, time * 1e3);
|
|
131
|
-
})
|
|
132
|
-
]);
|
|
133
|
-
} finally {
|
|
134
|
-
window.clearTimeout(refreshTimeout);
|
|
135
|
-
hideLoading();
|
|
136
|
-
window.location.replace(createCacheBustedUrl(redirectUrl));
|
|
137
|
-
}
|
|
58
|
+
function clearUrlCache(options = {}) {
|
|
59
|
+
redirectToLoading(options);
|
|
138
60
|
}
|
|
139
61
|
// Annotate the CommonJS export names for ESM import in node:
|
|
140
62
|
0 && (module.exports = {
|
|
141
|
-
clearUrlCache
|
|
63
|
+
clearUrlCache,
|
|
64
|
+
redirectToLoading
|
|
142
65
|
});
|
package/dist/client.d.cts
CHANGED
|
@@ -1,8 +1,12 @@
|
|
|
1
|
-
interface
|
|
1
|
+
interface RedirectToLoadingOptions {
|
|
2
2
|
urls?: string[];
|
|
3
3
|
redirectUrl?: string;
|
|
4
4
|
time?: number;
|
|
5
|
+
times?: number;
|
|
6
|
+
title?: string;
|
|
7
|
+
filename?: string;
|
|
5
8
|
}
|
|
6
|
-
declare function
|
|
9
|
+
declare function redirectToLoading(options?: RedirectToLoadingOptions): void;
|
|
10
|
+
declare function clearUrlCache(options?: RedirectToLoadingOptions): void;
|
|
7
11
|
|
|
8
|
-
export { type
|
|
12
|
+
export { type RedirectToLoadingOptions, clearUrlCache, redirectToLoading };
|
package/dist/client.d.ts
CHANGED
|
@@ -1,8 +1,12 @@
|
|
|
1
|
-
interface
|
|
1
|
+
interface RedirectToLoadingOptions {
|
|
2
2
|
urls?: string[];
|
|
3
3
|
redirectUrl?: string;
|
|
4
4
|
time?: number;
|
|
5
|
+
times?: number;
|
|
6
|
+
title?: string;
|
|
7
|
+
filename?: string;
|
|
5
8
|
}
|
|
6
|
-
declare function
|
|
9
|
+
declare function redirectToLoading(options?: RedirectToLoadingOptions): void;
|
|
10
|
+
declare function clearUrlCache(options?: RedirectToLoadingOptions): void;
|
|
7
11
|
|
|
8
|
-
export { type
|
|
12
|
+
export { type RedirectToLoadingOptions, clearUrlCache, redirectToLoading };
|
package/dist/client.mjs
CHANGED
|
@@ -1,117 +1,39 @@
|
|
|
1
1
|
// src/client.ts
|
|
2
|
-
var
|
|
3
|
-
|
|
4
|
-
|
|
5
|
-
var IFRAME_TIMEOUT = 5e3;
|
|
6
|
-
var DEFAULT_REFRESH_TIME = 5;
|
|
7
|
-
function showLoading(time) {
|
|
8
|
-
document.getElementById(LOADING_ID)?.remove();
|
|
9
|
-
const loading = document.createElement("div");
|
|
10
|
-
const spinner = document.createElement("div");
|
|
11
|
-
const text = document.createElement("div");
|
|
12
|
-
const deadline = Date.now() + time * 1e3;
|
|
13
|
-
loading.id = LOADING_ID;
|
|
14
|
-
loading.style.cssText = "position:fixed;inset:0;z-index:2147483647;display:flex;flex-direction:column;align-items:center;justify-content:center;background:rgba(0,0,0,.65);color:#fff;font:14px/1.5 sans-serif;";
|
|
15
|
-
spinner.style.cssText = "width:36px;height:36px;margin-bottom:16px;border:3px solid rgba(255,255,255,.35);border-top-color:#fff;border-radius:50%;animation:vite-build-version-loading .8s linear infinite;";
|
|
16
|
-
text.textContent = `\u8BF7\u7A0D\u7B49\uFF0C\u6B63\u5728\u68C0\u6D4B\u66F4\u65B0...\uFF08${Math.ceil(time)}\u79D2\uFF09`;
|
|
17
|
-
const style = document.createElement("style");
|
|
18
|
-
style.textContent = "@keyframes vite-build-version-loading{to{transform:rotate(360deg)}}";
|
|
19
|
-
loading.append(style, spinner, text);
|
|
20
|
-
document.documentElement.appendChild(loading);
|
|
21
|
-
const countdown = window.setInterval(() => {
|
|
22
|
-
const seconds = Math.max(0, Math.ceil((deadline - Date.now()) / 1e3));
|
|
23
|
-
text.textContent = `\u8BF7\u7A0D\u7B49\uFF0C\u6B63\u5728\u68C0\u6D4B\u66F4\u65B0...\uFF08${seconds}\u79D2\uFF09`;
|
|
24
|
-
}, 1e3);
|
|
25
|
-
return () => {
|
|
26
|
-
window.clearInterval(countdown);
|
|
27
|
-
loading.remove();
|
|
28
|
-
};
|
|
2
|
+
var DEFAULT_LOADING_FILENAME = "loading.html";
|
|
3
|
+
function createRandomParamKey() {
|
|
4
|
+
return Math.random().toString(36).slice(2);
|
|
29
5
|
}
|
|
30
|
-
function
|
|
31
|
-
const
|
|
32
|
-
|
|
33
|
-
|
|
34
|
-
targetUrl.searchParams.set(
|
|
35
|
-
CACHE_BUST_PARAM,
|
|
36
|
-
`${Date.now()}-${Math.random().toString(36).slice(2)}`
|
|
6
|
+
function createLoadingUrl(options) {
|
|
7
|
+
const loadingUrl = new URL(
|
|
8
|
+
options.filename ?? DEFAULT_LOADING_FILENAME,
|
|
9
|
+
window.location.href
|
|
37
10
|
);
|
|
38
|
-
|
|
39
|
-
|
|
40
|
-
|
|
41
|
-
|
|
42
|
-
|
|
43
|
-
|
|
44
|
-
|
|
11
|
+
const defaultUrl = window.location.origin + window.location.pathname;
|
|
12
|
+
const indexUrl = defaultUrl.endsWith("/") ? `${defaultUrl}index.html` : `${defaultUrl}/index.html`;
|
|
13
|
+
const urls = options.urls && options.urls.length > 0 ? options.urls : [defaultUrl, indexUrl];
|
|
14
|
+
const payload = {
|
|
15
|
+
urls,
|
|
16
|
+
redirectUrl: options.redirectUrl ?? window.location.href
|
|
17
|
+
};
|
|
18
|
+
if (options.time !== void 0) {
|
|
19
|
+
payload.time = options.time;
|
|
45
20
|
}
|
|
46
|
-
|
|
47
|
-
|
|
48
|
-
}
|
|
49
|
-
|
|
50
|
-
|
|
51
|
-
|
|
52
|
-
|
|
53
|
-
|
|
54
|
-
const complete = () => {
|
|
55
|
-
if (completed) {
|
|
56
|
-
return;
|
|
57
|
-
}
|
|
58
|
-
completed = true;
|
|
59
|
-
window.clearTimeout(timeout);
|
|
60
|
-
resolve();
|
|
61
|
-
};
|
|
62
|
-
const timeout = window.setTimeout(complete, IFRAME_TIMEOUT);
|
|
63
|
-
iframe.hidden = true;
|
|
64
|
-
iframe.id = IFRAME_ID;
|
|
65
|
-
iframe.addEventListener("load", complete, { once: true });
|
|
66
|
-
iframe.addEventListener("error", complete, { once: true });
|
|
67
|
-
iframe.src = url;
|
|
68
|
-
document.documentElement.appendChild(iframe);
|
|
69
|
-
});
|
|
21
|
+
if (options.times !== void 0) {
|
|
22
|
+
payload.times = options.times;
|
|
23
|
+
}
|
|
24
|
+
if (options.title) {
|
|
25
|
+
payload.title = options.title;
|
|
26
|
+
}
|
|
27
|
+
loadingUrl.searchParams.set(createRandomParamKey(), JSON.stringify(payload));
|
|
28
|
+
return loadingUrl.href;
|
|
70
29
|
}
|
|
71
|
-
|
|
72
|
-
|
|
73
|
-
console.info(`[vite-plugin-build-version] Clear cache for ${targetUrl}`);
|
|
74
|
-
await Promise.allSettled([
|
|
75
|
-
fetch(createCacheBustedUrl(targetUrl), { cache: "no-store" }).then(
|
|
76
|
-
(response) => response.arrayBuffer()
|
|
77
|
-
),
|
|
78
|
-
fetch(targetUrl, { cache: "reload" }).then(
|
|
79
|
-
(response) => response.arrayBuffer()
|
|
80
|
-
)
|
|
81
|
-
]);
|
|
82
|
-
await loadIframe(createCacheBustedUrl(targetUrl));
|
|
30
|
+
function redirectToLoading(options = {}) {
|
|
31
|
+
window.location.href = createLoadingUrl(options);
|
|
83
32
|
}
|
|
84
|
-
|
|
85
|
-
|
|
86
|
-
const urls = options.urls ?? [defaultUrl, createIndexUrl(defaultUrl)];
|
|
87
|
-
const configuredTime = options.time;
|
|
88
|
-
const time = typeof configuredTime === "number" && Number.isFinite(configuredTime) && configuredTime > 0 ? configuredTime : DEFAULT_REFRESH_TIME;
|
|
89
|
-
const redirectUrl = new URL(
|
|
90
|
-
options.redirectUrl ?? urls[0] ?? defaultUrl,
|
|
91
|
-
window.location.href
|
|
92
|
-
).href;
|
|
93
|
-
const hideLoading = showLoading(time);
|
|
94
|
-
let refreshTimeout = 0;
|
|
95
|
-
try {
|
|
96
|
-
await Promise.race([
|
|
97
|
-
(async () => {
|
|
98
|
-
for (const url of urls) {
|
|
99
|
-
try {
|
|
100
|
-
await clearTargetUrlCache(url);
|
|
101
|
-
} catch {
|
|
102
|
-
}
|
|
103
|
-
}
|
|
104
|
-
})(),
|
|
105
|
-
new Promise((resolve) => {
|
|
106
|
-
refreshTimeout = window.setTimeout(resolve, time * 1e3);
|
|
107
|
-
})
|
|
108
|
-
]);
|
|
109
|
-
} finally {
|
|
110
|
-
window.clearTimeout(refreshTimeout);
|
|
111
|
-
hideLoading();
|
|
112
|
-
window.location.replace(createCacheBustedUrl(redirectUrl));
|
|
113
|
-
}
|
|
33
|
+
function clearUrlCache(options = {}) {
|
|
34
|
+
redirectToLoading(options);
|
|
114
35
|
}
|
|
115
36
|
export {
|
|
116
|
-
clearUrlCache
|
|
37
|
+
clearUrlCache,
|
|
38
|
+
redirectToLoading
|
|
117
39
|
};
|
package/dist/index.cjs
CHANGED
|
@@ -26,8 +26,216 @@ __export(index_exports, {
|
|
|
26
26
|
module.exports = __toCommonJS(index_exports);
|
|
27
27
|
var import_node_fs = require("fs");
|
|
28
28
|
var import_node_path = require("path");
|
|
29
|
+
|
|
30
|
+
// src/loading.html
|
|
31
|
+
var loading_default = `<!doctype html>
|
|
32
|
+
<html lang="zh-CN">
|
|
33
|
+
<head>
|
|
34
|
+
<meta charset="UTF-8" />
|
|
35
|
+
<meta name="viewport" content="width=device-width, initial-scale=1.0" />
|
|
36
|
+
<title>Loading</title>
|
|
37
|
+
<style>
|
|
38
|
+
html,
|
|
39
|
+
body {
|
|
40
|
+
margin: 0;
|
|
41
|
+
height: 100%;
|
|
42
|
+
}
|
|
43
|
+
|
|
44
|
+
#vite-build-version-loading {
|
|
45
|
+
position: fixed;
|
|
46
|
+
inset: 0;
|
|
47
|
+
z-index: 2147483647;
|
|
48
|
+
display: flex;
|
|
49
|
+
flex-direction: column;
|
|
50
|
+
align-items: center;
|
|
51
|
+
justify-content: center;
|
|
52
|
+
gap: 16px;
|
|
53
|
+
color: #333333;
|
|
54
|
+
font: 14px/1.5 sans-serif;
|
|
55
|
+
}
|
|
56
|
+
|
|
57
|
+
#vite-build-version-loading .spinner {
|
|
58
|
+
width: 36px;
|
|
59
|
+
height: 36px;
|
|
60
|
+
border: 3px solid rgba(0, 0, 0, 0.15);
|
|
61
|
+
border-top-color: rgba(0, 0, 0, 0.6);
|
|
62
|
+
border-radius: 50%;
|
|
63
|
+
animation: vite-build-version-loading 0.8s linear infinite;
|
|
64
|
+
}
|
|
65
|
+
|
|
66
|
+
@keyframes vite-build-version-loading {
|
|
67
|
+
to {
|
|
68
|
+
transform: rotate(360deg);
|
|
69
|
+
}
|
|
70
|
+
}
|
|
71
|
+
</style>
|
|
72
|
+
</head>
|
|
73
|
+
<body>
|
|
74
|
+
<div id="vite-build-version-loading">
|
|
75
|
+
<div class="spinner"></div>
|
|
76
|
+
</div>
|
|
77
|
+
<script>
|
|
78
|
+
;(function () {
|
|
79
|
+
var IFRAME_ID = 'vite-plugin-build-version-file-cache-iframe'
|
|
80
|
+
var IFRAME_TIMEOUT = 5000
|
|
81
|
+
var DEFAULT_REFRESH_TIME = 5
|
|
82
|
+
var DEFAULT_CLEAR_TIMES = 2
|
|
83
|
+
|
|
84
|
+
var params = new URLSearchParams(window.location.search)
|
|
85
|
+
// \u53C2\u6570\u540D\u968F\u673A\u751F\u6210\uFF0Cloading \u9875\u6309\u503C\u89E3\u6790\uFF1A\u4EFB\u4F55\u503C\u662F JSON \u7684\u53C2\u6570\u90FD\u89C6\u4E3A\u6E05\u7406\u914D\u7F6E\u3002
|
|
86
|
+
var config = (function () {
|
|
87
|
+
var entries = Array.from(params.entries())
|
|
88
|
+
|
|
89
|
+
for (var i = 0; i < entries.length; i++) {
|
|
90
|
+
try {
|
|
91
|
+
var value = JSON.parse(entries[i][1])
|
|
92
|
+
|
|
93
|
+
if (value && typeof value === 'object' && Array.isArray(value.urls)) {
|
|
94
|
+
return value
|
|
95
|
+
}
|
|
96
|
+
} catch (error) {
|
|
97
|
+
// \u975E JSON \u53C2\u6570\uFF08\u4F8B\u5982\u81EA\u5B9A\u4E49 query\uFF09\u76F4\u63A5\u8DF3\u8FC7\u3002
|
|
98
|
+
}
|
|
99
|
+
}
|
|
100
|
+
|
|
101
|
+
return {}
|
|
102
|
+
})()
|
|
103
|
+
// \u9ED8\u8BA4\u628A\u672C\u9875\u9762\u6240\u5728\u76EE\u5F55\u5F53\u4F5C\u5E94\u7528\u6839\u8DEF\u5F84\u3002
|
|
104
|
+
var directoryUrl = new URL('.', window.location.href).href
|
|
105
|
+
var urls = Array.isArray(config.urls)
|
|
106
|
+
? config.urls.filter(Boolean)
|
|
107
|
+
: []
|
|
108
|
+
var time = Number(config.time)
|
|
109
|
+
var times = Math.floor(Number(config.times))
|
|
110
|
+
var redirectUrl = config.redirectUrl || directoryUrl
|
|
111
|
+
var title = config.title
|
|
112
|
+
|
|
113
|
+
if (urls.length === 0) {
|
|
114
|
+
urls = [directoryUrl, new URL('index.html', directoryUrl).href]
|
|
115
|
+
}
|
|
116
|
+
|
|
117
|
+
if (!Number.isFinite(time) || time <= 0) {
|
|
118
|
+
time = DEFAULT_REFRESH_TIME
|
|
119
|
+
}
|
|
120
|
+
|
|
121
|
+
if (!Number.isFinite(times) || times < 1) {
|
|
122
|
+
times = DEFAULT_CLEAR_TIMES
|
|
123
|
+
}
|
|
124
|
+
|
|
125
|
+
if (title) {
|
|
126
|
+
var titleElement = document.createElement('div')
|
|
127
|
+
titleElement.textContent = title
|
|
128
|
+
document.getElementById('vite-build-version-loading').appendChild(titleElement)
|
|
129
|
+
}
|
|
130
|
+
|
|
131
|
+
function createCacheBustKey() {
|
|
132
|
+
// \u53C2\u6570\u540D\u968F\u673A\uFF0C\u907F\u514D\u670D\u52A1\u5668\u6216 CDN \u9488\u5BF9\u56FA\u5B9A\u53C2\u6570\u540D\uFF08\u5982 _\u3001t\uFF09\u505A\u7F13\u5B58\u5904\u7406\u3002
|
|
133
|
+
return Date.now().toString(36) + Math.random().toString(36).slice(2, 8)
|
|
134
|
+
}
|
|
135
|
+
|
|
136
|
+
function createCacheBustedUrl(url) {
|
|
137
|
+
var targetUrl = new URL(url, window.location.href)
|
|
138
|
+
var hash = targetUrl.hash
|
|
139
|
+
|
|
140
|
+
// hash \u4E0D\u53C2\u4E0E HTTP \u8BF7\u6C42\uFF0C\u5148\u4FDD\u7559\u4E1A\u52A1\u8DEF\u7531\uFF0C\u518D\u5411\u771F\u5B9E\u8BF7\u6C42 URL \u5199\u5165\u7F13\u5B58\u6233\u3002
|
|
141
|
+
targetUrl.hash = ''
|
|
142
|
+
targetUrl.searchParams.set(
|
|
143
|
+
createCacheBustKey(),
|
|
144
|
+
Date.now() + '-' + Math.random().toString(36).slice(2)
|
|
145
|
+
)
|
|
146
|
+
targetUrl.hash = hash
|
|
147
|
+
|
|
148
|
+
return targetUrl.href
|
|
149
|
+
}
|
|
150
|
+
|
|
151
|
+
function loadIframe(url) {
|
|
152
|
+
return new Promise(function (resolve) {
|
|
153
|
+
// \u540C\u4E00\u9875\u9762\u53EA\u4FDD\u7559\u4E00\u4E2A\u7F13\u5B58\u5237\u65B0 iframe\uFF0C\u521B\u5EFA\u524D\u5148\u9500\u6BC1\u65E7\u5B9E\u4F8B\u3002
|
|
154
|
+
var existing = document.getElementById(IFRAME_ID)
|
|
155
|
+
|
|
156
|
+
if (existing) {
|
|
157
|
+
existing.remove()
|
|
158
|
+
}
|
|
159
|
+
|
|
160
|
+
var iframe = document.createElement('iframe')
|
|
161
|
+
var frameTimeout = 0
|
|
162
|
+
var completed = false
|
|
163
|
+
|
|
164
|
+
function complete() {
|
|
165
|
+
if (completed) {
|
|
166
|
+
return
|
|
167
|
+
}
|
|
168
|
+
|
|
169
|
+
completed = true
|
|
170
|
+
window.clearTimeout(frameTimeout)
|
|
171
|
+
resolve()
|
|
172
|
+
}
|
|
173
|
+
|
|
174
|
+
frameTimeout = window.setTimeout(complete, IFRAME_TIMEOUT)
|
|
175
|
+
|
|
176
|
+
iframe.hidden = true
|
|
177
|
+
iframe.id = IFRAME_ID
|
|
178
|
+
iframe.addEventListener('load', complete, { once: true })
|
|
179
|
+
iframe.addEventListener('error', complete, { once: true })
|
|
180
|
+
iframe.src = url
|
|
181
|
+
document.documentElement.appendChild(iframe)
|
|
182
|
+
})
|
|
183
|
+
}
|
|
184
|
+
|
|
185
|
+
function clearTargetUrlCache(url) {
|
|
186
|
+
var targetUrl = new URL(url, window.location.href).href
|
|
187
|
+
console.info('[vite-plugin-build-version] Clear cache for ' + targetUrl)
|
|
188
|
+
|
|
189
|
+
// \u968F\u673A URL \u7ED5\u8FC7\u65E7\u7F13\u5B58\uFF0C\u539F URL \u4F7F\u7528 reload \u6A21\u5F0F\u5237\u65B0\u5BF9\u5E94\u7F13\u5B58\u6761\u76EE\u3002
|
|
190
|
+
// \u7B49\u5F85\u54CD\u5E94\u4F53\u5B8C\u6574\u8BFB\u53D6\uFF0C\u907F\u514D\u540E\u7EED\u8DF3\u8F6C\u63D0\u524D\u53D6\u6D88\u7F13\u5B58\u5237\u65B0\u8BF7\u6C42\u3002
|
|
191
|
+
return Promise.allSettled([
|
|
192
|
+
fetch(createCacheBustedUrl(targetUrl), { cache: 'no-store' }).then(
|
|
193
|
+
function (response) {
|
|
194
|
+
return response.arrayBuffer()
|
|
195
|
+
}
|
|
196
|
+
),
|
|
197
|
+
fetch(targetUrl, { cache: 'reload' }).then(function (response) {
|
|
198
|
+
return response.arrayBuffer()
|
|
199
|
+
})
|
|
200
|
+
]).then(function () {
|
|
201
|
+
// iframe \u518D\u89E6\u53D1\u4E00\u6B21\u9875\u9762\u8D44\u6E90\u52A0\u8F7D\uFF0C\u8D85\u65F6\u6216\u5931\u8D25\u7531\u5916\u5C42\u7EE7\u7EED\u5904\u7406\u540E\u7EED URL\u3002
|
|
202
|
+
return loadIframe(createCacheBustedUrl(targetUrl))
|
|
203
|
+
})
|
|
204
|
+
}
|
|
205
|
+
|
|
206
|
+
var refreshTimeoutId = 0
|
|
207
|
+
var clearAllDone = (async function () {
|
|
208
|
+
// \u6574\u5957\u6E05\u7406\u64CD\u4F5C\u6309 times \u91CD\u590D\u6267\u884C\uFF0C\u9ED8\u8BA4 2 \u6B21\u3002
|
|
209
|
+
for (var round = 0; round < times; round++) {
|
|
210
|
+
for (var i = 0; i < urls.length; i++) {
|
|
211
|
+
try {
|
|
212
|
+
await clearTargetUrlCache(urls[i])
|
|
213
|
+
} catch (error) {
|
|
214
|
+
// \u5355\u7EC4\u5931\u8D25\u4E0D\u963B\u65AD\u540E\u7EED URL\uFF0C\u4FDD\u8BC1\u914D\u7F6E\u7684\u68C0\u6D4B\u7EC4\u90FD\u80FD\u6267\u884C\u3002
|
|
215
|
+
}
|
|
216
|
+
}
|
|
217
|
+
}
|
|
218
|
+
})()
|
|
219
|
+
var limitReached = new Promise(function (resolve) {
|
|
220
|
+
// \u5230\u8FBE\u603B\u7B49\u5F85\u65F6\u9650\u540E\u76F4\u63A5\u8DF3\u8F6C\uFF0C\u4E0D\u53D7\u7F13\u5B58\u8BF7\u6C42\u72B6\u6001\u5F71\u54CD\u3002
|
|
221
|
+
refreshTimeoutId = window.setTimeout(resolve, time * 1000)
|
|
222
|
+
})
|
|
223
|
+
|
|
224
|
+
Promise.race([clearAllDone, limitReached]).then(function () {
|
|
225
|
+
window.clearTimeout(refreshTimeoutId)
|
|
226
|
+
// \u6700\u7EC8\u8DF3\u8F6C\u539F\u6837\u4F7F\u7528\u76EE\u6807\u5730\u5740\uFF0C\u4E0D\u9644\u52A0\u7F13\u5B58\u6233\u3002
|
|
227
|
+
window.location.replace(redirectUrl)
|
|
228
|
+
})
|
|
229
|
+
})()
|
|
230
|
+
</script>
|
|
231
|
+
</body>
|
|
232
|
+
</html>
|
|
233
|
+
`;
|
|
234
|
+
|
|
235
|
+
// src/index.ts
|
|
29
236
|
var PLUGIN_NAME = "vite-plugin-build-version-file";
|
|
30
237
|
var DEFAULT_FILENAME = "version.json";
|
|
238
|
+
var DEFAULT_LOADING_PAGE = "loading";
|
|
31
239
|
var DEFAULT_GLOBAL_NAME = "__VERSION__";
|
|
32
240
|
var DEFAULT_DEFINE_NAME = "__VERSION__";
|
|
33
241
|
var DEFAULT_TIME_ZONE = "Asia/Shanghai";
|
|
@@ -65,6 +273,16 @@ function normalizeFileName(filename) {
|
|
|
65
273
|
}
|
|
66
274
|
return normalized;
|
|
67
275
|
}
|
|
276
|
+
function normalizeLoadingPage(loadingPage) {
|
|
277
|
+
if (loadingPage === false) {
|
|
278
|
+
return false;
|
|
279
|
+
}
|
|
280
|
+
const normalized = (loadingPage ?? DEFAULT_LOADING_PAGE).trim().replace(/^\/+/, "");
|
|
281
|
+
if (!normalized) {
|
|
282
|
+
throw new Error(`[${PLUGIN_NAME}] "loadingPage" cannot be empty.`);
|
|
283
|
+
}
|
|
284
|
+
return normalized.endsWith(".html") ? normalized : `${normalized}.html`;
|
|
285
|
+
}
|
|
68
286
|
function normalizeGlobalName(globalName) {
|
|
69
287
|
if (!globalName.trim()) {
|
|
70
288
|
throw new Error(`[${PLUGIN_NAME}] "globalName" cannot be empty.`);
|
|
@@ -142,6 +360,9 @@ function serializePayload(payload) {
|
|
|
142
360
|
function createInjectScript(globalName, payload) {
|
|
143
361
|
return `window[${JSON.stringify(globalName)}] = ${JSON.stringify(payload)};`;
|
|
144
362
|
}
|
|
363
|
+
function createInjectScriptTag(globalName, payload) {
|
|
364
|
+
return `<script>${createInjectScript(globalName, payload)}</script>`;
|
|
365
|
+
}
|
|
145
366
|
function injectScriptToHead(code, script) {
|
|
146
367
|
const scriptTag = `<script>${script}</script>`;
|
|
147
368
|
if (code.includes(script)) {
|
|
@@ -164,6 +385,13 @@ function toRequestPath(base, fileName) {
|
|
|
164
385
|
const baseWithoutTrailingSlash = withLeadingSlash.endsWith("/") ? withLeadingSlash.slice(0, -1) : withLeadingSlash;
|
|
165
386
|
return `${baseWithoutTrailingSlash}/${fileName}`.replace(/\/{2,}/g, "/");
|
|
166
387
|
}
|
|
388
|
+
function resolveNuxtFileName(config, fileName) {
|
|
389
|
+
if (config.appType !== "custom" || config.build.copyPublicDir !== false) {
|
|
390
|
+
return fileName;
|
|
391
|
+
}
|
|
392
|
+
const assetDir = normalizeFileName(config.build.assetsDir);
|
|
393
|
+
return assetDir === "." || fileName.startsWith(`${assetDir}/`) ? fileName : `${assetDir}/${fileName}`;
|
|
394
|
+
}
|
|
167
395
|
function resolveProjectRoot(root) {
|
|
168
396
|
return root ? (0, import_node_path.resolve)(process.cwd(), root) : process.cwd();
|
|
169
397
|
}
|
|
@@ -190,6 +418,7 @@ function createPayload(options, context, data, timeZone, packageInfo = {}) {
|
|
|
190
418
|
}
|
|
191
419
|
function buildVersionPlugin(options = {}) {
|
|
192
420
|
const fileName = normalizeFileName(options.filename ?? DEFAULT_FILENAME);
|
|
421
|
+
const loadingPage = normalizeLoadingPage(options.loadingPage);
|
|
193
422
|
const globalName = normalizeGlobalName(
|
|
194
423
|
options.globalName ?? DEFAULT_GLOBAL_NAME
|
|
195
424
|
);
|
|
@@ -201,12 +430,20 @@ function buildVersionPlugin(options = {}) {
|
|
|
201
430
|
const data = normalizeData(options.data);
|
|
202
431
|
let payload;
|
|
203
432
|
let skipBundleEmit = false;
|
|
433
|
+
let bundleFileName = fileName;
|
|
434
|
+
let bundleLoadingFileName = loadingPage;
|
|
204
435
|
const transformHtml = (code, ..._args) => {
|
|
205
436
|
if (!injectToHtml || !payload) {
|
|
206
437
|
return void 0;
|
|
207
438
|
}
|
|
208
439
|
return injectScriptToHead(code, createInjectScript(globalName, payload));
|
|
209
440
|
};
|
|
441
|
+
const headScript = () => {
|
|
442
|
+
if (!injectToHtml || !payload) {
|
|
443
|
+
return "";
|
|
444
|
+
}
|
|
445
|
+
return createInjectScriptTag(globalName, payload);
|
|
446
|
+
};
|
|
210
447
|
const plugin = {
|
|
211
448
|
name: PLUGIN_NAME,
|
|
212
449
|
config(userConfig, env) {
|
|
@@ -229,6 +466,10 @@ function buildVersionPlugin(options = {}) {
|
|
|
229
466
|
},
|
|
230
467
|
configResolved(config) {
|
|
231
468
|
skipBundleEmit = Boolean(config.build.ssr) && !config.build.ssrEmitAssets;
|
|
469
|
+
bundleFileName = resolveNuxtFileName(config, fileName);
|
|
470
|
+
if (loadingPage) {
|
|
471
|
+
bundleLoadingFileName = resolveNuxtFileName(config, loadingPage);
|
|
472
|
+
}
|
|
232
473
|
if (payload) {
|
|
233
474
|
return;
|
|
234
475
|
}
|
|
@@ -241,11 +482,21 @@ function buildVersionPlugin(options = {}) {
|
|
|
241
482
|
},
|
|
242
483
|
configureServer(server) {
|
|
243
484
|
const requestPath = toRequestPath(server.config.base, fileName);
|
|
485
|
+
const loadingRequestPath = loadingPage ? toRequestPath(server.config.base, loadingPage) : void 0;
|
|
244
486
|
server.middlewares.use((request, response, next) => {
|
|
245
487
|
if (request.method !== "GET" && request.method !== "HEAD") {
|
|
246
488
|
next();
|
|
247
489
|
return;
|
|
248
490
|
}
|
|
491
|
+
if (loadingRequestPath && parsePathname(request.url) === loadingRequestPath) {
|
|
492
|
+
response.statusCode = 200;
|
|
493
|
+
response.setHeader("Content-Type", "text/html; charset=utf-8");
|
|
494
|
+
response.setHeader("Cache-Control", "no-cache");
|
|
495
|
+
response.end(
|
|
496
|
+
request.method === "HEAD" ? void 0 : loading_default
|
|
497
|
+
);
|
|
498
|
+
return;
|
|
499
|
+
}
|
|
249
500
|
if (parsePathname(request.url) !== requestPath || !payload) {
|
|
250
501
|
next();
|
|
251
502
|
return;
|
|
@@ -276,9 +527,16 @@ function buildVersionPlugin(options = {}) {
|
|
|
276
527
|
}
|
|
277
528
|
this.emitFile({
|
|
278
529
|
type: "asset",
|
|
279
|
-
fileName,
|
|
530
|
+
fileName: bundleFileName,
|
|
280
531
|
source: serializePayload(payload)
|
|
281
532
|
});
|
|
533
|
+
if (bundleLoadingFileName) {
|
|
534
|
+
this.emitFile({
|
|
535
|
+
type: "asset",
|
|
536
|
+
fileName: bundleLoadingFileName,
|
|
537
|
+
source: loading_default
|
|
538
|
+
});
|
|
539
|
+
}
|
|
282
540
|
if (options.log) {
|
|
283
541
|
console.log(options.log(payload));
|
|
284
542
|
} else {
|
|
@@ -290,6 +548,9 @@ function buildVersionPlugin(options = {}) {
|
|
|
290
548
|
Object.defineProperty(plugin, "transformHtml", {
|
|
291
549
|
value: transformHtml
|
|
292
550
|
});
|
|
551
|
+
Object.defineProperty(plugin, "headScript", {
|
|
552
|
+
value: headScript
|
|
553
|
+
});
|
|
293
554
|
return plugin;
|
|
294
555
|
}
|
|
295
556
|
var index_default = buildVersionPlugin;
|