nuxt-gin-tools 0.2.10 → 0.2.12
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/commands/api-generate.d.ts +11 -0
- package/commands/api-generate.js +133 -0
- package/commands/builder.d.ts +2 -0
- package/commands/builder.js +26 -0
- package/commands/cleanup.d.ts +8 -0
- package/commands/cleanup.js +97 -0
- package/commands/dev-go.d.ts +8 -0
- package/commands/dev-go.js +306 -0
- package/commands/develop.d.ts +21 -0
- package/commands/develop.js +106 -0
- package/commands/pack.d.ts +82 -0
- package/commands/pack.js +230 -0
- package/commands/postinstall.d.ts +2 -0
- package/commands/postinstall.js +32 -0
- package/commands/update.d.ts +2 -0
- package/commands/update.js +22 -0
- package/index.js +6 -6
- package/package.json +1 -1
- package/src/commands/api-generate.d.ts +11 -0
- package/src/commands/api-generate.js +133 -0
- package/src/commands/builder.d.ts +2 -0
- package/src/commands/builder.js +26 -0
- package/src/commands/cleanup.d.ts +8 -0
- package/src/commands/cleanup.js +97 -0
- package/src/commands/dev-go.d.ts +8 -0
- package/src/commands/dev-go.js +306 -0
- package/src/commands/develop.d.ts +21 -0
- package/src/commands/develop.js +106 -0
- package/src/commands/pack.d.ts +82 -0
- package/src/commands/pack.js +230 -0
- package/src/commands/postinstall.d.ts +2 -0
- package/src/commands/postinstall.js +32 -0
- package/src/commands/update.d.ts +2 -0
- package/src/commands/update.js +22 -0
- package/src/nuxt-config.d.ts +7 -51
- package/src/nuxt-config.js +110 -101
|
@@ -0,0 +1,230 @@
|
|
|
1
|
+
"use strict";
|
|
2
|
+
var __createBinding = (this && this.__createBinding) || (Object.create ? (function(o, m, k, k2) {
|
|
3
|
+
if (k2 === undefined) k2 = k;
|
|
4
|
+
var desc = Object.getOwnPropertyDescriptor(m, k);
|
|
5
|
+
if (!desc || ("get" in desc ? !m.__esModule : desc.writable || desc.configurable)) {
|
|
6
|
+
desc = { enumerable: true, get: function() { return m[k]; } };
|
|
7
|
+
}
|
|
8
|
+
Object.defineProperty(o, k2, desc);
|
|
9
|
+
}) : (function(o, m, k, k2) {
|
|
10
|
+
if (k2 === undefined) k2 = k;
|
|
11
|
+
o[k2] = m[k];
|
|
12
|
+
}));
|
|
13
|
+
var __setModuleDefault = (this && this.__setModuleDefault) || (Object.create ? (function(o, v) {
|
|
14
|
+
Object.defineProperty(o, "default", { enumerable: true, value: v });
|
|
15
|
+
}) : function(o, v) {
|
|
16
|
+
o["default"] = v;
|
|
17
|
+
});
|
|
18
|
+
var __importStar = (this && this.__importStar) || (function () {
|
|
19
|
+
var ownKeys = function(o) {
|
|
20
|
+
ownKeys = Object.getOwnPropertyNames || function (o) {
|
|
21
|
+
var ar = [];
|
|
22
|
+
for (var k in o) if (Object.prototype.hasOwnProperty.call(o, k)) ar[ar.length] = k;
|
|
23
|
+
return ar;
|
|
24
|
+
};
|
|
25
|
+
return ownKeys(o);
|
|
26
|
+
};
|
|
27
|
+
return function (mod) {
|
|
28
|
+
if (mod && mod.__esModule) return mod;
|
|
29
|
+
var result = {};
|
|
30
|
+
if (mod != null) for (var k = ownKeys(mod), i = 0; i < k.length; i++) if (k[i] !== "default") __createBinding(result, mod, k[i]);
|
|
31
|
+
__setModuleDefault(result, mod);
|
|
32
|
+
return result;
|
|
33
|
+
};
|
|
34
|
+
})();
|
|
35
|
+
var __awaiter = (this && this.__awaiter) || function (thisArg, _arguments, P, generator) {
|
|
36
|
+
function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); }
|
|
37
|
+
return new (P || (P = Promise))(function (resolve, reject) {
|
|
38
|
+
function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } }
|
|
39
|
+
function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } }
|
|
40
|
+
function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); }
|
|
41
|
+
step((generator = generator.apply(thisArg, _arguments || [])).next());
|
|
42
|
+
});
|
|
43
|
+
};
|
|
44
|
+
var __importDefault = (this && this.__importDefault) || function (mod) {
|
|
45
|
+
return (mod && mod.__esModule) ? mod : { "default": mod };
|
|
46
|
+
};
|
|
47
|
+
Object.defineProperty(exports, "__esModule", { value: true });
|
|
48
|
+
exports.FILES_TO_COPY = exports.PACKAGE_JSON_CONTENT = exports.SERVER_EXECUTABLE = exports.PACK_CONFIG_PATH = exports.ORIGINAL_DIST_PATH = exports.SERVER_PATH = exports.ZIP_PATH = void 0;
|
|
49
|
+
exports.builtPath = builtPath;
|
|
50
|
+
exports.buildAndPack = buildAndPack;
|
|
51
|
+
// 导入项目构建工具,用于执行 Nuxt 项目的构建流程
|
|
52
|
+
const builder_1 = __importDefault(require("./builder"));
|
|
53
|
+
// 导入 7zip 压缩工具库,用于将构建后的文件打包为 7z 格式
|
|
54
|
+
const Zip = __importStar(require("7zip-min"));
|
|
55
|
+
// 导入增强版的文件系统模块,提供更丰富的文件操作 API
|
|
56
|
+
const FS = __importStar(require("fs-extra"));
|
|
57
|
+
// 导入路径处理模块,用于规范化和解析文件路径
|
|
58
|
+
const Path = __importStar(require("path"));
|
|
59
|
+
const os = __importStar(require("os"));
|
|
60
|
+
const fast_glob_1 = __importDefault(require("fast-glob"));
|
|
61
|
+
/**
|
|
62
|
+
* 生成相对于服务器构建目录的绝对路径
|
|
63
|
+
* @param relativePath - 相对路径
|
|
64
|
+
* @returns 解析后的绝对路径
|
|
65
|
+
*/
|
|
66
|
+
function builtPath(relativePath) {
|
|
67
|
+
return Path.resolve(exports.SERVER_PATH, relativePath);
|
|
68
|
+
}
|
|
69
|
+
// 定义打包后的 7z 文件输出路径
|
|
70
|
+
exports.ZIP_PATH = Path.resolve(process.cwd(), ".build/production/server.7z");
|
|
71
|
+
// 定义服务器构建文件的输出目录
|
|
72
|
+
exports.SERVER_PATH = Path.resolve(process.cwd(), ".build/production/server");
|
|
73
|
+
// 定义原始 dist 目录路径,用于清理操作
|
|
74
|
+
exports.ORIGINAL_DIST_PATH = Path.resolve(process.cwd(), "dist");
|
|
75
|
+
exports.PACK_CONFIG_PATH = Path.resolve(process.cwd(), "pack.config.json");
|
|
76
|
+
exports.SERVER_EXECUTABLE = os.platform() === "win32" ? "server-production.exe" : "server-production"; // 根据操作系统选择可执行文件名
|
|
77
|
+
// 定义打包后项目的 package.json 内容
|
|
78
|
+
exports.PACKAGE_JSON_CONTENT = {
|
|
79
|
+
private: true,
|
|
80
|
+
scripts: {
|
|
81
|
+
start: "./server-production.exe", // 定义启动命令
|
|
82
|
+
},
|
|
83
|
+
};
|
|
84
|
+
// 定义需要复制到构建目录的文件映射关系(目标为构建目录下的相对路径)
|
|
85
|
+
const DEFAULT_FILES_TO_COPY = {
|
|
86
|
+
"vue/.output": "vue/.output", // Vue 应用构建输出
|
|
87
|
+
[`.build/.server/production.exe`]: "server-production.exe", // 生产环境可执行文件
|
|
88
|
+
"server.config.json": "server.config.json", // 服务器配置文件
|
|
89
|
+
};
|
|
90
|
+
// 兼容旧导出:默认构建目录下的绝对目标路径
|
|
91
|
+
exports.FILES_TO_COPY = Object.fromEntries(Object.entries(DEFAULT_FILES_TO_COPY).map(([src, dest]) => [src, builtPath(dest)]));
|
|
92
|
+
/**
|
|
93
|
+
* 写入启动脚本和 package.json 文件到构建目录
|
|
94
|
+
*/
|
|
95
|
+
function writeScriptFiles(serverPath, config) {
|
|
96
|
+
// 写入 Windows 批处理启动脚本
|
|
97
|
+
FS.outputFileSync(Path.resolve(serverPath, "start.bat"), `powershell -ExecutionPolicy ByPass -File ./start.ps1`);
|
|
98
|
+
// 写入 PowerShell 启动脚本
|
|
99
|
+
FS.outputFileSync(Path.resolve(serverPath, "start.ps1"), `./server-production.exe`);
|
|
100
|
+
// 写入 Linux/macOS 启动脚本
|
|
101
|
+
FS.outputFileSync(Path.resolve(serverPath, "start.sh"), `./server-production.exe`);
|
|
102
|
+
// 写入 package.json 文件,使用 2 个空格缩进
|
|
103
|
+
const mergedPackageJson = mergePackageJson(exports.PACKAGE_JSON_CONTENT, config === null || config === void 0 ? void 0 : config.packageJson);
|
|
104
|
+
FS.outputJSONSync(Path.resolve(serverPath, "package.json"), mergedPackageJson, { spaces: 2 });
|
|
105
|
+
}
|
|
106
|
+
/**
|
|
107
|
+
* 将配置的源文件复制到构建目录
|
|
108
|
+
*/
|
|
109
|
+
function copyGeneratedFiles(serverPath, config) {
|
|
110
|
+
var _a;
|
|
111
|
+
const copyOptions = {
|
|
112
|
+
overwrite: (config === null || config === void 0 ? void 0 : config.overwrite) !== false,
|
|
113
|
+
errorOnExist: (config === null || config === void 0 ? void 0 : config.overwrite) === false,
|
|
114
|
+
};
|
|
115
|
+
// 遍历文件映射,将每个源文件复制到目标位置
|
|
116
|
+
for (const [src, dest] of Object.entries(DEFAULT_FILES_TO_COPY)) {
|
|
117
|
+
const resolvedDest = Path.resolve(serverPath, dest);
|
|
118
|
+
FS.copySync(Path.resolve(process.cwd(), src), resolvedDest, copyOptions);
|
|
119
|
+
}
|
|
120
|
+
if (config === null || config === void 0 ? void 0 : config.extraFiles) {
|
|
121
|
+
for (const [src, dest] of Object.entries(config.extraFiles)) {
|
|
122
|
+
const resolvedSrc = Path.resolve(process.cwd(), src);
|
|
123
|
+
const resolvedDest = Path.isAbsolute(dest) ? dest : Path.resolve(serverPath, dest);
|
|
124
|
+
FS.copySync(resolvedSrc, resolvedDest, copyOptions);
|
|
125
|
+
}
|
|
126
|
+
}
|
|
127
|
+
if ((_a = config === null || config === void 0 ? void 0 : config.extraFilesGlobs) === null || _a === void 0 ? void 0 : _a.length) {
|
|
128
|
+
const matchedFiles = fast_glob_1.default.sync(config.extraFilesGlobs, {
|
|
129
|
+
cwd: process.cwd(),
|
|
130
|
+
onlyFiles: true,
|
|
131
|
+
dot: true,
|
|
132
|
+
ignore: config.exclude,
|
|
133
|
+
});
|
|
134
|
+
for (const file of matchedFiles) {
|
|
135
|
+
const resolvedSrc = Path.resolve(process.cwd(), file);
|
|
136
|
+
const resolvedDest = Path.resolve(serverPath, file);
|
|
137
|
+
FS.copySync(resolvedSrc, resolvedDest, copyOptions);
|
|
138
|
+
}
|
|
139
|
+
}
|
|
140
|
+
}
|
|
141
|
+
function mergePackageJson(base, override) {
|
|
142
|
+
if (!override) {
|
|
143
|
+
return base;
|
|
144
|
+
}
|
|
145
|
+
const baseScripts = typeof base.scripts === "object" && base.scripts ? base.scripts : {};
|
|
146
|
+
const overrideScripts = typeof override.scripts === "object" && override.scripts ? override.scripts : {};
|
|
147
|
+
return Object.assign(Object.assign(Object.assign({}, base), override), { scripts: Object.assign(Object.assign({}, baseScripts), overrideScripts) });
|
|
148
|
+
}
|
|
149
|
+
function readPackConfigFromCwd() {
|
|
150
|
+
if (!FS.existsSync(exports.PACK_CONFIG_PATH)) {
|
|
151
|
+
return undefined;
|
|
152
|
+
}
|
|
153
|
+
return FS.readJSONSync(exports.PACK_CONFIG_PATH);
|
|
154
|
+
}
|
|
155
|
+
function resolveServerPath(config) {
|
|
156
|
+
if (!(config === null || config === void 0 ? void 0 : config.serverPath)) {
|
|
157
|
+
return exports.SERVER_PATH;
|
|
158
|
+
}
|
|
159
|
+
return Path.isAbsolute(config.serverPath)
|
|
160
|
+
? config.serverPath
|
|
161
|
+
: Path.resolve(process.cwd(), config.serverPath);
|
|
162
|
+
}
|
|
163
|
+
function resolveZipPath(config) {
|
|
164
|
+
if (config === null || config === void 0 ? void 0 : config.zipPath) {
|
|
165
|
+
return Path.isAbsolute(config.zipPath)
|
|
166
|
+
? config.zipPath
|
|
167
|
+
: Path.resolve(process.cwd(), config.zipPath);
|
|
168
|
+
}
|
|
169
|
+
if (config === null || config === void 0 ? void 0 : config.zipName) {
|
|
170
|
+
return Path.resolve(Path.dirname(exports.ZIP_PATH), config.zipName);
|
|
171
|
+
}
|
|
172
|
+
return exports.ZIP_PATH;
|
|
173
|
+
}
|
|
174
|
+
/**
|
|
175
|
+
* 打包文件为7z格式
|
|
176
|
+
*/
|
|
177
|
+
function makeZip(serverPath, zipPath) {
|
|
178
|
+
return new Promise((resolve, reject) => {
|
|
179
|
+
// 使用 7zip 将服务器构建目录打包为 7z 文件
|
|
180
|
+
Zip.pack(serverPath, zipPath, (error) => {
|
|
181
|
+
if (error) {
|
|
182
|
+
console.error("打包失败:", error);
|
|
183
|
+
reject(error);
|
|
184
|
+
}
|
|
185
|
+
console.log("打包成功:", zipPath);
|
|
186
|
+
resolve(zipPath);
|
|
187
|
+
});
|
|
188
|
+
});
|
|
189
|
+
}
|
|
190
|
+
/**
|
|
191
|
+
* 清理原始 dist 目录
|
|
192
|
+
*/
|
|
193
|
+
function cleanUp(config) {
|
|
194
|
+
if ((config === null || config === void 0 ? void 0 : config.cleanDist) === false) {
|
|
195
|
+
return;
|
|
196
|
+
}
|
|
197
|
+
// 检查原始 dist 目录是否存在,存在则删除
|
|
198
|
+
if (FS.existsSync(exports.ORIGINAL_DIST_PATH)) {
|
|
199
|
+
FS.removeSync(exports.ORIGINAL_DIST_PATH);
|
|
200
|
+
}
|
|
201
|
+
}
|
|
202
|
+
/**
|
|
203
|
+
* 构建并打包项目的主函数
|
|
204
|
+
* 1. 执行项目构建
|
|
205
|
+
* 2. 复制生成的文件
|
|
206
|
+
* 3. 写入启动脚本
|
|
207
|
+
* 4. 打包文件为 7z 格式
|
|
208
|
+
* 5. 清理原始 dist 目录
|
|
209
|
+
*/
|
|
210
|
+
function buildAndPack(config) {
|
|
211
|
+
return __awaiter(this, void 0, void 0, function* () {
|
|
212
|
+
const resolvedConfig = config !== null && config !== void 0 ? config : readPackConfigFromCwd();
|
|
213
|
+
const serverPath = resolveServerPath(resolvedConfig);
|
|
214
|
+
const zipPath = resolveZipPath(resolvedConfig);
|
|
215
|
+
yield (0, builder_1.default)(); // 执行项目构建
|
|
216
|
+
if (resolvedConfig === null || resolvedConfig === void 0 ? void 0 : resolvedConfig.beforePack) {
|
|
217
|
+
yield resolvedConfig.beforePack();
|
|
218
|
+
}
|
|
219
|
+
copyGeneratedFiles(serverPath, resolvedConfig); // 复制相关文件
|
|
220
|
+
if ((resolvedConfig === null || resolvedConfig === void 0 ? void 0 : resolvedConfig.writeScripts) !== false) {
|
|
221
|
+
writeScriptFiles(serverPath, resolvedConfig); // 写入脚本文件
|
|
222
|
+
}
|
|
223
|
+
yield makeZip(serverPath, zipPath); // 打包文件
|
|
224
|
+
if (resolvedConfig === null || resolvedConfig === void 0 ? void 0 : resolvedConfig.afterPack) {
|
|
225
|
+
yield resolvedConfig.afterPack(zipPath);
|
|
226
|
+
}
|
|
227
|
+
cleanUp(resolvedConfig); // 清理临时文件
|
|
228
|
+
});
|
|
229
|
+
}
|
|
230
|
+
exports.default = buildAndPack;
|
|
@@ -0,0 +1,32 @@
|
|
|
1
|
+
"use strict";
|
|
2
|
+
var __importDefault = (this && this.__importDefault) || function (mod) {
|
|
3
|
+
return (mod && mod.__esModule) ? mod : { "default": mod };
|
|
4
|
+
};
|
|
5
|
+
Object.defineProperty(exports, "__esModule", { value: true });
|
|
6
|
+
exports.postInstall = postInstall;
|
|
7
|
+
const concurrently_1 = __importDefault(require("concurrently"));
|
|
8
|
+
const node_child_process_1 = require("node:child_process");
|
|
9
|
+
function postInstall() {
|
|
10
|
+
const hasGo = (0, node_child_process_1.spawnSync)("go", ["version"], { stdio: "ignore", shell: true }).status ===
|
|
11
|
+
0;
|
|
12
|
+
const commands = [
|
|
13
|
+
{
|
|
14
|
+
command: "npx nuxt prepare",
|
|
15
|
+
name: "nuxt",
|
|
16
|
+
prefixColor: "blue",
|
|
17
|
+
},
|
|
18
|
+
];
|
|
19
|
+
if (hasGo) {
|
|
20
|
+
commands.unshift({
|
|
21
|
+
command: "go mod download && go mod tidy",
|
|
22
|
+
name: "go",
|
|
23
|
+
prefixColor: "green",
|
|
24
|
+
});
|
|
25
|
+
}
|
|
26
|
+
else {
|
|
27
|
+
console.warn("[nuxt-gin-tools] 未检测到 Go,已跳过 Go 相关安装。请先安装 Go 后再重新运行相关命令。");
|
|
28
|
+
}
|
|
29
|
+
// 执行并发命令
|
|
30
|
+
return (0, concurrently_1.default)(commands).result;
|
|
31
|
+
}
|
|
32
|
+
exports.default = postInstall;
|
|
@@ -0,0 +1,22 @@
|
|
|
1
|
+
"use strict";
|
|
2
|
+
var __importDefault = (this && this.__importDefault) || function (mod) {
|
|
3
|
+
return (mod && mod.__esModule) ? mod : { "default": mod };
|
|
4
|
+
};
|
|
5
|
+
Object.defineProperty(exports, "__esModule", { value: true });
|
|
6
|
+
exports.update = update;
|
|
7
|
+
const concurrently_1 = __importDefault(require("concurrently"));
|
|
8
|
+
function update() {
|
|
9
|
+
(0, concurrently_1.default)([
|
|
10
|
+
{
|
|
11
|
+
command: "pnpm update --latest",
|
|
12
|
+
name: "pnpm",
|
|
13
|
+
prefixColor: "magenta",
|
|
14
|
+
},
|
|
15
|
+
{
|
|
16
|
+
command: "go get -u && go mod tidy",
|
|
17
|
+
name: "go",
|
|
18
|
+
prefixColor: "green",
|
|
19
|
+
},
|
|
20
|
+
]);
|
|
21
|
+
}
|
|
22
|
+
exports.default = update;
|
package/src/nuxt-config.d.ts
CHANGED
|
@@ -1,63 +1,19 @@
|
|
|
1
1
|
import type { NuxtConfig } from "nuxt/config";
|
|
2
|
+
import { type IncomingMessage, type ServerResponse } from "node:http";
|
|
3
|
+
import type { Socket } from "node:net";
|
|
2
4
|
export interface ServerConfigJson {
|
|
3
|
-
/**
|
|
4
|
-
* 前端基础 URL
|
|
5
|
-
* 用于指定前端路由的基础路径
|
|
6
|
-
*/
|
|
5
|
+
/** 前端基础 URL */
|
|
7
6
|
baseUrl: string;
|
|
8
|
-
/**
|
|
9
|
-
* Nuxt 端口号
|
|
10
|
-
* 用于指定 Nuxt 项目的开发服务器端口号
|
|
11
|
-
* 例如,如果 Nuxt 项目的开发服务器端口号为 3000,则 nuxtPort 为 3000
|
|
12
|
-
*/
|
|
7
|
+
/** Nuxt 开发端口 */
|
|
13
8
|
nuxtPort: number;
|
|
14
|
-
/**
|
|
15
|
-
* Gin 端口号
|
|
16
|
-
* 用于指定 Gin 服务器的端口号
|
|
17
|
-
* 例如,如果 Gin 服务器的端口号为 8080,则 ginPort 为 8080
|
|
18
|
-
*/
|
|
9
|
+
/** Gin 服务端口 */
|
|
19
10
|
ginPort: number;
|
|
20
11
|
}
|
|
21
12
|
export interface MyNuxtConfig {
|
|
22
|
-
/**
|
|
23
|
-
* 服务器基础路径
|
|
24
|
-
* 用于指定服务器端路由的基础路径
|
|
25
|
-
* 例如,如果服务器端路由为 /api,则 serverBasePath 为 /api
|
|
26
|
-
*/
|
|
27
|
-
apiBasePath: string;
|
|
28
|
-
/**
|
|
29
|
-
* WebSocket 代理基础路径列表(可选)
|
|
30
|
-
* 例如:["/ws-go", "/socket"]
|
|
31
|
-
* 会同时注入 Nitro devProxy 与 Vite proxy,默认启用 ws。
|
|
32
|
-
*/
|
|
33
|
-
wsProxyBasePaths?: string[];
|
|
34
|
-
/**
|
|
35
|
-
* 服务器配置
|
|
36
|
-
* 包含服务器端的相关配置,如端口号、基础路径等
|
|
37
|
-
*/
|
|
13
|
+
/** 服务器配置 */
|
|
38
14
|
serverConfig: ServerConfigJson;
|
|
39
15
|
}
|
|
40
16
|
/**
|
|
41
|
-
* 创建默认的 Nuxt
|
|
42
|
-
* @param param0 包含服务器配置和 API 基础路径的参数对象
|
|
43
|
-
* @returns Nuxt 配置对象
|
|
44
|
-
*
|
|
45
|
-
* 用法如下:
|
|
46
|
-
* ```typescript
|
|
47
|
-
* import { createDefaultConfig } from 'nuxt-gin-tools/src/nuxt-config';
|
|
48
|
-
* import type { NuxtConfig } from 'nuxt/config';
|
|
49
|
-
* import { defineNuxtConfig } from 'nuxt/config';
|
|
50
|
-
* import SERVER_CONFIG from './server.config.json';
|
|
51
|
-
* import { BASE_PATH } from './vue/composables/api/base';
|
|
52
|
-
*
|
|
53
|
-
* const config = createDefaultConfig({
|
|
54
|
-
* apiBasePath: BASE_PATH,
|
|
55
|
-
* serverConfig: SERVER_CONFIG,
|
|
56
|
-
* }) as NuxtConfig;
|
|
57
|
-
*
|
|
58
|
-
* export default defineNuxtConfig({
|
|
59
|
-
* ...config,
|
|
60
|
-
* });
|
|
61
|
-
* ```
|
|
17
|
+
* 创建默认的 Nuxt 配置。
|
|
62
18
|
*/
|
|
63
19
|
export function createDefaultConfig(config: MyNuxtConfig): NuxtConfig;
|
package/src/nuxt-config.js
CHANGED
|
@@ -1,85 +1,92 @@
|
|
|
1
1
|
"use strict";
|
|
2
2
|
Object.defineProperty(exports, "__esModule", { value: true });
|
|
3
3
|
exports.createDefaultConfig = createDefaultConfig;
|
|
4
|
+
const node_http_1 = require("node:http");
|
|
5
|
+
function normalizePathPrefix(value) {
|
|
6
|
+
const withLeadingSlash = value.startsWith("/") ? value : `/${value}`;
|
|
7
|
+
if (withLeadingSlash !== "/" && withLeadingSlash.endsWith("/")) {
|
|
8
|
+
return withLeadingSlash.slice(0, -1);
|
|
9
|
+
}
|
|
10
|
+
return withLeadingSlash;
|
|
11
|
+
}
|
|
12
|
+
function normalizeBaseUrl(value) {
|
|
13
|
+
return normalizePathPrefix(value || "/");
|
|
14
|
+
}
|
|
15
|
+
function isViteInternalRequest(requestPath) {
|
|
16
|
+
return (requestPath.startsWith("/@vite") ||
|
|
17
|
+
requestPath.startsWith("/__vite") ||
|
|
18
|
+
requestPath.startsWith("/node_modules/") ||
|
|
19
|
+
requestPath.startsWith("/@id/"));
|
|
20
|
+
}
|
|
21
|
+
function isBaseUrlRequest(baseUrl, requestPath) {
|
|
22
|
+
if (baseUrl === "/") {
|
|
23
|
+
return true;
|
|
24
|
+
}
|
|
25
|
+
return requestPath === baseUrl || requestPath.startsWith(`${baseUrl}/`);
|
|
26
|
+
}
|
|
27
|
+
function forwardToGin(ginPort, req, res) {
|
|
28
|
+
var _a;
|
|
29
|
+
const proxyReq = (0, node_http_1.request)({
|
|
30
|
+
hostname: "127.0.0.1",
|
|
31
|
+
port: ginPort,
|
|
32
|
+
path: (_a = req.url) !== null && _a !== void 0 ? _a : "/",
|
|
33
|
+
method: req.method,
|
|
34
|
+
headers: Object.assign(Object.assign({}, req.headers), { host: `127.0.0.1:${ginPort}` }),
|
|
35
|
+
}, (proxyRes) => {
|
|
36
|
+
var _a;
|
|
37
|
+
res.writeHead((_a = proxyRes.statusCode) !== null && _a !== void 0 ? _a : 502, proxyRes.headers);
|
|
38
|
+
proxyRes.pipe(res);
|
|
39
|
+
});
|
|
40
|
+
proxyReq.on("error", (error) => {
|
|
41
|
+
const message = error instanceof Error ? error.message : String(error);
|
|
42
|
+
res.statusCode = 502;
|
|
43
|
+
res.setHeader("content-type", "application/json; charset=utf-8");
|
|
44
|
+
res.end(JSON.stringify({ error: "Bad Gateway", message }));
|
|
45
|
+
});
|
|
46
|
+
req.pipe(proxyReq);
|
|
47
|
+
}
|
|
48
|
+
function forwardWebSocketToGin(ginPort, req, clientSocket, clientHead) {
|
|
49
|
+
var _a, _b;
|
|
50
|
+
const proxyReq = (0, node_http_1.request)({
|
|
51
|
+
hostname: "127.0.0.1",
|
|
52
|
+
port: ginPort,
|
|
53
|
+
path: (_a = req.url) !== null && _a !== void 0 ? _a : "/",
|
|
54
|
+
method: (_b = req.method) !== null && _b !== void 0 ? _b : "GET",
|
|
55
|
+
headers: Object.assign(Object.assign({}, req.headers), { host: `127.0.0.1:${ginPort}`, connection: "Upgrade" }),
|
|
56
|
+
});
|
|
57
|
+
proxyReq.on("upgrade", (proxyRes, proxySocket, proxyHead) => {
|
|
58
|
+
var _a, _b;
|
|
59
|
+
const statusLine = `HTTP/1.1 ${(_a = proxyRes.statusCode) !== null && _a !== void 0 ? _a : 101} ${(_b = proxyRes.statusMessage) !== null && _b !== void 0 ? _b : "Switching Protocols"}\r\n`;
|
|
60
|
+
const headers = proxyRes.rawHeaders;
|
|
61
|
+
let headerText = "";
|
|
62
|
+
for (let i = 0; i < headers.length; i += 2) {
|
|
63
|
+
headerText += `${headers[i]}: ${headers[i + 1]}\r\n`;
|
|
64
|
+
}
|
|
65
|
+
clientSocket.write(`${statusLine}${headerText}\r\n`);
|
|
66
|
+
if (clientHead.length > 0) {
|
|
67
|
+
proxySocket.write(clientHead);
|
|
68
|
+
}
|
|
69
|
+
if (proxyHead.length > 0) {
|
|
70
|
+
clientSocket.write(proxyHead);
|
|
71
|
+
}
|
|
72
|
+
proxySocket.pipe(clientSocket).pipe(proxySocket);
|
|
73
|
+
});
|
|
74
|
+
proxyReq.on("error", () => {
|
|
75
|
+
if (!clientSocket.destroyed) {
|
|
76
|
+
clientSocket.destroy();
|
|
77
|
+
}
|
|
78
|
+
});
|
|
79
|
+
proxyReq.end();
|
|
80
|
+
}
|
|
4
81
|
/**
|
|
5
|
-
* 创建默认的 Nuxt
|
|
6
|
-
* @param param0 包含服务器配置和 API 基础路径的参数对象
|
|
7
|
-
* @returns Nuxt 配置对象
|
|
8
|
-
*
|
|
9
|
-
* 用法如下:
|
|
10
|
-
* ```typescript
|
|
11
|
-
* import { createDefaultConfig } from 'nuxt-gin-tools/src/nuxt-config';
|
|
12
|
-
* import type { NuxtConfig } from 'nuxt/config';
|
|
13
|
-
* import { defineNuxtConfig } from 'nuxt/config';
|
|
14
|
-
* import SERVER_CONFIG from './server.config.json';
|
|
15
|
-
* import { BASE_PATH } from './vue/composables/api/base';
|
|
16
|
-
*
|
|
17
|
-
* const config = createDefaultConfig({
|
|
18
|
-
* apiBasePath: BASE_PATH,
|
|
19
|
-
* serverConfig: SERVER_CONFIG,
|
|
20
|
-
* }) as NuxtConfig;
|
|
21
|
-
*
|
|
22
|
-
* export default defineNuxtConfig({
|
|
23
|
-
* ...config,
|
|
24
|
-
* });
|
|
25
|
-
* ```
|
|
82
|
+
* 创建默认的 Nuxt 配置。
|
|
26
83
|
*/
|
|
27
|
-
function createDefaultConfig({ serverConfig,
|
|
28
|
-
|
|
29
|
-
* 处理基础路径,去除协议和域名部分,只保留路径部分
|
|
30
|
-
* 例如,将 "https://example.com/api-go" 转换为 "/api-go"
|
|
31
|
-
*/
|
|
32
|
-
const thisBasePath = apiBasePath.replace(/^https?:[/]{2}[^/]+/, "");
|
|
33
|
-
const normalizedProxyBasePath = thisBasePath.endsWith("/")
|
|
34
|
-
? thisBasePath.slice(0, -1)
|
|
35
|
-
: thisBasePath;
|
|
36
|
-
const normalizeBasePath = (rawPath) => {
|
|
37
|
-
const trimmed = rawPath.replace(/^https?:[/]{2}[^/]+/, "");
|
|
38
|
-
if (!trimmed)
|
|
39
|
-
return "/";
|
|
40
|
-
if (trimmed === "/")
|
|
41
|
-
return "/";
|
|
42
|
-
return trimmed.endsWith("/") ? trimmed.slice(0, -1) : trimmed;
|
|
43
|
-
};
|
|
44
|
-
// Proxy target should point to backend origin only.
|
|
45
|
-
// The matched route prefix (e.g. /api-go/v1, /ws-go) is preserved by proxy itself.
|
|
46
|
-
// If target also appends basePath, final upstream path becomes duplicated and can
|
|
47
|
-
// break websocket upgrades with ECONNRESET.
|
|
48
|
-
const buildTarget = () => `http://127.0.0.1:${serverConfig.ginPort}`;
|
|
49
|
-
/**
|
|
50
|
-
* 目标服务器的 URL
|
|
51
|
-
* 格式为:http://localhost:ginPort/serverBasePath
|
|
52
|
-
* 其中,ginPort 是从 serverConfig 中获取的 Gin 服务器的端口号
|
|
53
|
-
* serverBasePath 是从 MyNuxtConfig 中获取的服务器基础路径
|
|
54
|
-
*/
|
|
55
|
-
const target = buildTarget();
|
|
56
|
-
const proxyEntries = {
|
|
57
|
-
[normalizedProxyBasePath]: {
|
|
58
|
-
target,
|
|
59
|
-
changeOrigin: true,
|
|
60
|
-
ws: true,
|
|
61
|
-
},
|
|
62
|
-
};
|
|
63
|
-
for (const rawPath of wsProxyBasePaths) {
|
|
64
|
-
const normalizedPath = normalizeBasePath(rawPath);
|
|
65
|
-
proxyEntries[normalizedPath] = {
|
|
66
|
-
target: buildTarget(),
|
|
67
|
-
changeOrigin: true,
|
|
68
|
-
ws: true,
|
|
69
|
-
};
|
|
70
|
-
}
|
|
84
|
+
function createDefaultConfig({ serverConfig, }) {
|
|
85
|
+
const baseUrl = normalizeBaseUrl(serverConfig.baseUrl);
|
|
71
86
|
return {
|
|
72
|
-
buildDir: "vue/.nuxt",
|
|
73
|
-
srcDir: "vue",
|
|
74
|
-
// 设置服务器端代码的目录为 "vue/server",表示服务器端的代码将存放在该目录下
|
|
75
|
-
// serverDir: "vue/server",
|
|
76
|
-
// 禁用服务器端渲染(SSR),即页面将在客户端进行渲染
|
|
87
|
+
buildDir: "vue/.nuxt",
|
|
88
|
+
srcDir: "vue",
|
|
77
89
|
ssr: false,
|
|
78
|
-
/**
|
|
79
|
-
* 配置实验性功能
|
|
80
|
-
* 禁用 payloadExtraction 功能,该功能可能用于提取页面的有效负载数据
|
|
81
|
-
* 这里禁用它可能是为了避免某些兼容性问题或特定的项目需求
|
|
82
|
-
*/
|
|
83
90
|
experimental: {
|
|
84
91
|
payloadExtraction: false,
|
|
85
92
|
},
|
|
@@ -88,17 +95,7 @@ function createDefaultConfig({ serverConfig, apiBasePath, wsProxyBasePaths = [],
|
|
|
88
95
|
enabled: true,
|
|
89
96
|
},
|
|
90
97
|
},
|
|
91
|
-
/**
|
|
92
|
-
* 配置应用的基础 URL
|
|
93
|
-
* 从 server.config.json 文件中获取 baseUrl 作为应用的基础 URL
|
|
94
|
-
* 这个基础 URL 将用于构建应用的路由和请求地址
|
|
95
|
-
*/
|
|
96
98
|
app: { baseURL: serverConfig.baseUrl },
|
|
97
|
-
/**
|
|
98
|
-
* 配置开发服务器的端口号
|
|
99
|
-
* 从 server.config.json 文件中获取 nuxtPort 作为开发服务器的端口号
|
|
100
|
-
* 启动开发服务器时,将使用该端口号进行监听
|
|
101
|
-
*/
|
|
102
99
|
devServer: {
|
|
103
100
|
port: serverConfig.nuxtPort,
|
|
104
101
|
cors: {
|
|
@@ -109,23 +106,35 @@ function createDefaultConfig({ serverConfig, apiBasePath, wsProxyBasePaths = [],
|
|
|
109
106
|
maxAge: "1728000",
|
|
110
107
|
},
|
|
111
108
|
},
|
|
112
|
-
nitro: {
|
|
113
|
-
output: {
|
|
114
|
-
// 设置输出目录为 "vue/.nuxt", 表示 Nitro 的构建输出
|
|
115
|
-
dir: "vue/.output",
|
|
116
|
-
},
|
|
117
|
-
// 定义代理规则,将匹配基础路径的请求代理到目标服务器
|
|
118
|
-
devProxy: proxyEntries,
|
|
119
|
-
},
|
|
120
109
|
vite: {
|
|
121
|
-
server: {
|
|
122
|
-
|
|
123
|
-
|
|
124
|
-
|
|
125
|
-
|
|
126
|
-
|
|
127
|
-
|
|
128
|
-
|
|
110
|
+
server: {},
|
|
111
|
+
plugins: [
|
|
112
|
+
{
|
|
113
|
+
name: "nuxt-gin-base-url-proxy",
|
|
114
|
+
configureServer(server) {
|
|
115
|
+
server.middlewares.use((req, res, next) => {
|
|
116
|
+
var _a;
|
|
117
|
+
const requestPath = ((_a = req.url) !== null && _a !== void 0 ? _a : "/").split("?")[0] || "/";
|
|
118
|
+
const shouldForward = !isViteInternalRequest(requestPath) && !isBaseUrlRequest(baseUrl, requestPath);
|
|
119
|
+
if (shouldForward) {
|
|
120
|
+
forwardToGin(serverConfig.ginPort, req, res);
|
|
121
|
+
return;
|
|
122
|
+
}
|
|
123
|
+
next();
|
|
124
|
+
});
|
|
125
|
+
if (server.httpServer) {
|
|
126
|
+
server.httpServer.on("upgrade", (req, socket, head) => {
|
|
127
|
+
var _a;
|
|
128
|
+
const requestPath = ((_a = req.url) !== null && _a !== void 0 ? _a : "/").split("?")[0] || "/";
|
|
129
|
+
const shouldForward = !isViteInternalRequest(requestPath) && !isBaseUrlRequest(baseUrl, requestPath);
|
|
130
|
+
if (shouldForward) {
|
|
131
|
+
forwardWebSocketToGin(serverConfig.ginPort, req, socket, head);
|
|
132
|
+
}
|
|
133
|
+
});
|
|
134
|
+
}
|
|
135
|
+
},
|
|
136
|
+
},
|
|
137
|
+
],
|
|
129
138
|
esbuild: { jsxFactory: "h", jsxFragment: "Fragment" },
|
|
130
139
|
},
|
|
131
140
|
};
|