@kkkwww/deploy 1.0.16 → 1.0.18
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/lib/index.d.ts +1 -1
- package/lib/index.js +158 -104
- package/lib/index.js.map +1 -1
- package/package.json +1 -1
package/lib/index.d.ts
CHANGED
|
@@ -1,2 +1,2 @@
|
|
|
1
|
-
#!/usr/bin/env node
|
|
1
|
+
#!/usr/bin/env ts-node
|
|
2
2
|
export {};
|
package/lib/index.js
CHANGED
|
@@ -1,4 +1,4 @@
|
|
|
1
|
-
#!/usr/bin/env node
|
|
1
|
+
#!/usr/bin/env ts-node
|
|
2
2
|
var __awaiter = (this && this.__awaiter) || function (thisArg, _arguments, P, generator) {
|
|
3
3
|
function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); }
|
|
4
4
|
return new (P || (P = Promise))(function (resolve, reject) {
|
|
@@ -14,13 +14,34 @@ import os from 'os';
|
|
|
14
14
|
import SftpClient from 'ssh2-sftp-client';
|
|
15
15
|
import { fileURLToPath } from 'url';
|
|
16
16
|
// ==========================
|
|
17
|
+
// ESM 兼容 __dirname
|
|
18
|
+
// ==========================
|
|
17
19
|
const __filename = fileURLToPath(import.meta.url);
|
|
18
20
|
const __dirname = path.dirname(__filename);
|
|
19
21
|
// ==========================
|
|
22
|
+
// 版本号
|
|
23
|
+
// ==========================
|
|
24
|
+
let VERSION = '0.0.0';
|
|
25
|
+
try {
|
|
26
|
+
const pkgPath = path.resolve(__dirname, '../package.json');
|
|
27
|
+
if (fs.existsSync(pkgPath)) {
|
|
28
|
+
const pkg = JSON.parse(fs.readFileSync(pkgPath, 'utf8'));
|
|
29
|
+
VERSION = pkg.version || '0.0.0';
|
|
30
|
+
}
|
|
31
|
+
}
|
|
32
|
+
catch (_a) { }
|
|
33
|
+
// ==========================
|
|
34
|
+
// 并发线程
|
|
35
|
+
// ==========================
|
|
20
36
|
const CONCURRENCY = 5;
|
|
37
|
+
// ==========================
|
|
38
|
+
// 文件路径
|
|
39
|
+
// ==========================
|
|
21
40
|
const CACHE_FILE = path.join(os.homedir(), '.deploy-cache.json');
|
|
22
41
|
const SKIP_LOG_FILE = path.join(os.homedir(), '.deploy-skip.log');
|
|
23
42
|
// ==========================
|
|
43
|
+
// 解析命令行参数
|
|
44
|
+
// ==========================
|
|
24
45
|
function getArgs() {
|
|
25
46
|
const args = {};
|
|
26
47
|
process.argv.slice(2).forEach((arg) => {
|
|
@@ -32,6 +53,8 @@ function getArgs() {
|
|
|
32
53
|
return args;
|
|
33
54
|
}
|
|
34
55
|
// ==========================
|
|
56
|
+
// 缓存读取和保存(数组形式,按 host)
|
|
57
|
+
// ==========================
|
|
35
58
|
function loadCache() {
|
|
36
59
|
try {
|
|
37
60
|
if (fs.existsSync(CACHE_FILE)) {
|
|
@@ -39,71 +62,110 @@ function loadCache() {
|
|
|
39
62
|
}
|
|
40
63
|
}
|
|
41
64
|
catch (_a) { }
|
|
42
|
-
return
|
|
65
|
+
return [];
|
|
66
|
+
}
|
|
67
|
+
function getCacheByHost(host) {
|
|
68
|
+
const list = loadCache();
|
|
69
|
+
return list.find(item => item.host === host) || {};
|
|
70
|
+
}
|
|
71
|
+
function saveCache(config) {
|
|
72
|
+
try {
|
|
73
|
+
const list = loadCache().filter(item => item.host !== config.host);
|
|
74
|
+
list.push({
|
|
75
|
+
host: config.host,
|
|
76
|
+
port: config.port,
|
|
77
|
+
user: config.user,
|
|
78
|
+
password: config.password,
|
|
79
|
+
remotePath: config.remotePath,
|
|
80
|
+
backup: config.backup
|
|
81
|
+
});
|
|
82
|
+
fs.writeFileSync(CACHE_FILE, JSON.stringify(list, null, 2));
|
|
83
|
+
console.log(`✅ 缓存已保存:${CACHE_FILE}`);
|
|
84
|
+
}
|
|
85
|
+
catch (e) {
|
|
86
|
+
console.error('❌ 保存缓存失败', e);
|
|
87
|
+
}
|
|
43
88
|
}
|
|
44
89
|
// ==========================
|
|
45
|
-
|
|
46
|
-
|
|
47
|
-
|
|
48
|
-
|
|
90
|
+
// 时间戳
|
|
91
|
+
// ==========================
|
|
92
|
+
function getTimeStamp() {
|
|
93
|
+
return new Date().toISOString().replace(/[:.]/g, '-');
|
|
49
94
|
}
|
|
50
95
|
// ==========================
|
|
51
|
-
|
|
52
|
-
|
|
53
|
-
|
|
54
|
-
|
|
96
|
+
// 跳过日志
|
|
97
|
+
// ==========================
|
|
98
|
+
function logSkip(fileName) {
|
|
99
|
+
const logLine = `${new Date().toISOString()} ⚡ 跳过已存在文件:${fileName}\n`;
|
|
100
|
+
fs.appendFileSync(SKIP_LOG_FILE, logLine);
|
|
101
|
+
console.log(logLine.trim());
|
|
55
102
|
}
|
|
56
103
|
// ==========================
|
|
57
|
-
|
|
104
|
+
// 判断文件是否相同
|
|
105
|
+
// ==========================
|
|
106
|
+
function isSameFile(sftp, localFile, remoteFile) {
|
|
58
107
|
return __awaiter(this, void 0, void 0, function* () {
|
|
59
108
|
try {
|
|
60
|
-
const
|
|
61
|
-
const
|
|
62
|
-
|
|
63
|
-
Math.floor(
|
|
64
|
-
|
|
65
|
-
catch (_a) {
|
|
66
|
-
return false;
|
|
109
|
+
const localStat = fs.statSync(localFile);
|
|
110
|
+
const remoteStat = yield sftp.stat(remoteFile);
|
|
111
|
+
if (localStat.size === remoteStat.size &&
|
|
112
|
+
Math.floor(localStat.mtimeMs / 1000) === Math.floor(remoteStat.modifyTime / 1000))
|
|
113
|
+
return true;
|
|
67
114
|
}
|
|
115
|
+
catch (_a) { }
|
|
116
|
+
return false;
|
|
68
117
|
});
|
|
69
118
|
}
|
|
70
119
|
// ==========================
|
|
120
|
+
// 确保远程目录存在(逐级创建)
|
|
121
|
+
// ==========================
|
|
71
122
|
function ensureRemoteDir(sftp, remoteDir) {
|
|
72
123
|
return __awaiter(this, void 0, void 0, function* () {
|
|
73
|
-
const
|
|
74
|
-
let
|
|
75
|
-
for (const
|
|
76
|
-
|
|
124
|
+
const dirs = remoteDir.split('/').filter(Boolean);
|
|
125
|
+
let current = '';
|
|
126
|
+
for (const dir of dirs) {
|
|
127
|
+
current += '/' + dir;
|
|
77
128
|
try {
|
|
78
|
-
yield sftp.stat(
|
|
129
|
+
yield sftp.stat(current);
|
|
79
130
|
}
|
|
80
131
|
catch (_a) {
|
|
81
|
-
|
|
82
|
-
|
|
132
|
+
try {
|
|
133
|
+
yield sftp.mkdir(current);
|
|
134
|
+
console.log(`📁 创建远程目录:${current}`);
|
|
135
|
+
}
|
|
136
|
+
catch (err) {
|
|
137
|
+
console.error(`❌ 创建目录失败:${current}`, err);
|
|
138
|
+
}
|
|
83
139
|
}
|
|
84
140
|
}
|
|
85
141
|
});
|
|
86
142
|
}
|
|
87
143
|
// ==========================
|
|
88
|
-
|
|
144
|
+
// 上传单文件
|
|
145
|
+
// ==========================
|
|
146
|
+
function uploadFile(sftp, localFile, remoteFile) {
|
|
89
147
|
return __awaiter(this, void 0, void 0, function* () {
|
|
90
|
-
|
|
91
|
-
|
|
148
|
+
const fileName = path.basename(localFile);
|
|
149
|
+
if (yield isSameFile(sftp, localFile, remoteFile)) {
|
|
150
|
+
logSkip(fileName);
|
|
92
151
|
return;
|
|
93
152
|
}
|
|
94
|
-
const
|
|
153
|
+
const fileSize = fs.statSync(localFile).size;
|
|
95
154
|
let uploaded = 0;
|
|
96
|
-
|
|
155
|
+
// 📌 先打印本地和远程路径
|
|
156
|
+
console.log(`\n📤 上传文件`);
|
|
157
|
+
console.log(` 本地路径: ${localFile}`);
|
|
158
|
+
console.log(` 远程路径: ${remoteFile}`);
|
|
97
159
|
return new Promise((resolve, reject) => {
|
|
98
|
-
const
|
|
99
|
-
|
|
100
|
-
uploaded +=
|
|
101
|
-
const pct = ((uploaded /
|
|
102
|
-
process.stdout.write(`
|
|
160
|
+
const readStream = fs.createReadStream(localFile);
|
|
161
|
+
readStream.on('data', (chunk) => {
|
|
162
|
+
uploaded += chunk.length;
|
|
163
|
+
const pct = ((uploaded / fileSize) * 100).toFixed(1);
|
|
164
|
+
process.stdout.write(` 进度:${pct}% (${uploaded}/${fileSize} B)\r`);
|
|
103
165
|
});
|
|
104
|
-
sftp.put(
|
|
166
|
+
sftp.put(readStream, remoteFile)
|
|
105
167
|
.then(() => {
|
|
106
|
-
console.log(` ✅
|
|
168
|
+
console.log(` ✅ 完成:${fileName}`);
|
|
107
169
|
resolve();
|
|
108
170
|
})
|
|
109
171
|
.catch(reject);
|
|
@@ -111,110 +173,102 @@ function uploadFile(sftp, local, remote) {
|
|
|
111
173
|
});
|
|
112
174
|
}
|
|
113
175
|
// ==========================
|
|
114
|
-
|
|
176
|
+
// 并发上传
|
|
177
|
+
// ==========================
|
|
178
|
+
function uploadWithConcurrency(tasks, concurrency) {
|
|
115
179
|
return __awaiter(this, void 0, void 0, function* () {
|
|
116
|
-
const
|
|
117
|
-
for (const
|
|
118
|
-
const p =
|
|
119
|
-
|
|
120
|
-
if (
|
|
121
|
-
yield Promise.race(
|
|
180
|
+
const executing = new Set();
|
|
181
|
+
for (const task of tasks) {
|
|
182
|
+
const p = task().finally(() => executing.delete(p));
|
|
183
|
+
executing.add(p);
|
|
184
|
+
if (executing.size >= concurrency) {
|
|
185
|
+
yield Promise.race(executing);
|
|
122
186
|
}
|
|
123
187
|
}
|
|
124
|
-
yield Promise.all(
|
|
188
|
+
yield Promise.all(executing);
|
|
125
189
|
});
|
|
126
190
|
}
|
|
127
191
|
// ==========================
|
|
128
|
-
|
|
192
|
+
// 递归上传目录
|
|
193
|
+
// ==========================
|
|
194
|
+
function uploadDirConcurrent(sftp, localDir, remoteDir) {
|
|
129
195
|
return __awaiter(this, void 0, void 0, function* () {
|
|
130
196
|
yield ensureRemoteDir(sftp, remoteDir);
|
|
131
|
-
const
|
|
197
|
+
const files = fs.readdirSync(localDir);
|
|
132
198
|
const tasks = [];
|
|
133
|
-
for (const
|
|
134
|
-
const local = path.join(localDir,
|
|
135
|
-
const remote = path.posix.join(remoteDir,
|
|
199
|
+
for (const file of files) {
|
|
200
|
+
const local = path.join(localDir, file);
|
|
201
|
+
const remote = path.posix.join(remoteDir, file);
|
|
136
202
|
const stat = fs.statSync(local);
|
|
137
203
|
if (stat.isDirectory()) {
|
|
138
|
-
yield
|
|
204
|
+
yield uploadDirConcurrent(sftp, local, remote);
|
|
139
205
|
}
|
|
140
206
|
else {
|
|
141
207
|
tasks.push(() => uploadFile(sftp, local, remote));
|
|
142
208
|
}
|
|
143
209
|
}
|
|
144
|
-
yield uploadWithConcurrency(tasks);
|
|
210
|
+
yield uploadWithConcurrency(tasks, CONCURRENCY);
|
|
145
211
|
});
|
|
146
212
|
}
|
|
147
213
|
// ==========================
|
|
214
|
+
// 主逻辑
|
|
215
|
+
// ==========================
|
|
148
216
|
function run() {
|
|
149
217
|
return __awaiter(this, void 0, void 0, function* () {
|
|
218
|
+
var _a;
|
|
150
219
|
const args = getArgs();
|
|
220
|
+
if (args.v || args.version) {
|
|
221
|
+
console.log(`deploy 工具 v${VERSION} 并发 ${CONCURRENCY}`);
|
|
222
|
+
return;
|
|
223
|
+
}
|
|
151
224
|
const host = args.host;
|
|
152
|
-
const
|
|
153
|
-
const
|
|
154
|
-
|
|
155
|
-
|
|
156
|
-
|
|
157
|
-
|
|
158
|
-
|
|
225
|
+
const cache = host ? getCacheByHost(host) : {};
|
|
226
|
+
const config = {
|
|
227
|
+
host: host || cache.host,
|
|
228
|
+
port: Number(args.port || cache.port) || 22,
|
|
229
|
+
user: args.user || args.username || cache.user,
|
|
230
|
+
password: args.password || cache.password,
|
|
231
|
+
localPath: args.local || args.dir,
|
|
232
|
+
remotePath: args.remote || args.serverDir || cache.remotePath,
|
|
233
|
+
backup: args.backup === 'false' ? false : ((_a = cache.backup) !== null && _a !== void 0 ? _a : true),
|
|
234
|
+
};
|
|
235
|
+
if (!config.host || !config.user || !config.localPath || !config.remotePath) {
|
|
159
236
|
console.log(`
|
|
160
|
-
|
|
161
|
-
--host=IP --
|
|
162
|
-
--
|
|
163
|
-
|
|
164
|
-
|
|
237
|
+
🚀 deploy 使用示例:
|
|
238
|
+
创建远程根目录:deploy --host=IP --username=xxx --password=xxx --dir=dir --serverDir=/server/dist --createRoot=true
|
|
239
|
+
上传 dir 内部文件到服务器:deploy --host=IP --username=xxx --password=xxx --dir=dir --serverDir=/server/dist
|
|
240
|
+
关闭备份:--backup=false
|
|
241
|
+
查看版本:--version
|
|
242
|
+
`);
|
|
165
243
|
return;
|
|
166
244
|
}
|
|
167
|
-
const
|
|
168
|
-
|
|
245
|
+
const localAbs = path.resolve(config.localPath);
|
|
246
|
+
const localName = path.basename(localAbs);
|
|
247
|
+
const createRoot = args.createRoot === 'true' || false;
|
|
248
|
+
const remoteDir = createRoot ? path.posix.join(config.remotePath, localName) : config.remotePath;
|
|
249
|
+
console.log(`本地目录: ${localAbs}`);
|
|
250
|
+
console.log(`远程目录: ${remoteDir}`);
|
|
169
251
|
const sftp = new SftpClient();
|
|
170
252
|
try {
|
|
253
|
+
console.log('🔗 连接服务器...');
|
|
171
254
|
yield sftp.connect(config);
|
|
172
|
-
console.log('✅
|
|
173
|
-
// ======================
|
|
174
|
-
// 根目录处理逻辑
|
|
175
|
-
// ======================
|
|
176
|
-
const localAbs = path.resolve(localPath);
|
|
177
|
-
const baseName = path.basename(localAbs);
|
|
178
|
-
const keepRoot = remotePath.endsWith('/');
|
|
179
|
-
const finalRemote = keepRoot
|
|
180
|
-
? path.posix.join(remotePath, baseName)
|
|
181
|
-
: remotePath;
|
|
182
|
-
console.log(keepRoot
|
|
183
|
-
? `📁 保留根目录:${baseName}`
|
|
184
|
-
: `📂 不保留根目录,仅上传内容`);
|
|
185
|
-
console.log(`🚀 ${localAbs} → ${finalRemote}`);
|
|
186
|
-
// ======================
|
|
187
|
-
// 备份
|
|
188
|
-
// ======================
|
|
189
|
-
if (backup) {
|
|
190
|
-
try {
|
|
191
|
-
yield sftp.stat(finalRemote);
|
|
192
|
-
const backupPath = finalRemote + '_bak_' + Date.now();
|
|
193
|
-
yield sftp.rename(finalRemote, backupPath);
|
|
194
|
-
console.log(`📦 已备份 → ${backupPath}`);
|
|
195
|
-
}
|
|
196
|
-
catch (_a) { }
|
|
197
|
-
}
|
|
198
|
-
// ======================
|
|
199
|
-
// 上传
|
|
200
|
-
// ======================
|
|
255
|
+
console.log('✅ 连接成功');
|
|
201
256
|
if (fs.statSync(localAbs).isDirectory()) {
|
|
202
|
-
|
|
257
|
+
console.log(`🚀 开始上传目录(并发 ${CONCURRENCY})`);
|
|
258
|
+
yield uploadDirConcurrent(sftp, localAbs, remoteDir);
|
|
203
259
|
}
|
|
204
260
|
else {
|
|
205
|
-
yield uploadFile(sftp, localAbs,
|
|
261
|
+
yield uploadFile(sftp, localAbs, remoteDir);
|
|
206
262
|
}
|
|
207
|
-
console.log('\n🎉
|
|
208
|
-
|
|
209
|
-
saveCache(host, config);
|
|
210
|
-
console.log('✅ 已缓存');
|
|
263
|
+
console.log('\n🎉 上传完成!');
|
|
264
|
+
saveCache(config);
|
|
211
265
|
}
|
|
212
|
-
catch (
|
|
213
|
-
console.error('❌
|
|
266
|
+
catch (err) {
|
|
267
|
+
console.error('❌ 错误:', err.message);
|
|
214
268
|
}
|
|
215
269
|
finally {
|
|
216
270
|
yield sftp.end();
|
|
217
|
-
console.log('🔌
|
|
271
|
+
console.log('🔌 连接已关闭');
|
|
218
272
|
}
|
|
219
273
|
});
|
|
220
274
|
}
|
package/lib/index.js.map
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"index.js","sourceRoot":"","sources":["../src/index.ts"],"names":[],"mappings":";;;;;;;;;;AACA,OAAO,EAAE,MAAM,IAAI,CAAC;AACpB,OAAO,IAAI,MAAM,MAAM,CAAC;AACxB,OAAO,EAAE,MAAM,IAAI,CAAC;AACpB,OAAO,UAAU,MAAM,kBAAkB,CAAC;AAC1C,OAAO,EAAE,aAAa,EAAE,MAAM,KAAK,CAAC;AAEpC,6BAA6B;AAC7B,MAAM,UAAU,GAAG,aAAa,CAAC,MAAM,CAAC,IAAI,CAAC,GAAG,CAAC,CAAC;AAClD,MAAM,SAAS,GAAG,IAAI,CAAC,OAAO,CAAC,UAAU,CAAC,CAAC;AAE3C,6BAA6B;AAC7B,MAAM,WAAW,GAAG,CAAC,CAAC;
|
|
1
|
+
{"version":3,"file":"index.js","sourceRoot":"","sources":["../src/index.ts"],"names":[],"mappings":"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"}
|