kirby-deploy 0.0.4 → 0.1.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/dist/cli.js +68 -35
- package/dist/index.d.ts +29 -76
- package/package.json +7 -7
- package/src/commands/languages.ts +40 -0
- package/src/commands/main.ts +7 -1
- package/src/config.ts +4 -2
- package/src/types.ts +4 -3
package/dist/cli.js
CHANGED
|
@@ -4,11 +4,11 @@
|
|
|
4
4
|
import { runMain } from "citty";
|
|
5
5
|
|
|
6
6
|
// src/commands/main.ts
|
|
7
|
-
import { defineCommand as
|
|
8
|
-
import
|
|
9
|
-
import { colors as
|
|
7
|
+
import { defineCommand as defineCommand4 } from "citty";
|
|
8
|
+
import consola9 from "consola";
|
|
9
|
+
import { colors as colors6 } from "consola/utils";
|
|
10
10
|
import { readFileSync } from "fs";
|
|
11
|
-
import { join as
|
|
11
|
+
import { join as join6, relative } from "path/posix";
|
|
12
12
|
import { cwd as cwd2 } from "process";
|
|
13
13
|
|
|
14
14
|
// src/config.ts
|
|
@@ -34,7 +34,8 @@ var FolderStructureSchema = object({
|
|
|
34
34
|
media: string(),
|
|
35
35
|
accounts: string(),
|
|
36
36
|
sessions: string(),
|
|
37
|
-
cache: string()
|
|
37
|
+
cache: string(),
|
|
38
|
+
site: string()
|
|
38
39
|
});
|
|
39
40
|
var ConfigSchema = object({
|
|
40
41
|
host: string(),
|
|
@@ -73,7 +74,8 @@ var loadConfig = async () => {
|
|
|
73
74
|
parse(ConfigSchema, config);
|
|
74
75
|
} catch (e) {
|
|
75
76
|
const issues = flatten(e).nested;
|
|
76
|
-
|
|
77
|
+
if (!issues) return null;
|
|
78
|
+
const info = Object.entries(issues).map(([key, messages = []]) => ` - ${key} (${messages.join(", ")})`).join("\n");
|
|
77
79
|
consola.error(`Invalid properties in ${configFile}
|
|
78
80
|
${info}`);
|
|
79
81
|
return null;
|
|
@@ -86,7 +88,8 @@ ${info}`);
|
|
|
86
88
|
media: "public/media",
|
|
87
89
|
accounts: "storage/accounts",
|
|
88
90
|
sessions: "storage/sessions",
|
|
89
|
-
cache: "storage/cache"
|
|
91
|
+
cache: "storage/cache",
|
|
92
|
+
site: "site"
|
|
90
93
|
};
|
|
91
94
|
} else if (config.folderStructure === "flat") {
|
|
92
95
|
folderStructure = {
|
|
@@ -94,7 +97,8 @@ ${info}`);
|
|
|
94
97
|
media: "site/media",
|
|
95
98
|
accounts: "site/accounts",
|
|
96
99
|
sessions: "site/sessions",
|
|
97
|
-
cache: "site/cache"
|
|
100
|
+
cache: "site/cache",
|
|
101
|
+
site: "site"
|
|
98
102
|
};
|
|
99
103
|
} else {
|
|
100
104
|
folderStructure = config.folderStructure;
|
|
@@ -116,8 +120,7 @@ ${info}`);
|
|
|
116
120
|
"ftp:ssl-force": true,
|
|
117
121
|
...config.lftpSettings
|
|
118
122
|
},
|
|
119
|
-
lftpFlags: ["--parallel=10", "--dereference", ...config.lftpFlags ?? []]
|
|
120
|
-
url: "fu"
|
|
123
|
+
lftpFlags: ["--parallel=10", "--dereference", ...config.lftpFlags ?? []]
|
|
121
124
|
};
|
|
122
125
|
return configResolved;
|
|
123
126
|
};
|
|
@@ -140,8 +143,7 @@ var cat = (file, { host, user, password, lftpSettings }) => {
|
|
|
140
143
|
const child = isWindows ? spawnSync("wsl", ["lftp", "-c", commands.join("; ")], {
|
|
141
144
|
encoding: "utf-8"
|
|
142
145
|
}) : spawnSync("lftp", ["-c", commands.join("; ")], { encoding: "utf-8" });
|
|
143
|
-
if (child.stderr)
|
|
144
|
-
consola2.error(child.stderr);
|
|
146
|
+
if (child.stderr) consola2.error(child.stderr);
|
|
145
147
|
return child.stdout;
|
|
146
148
|
};
|
|
147
149
|
|
|
@@ -170,8 +172,7 @@ var mirror = (source, destination, flags, { lftpSettings, host, user, password,
|
|
|
170
172
|
let hasErrors = false;
|
|
171
173
|
let hasChanges = false;
|
|
172
174
|
const handleData = (data) => {
|
|
173
|
-
if (verbose)
|
|
174
|
-
consola3.log(`${colors.bgBlue(" LFTP ")} ${data}
|
|
175
|
+
if (verbose) consola3.log(`${colors.bgBlue(" LFTP ")} ${data}
|
|
175
176
|
`);
|
|
176
177
|
data.toString().split("\n").forEach((line) => {
|
|
177
178
|
let match = null;
|
|
@@ -221,8 +222,7 @@ import * as readline from "node:readline";
|
|
|
221
222
|
var upperFirst = (string2) => string2.charAt(0).toUpperCase() + string2.slice(1);
|
|
222
223
|
var isGit = () => existsSync(join(cwd(), ".git"));
|
|
223
224
|
var getBranch = () => {
|
|
224
|
-
if (!isGit())
|
|
225
|
-
return;
|
|
225
|
+
if (!isGit()) return;
|
|
226
226
|
const { stderr, stdout } = spawnSync2("git", ["branch", "--show-current"], {
|
|
227
227
|
encoding: "utf-8"
|
|
228
228
|
});
|
|
@@ -302,8 +302,7 @@ var sync = async (source, mode, config) => {
|
|
|
302
302
|
return false;
|
|
303
303
|
}
|
|
304
304
|
const shouldContinue = await confirm(`Apply changes to ${targetName}?`);
|
|
305
|
-
if (!shouldContinue)
|
|
306
|
-
return false;
|
|
305
|
+
if (!shouldContinue) return false;
|
|
307
306
|
consola5.log("");
|
|
308
307
|
}
|
|
309
308
|
consola5.log("Apply changes...\n");
|
|
@@ -345,8 +344,7 @@ import { colors as colors3 } from "consola/utils";
|
|
|
345
344
|
import { join as join3 } from "path/posix";
|
|
346
345
|
var syncAccounts = async (mode) => {
|
|
347
346
|
const config = await loadConfig();
|
|
348
|
-
if (!config)
|
|
349
|
-
return;
|
|
347
|
+
if (!config) return;
|
|
350
348
|
const { accounts } = config.folderStructure;
|
|
351
349
|
const source = `./${accounts}/`;
|
|
352
350
|
const branch = getBranch();
|
|
@@ -382,8 +380,7 @@ import { colors as colors4 } from "consola/utils";
|
|
|
382
380
|
import { join as join4 } from "path/posix";
|
|
383
381
|
var syncContent = async (mode) => {
|
|
384
382
|
const config = await loadConfig();
|
|
385
|
-
if (!config)
|
|
386
|
-
return;
|
|
383
|
+
if (!config) return;
|
|
387
384
|
const { content } = config.folderStructure;
|
|
388
385
|
const source = `./${content}/`;
|
|
389
386
|
const branch = getBranch();
|
|
@@ -411,17 +408,50 @@ var syncContent = async (mode) => {
|
|
|
411
408
|
var contentPush = defineCommand2({ run: () => syncContent("push") });
|
|
412
409
|
var contentPull = defineCommand2({ run: () => syncContent("pull") });
|
|
413
410
|
|
|
411
|
+
// src/commands/languages.ts
|
|
412
|
+
import { defineCommand as defineCommand3 } from "citty";
|
|
413
|
+
import consola8 from "consola";
|
|
414
|
+
import { colors as colors5 } from "consola/utils";
|
|
415
|
+
import { join as join5 } from "path/posix";
|
|
416
|
+
var syncLanguages = async (mode) => {
|
|
417
|
+
const config = await loadConfig();
|
|
418
|
+
if (!config) return;
|
|
419
|
+
const { site } = config.folderStructure;
|
|
420
|
+
const source = `./${site}/languages/`;
|
|
421
|
+
const branch = getBranch();
|
|
422
|
+
const displaySource = colors5.magenta(
|
|
423
|
+
`${source}${branch ? colors5.cyan(` (${branch})`) : ""}`
|
|
424
|
+
);
|
|
425
|
+
const displayDestination = colors5.magenta(
|
|
426
|
+
join5(config.host, config.remoteDir, source)
|
|
427
|
+
);
|
|
428
|
+
const direction = mode === "pull" ? "from" : "to";
|
|
429
|
+
consola8.log(
|
|
430
|
+
`\u{1F511} ${upperFirst(mode)} ${displaySource} ${direction} ${displayDestination}
|
|
431
|
+
`
|
|
432
|
+
);
|
|
433
|
+
return sync(source, mode, {
|
|
434
|
+
...config,
|
|
435
|
+
// User provided includes/excludes can only be used in the main command
|
|
436
|
+
// because they are relative to the base directory, so we reset them.
|
|
437
|
+
exclude: [],
|
|
438
|
+
excludeGlob: [".*", ".*/"],
|
|
439
|
+
include: [],
|
|
440
|
+
includeGlob: []
|
|
441
|
+
});
|
|
442
|
+
};
|
|
443
|
+
var languagesPush = defineCommand3({ run: () => syncLanguages("push") });
|
|
444
|
+
var languagesPull = defineCommand3({ run: () => syncLanguages("pull") });
|
|
445
|
+
|
|
414
446
|
// src/commands/main.ts
|
|
415
|
-
var main =
|
|
447
|
+
var main = defineCommand4({
|
|
416
448
|
run: async ({ rawArgs, cmd }) => {
|
|
417
449
|
const [firstArg] = rawArgs;
|
|
418
450
|
const subCommands = Object.keys(cmd.subCommands ?? {});
|
|
419
451
|
const isSubCommand = subCommands.includes(firstArg);
|
|
420
|
-
if (isSubCommand)
|
|
421
|
-
return;
|
|
452
|
+
if (isSubCommand) return;
|
|
422
453
|
const config = await loadConfig();
|
|
423
|
-
if (!config)
|
|
424
|
-
return;
|
|
454
|
+
if (!config) return;
|
|
425
455
|
const { folderStructure } = config;
|
|
426
456
|
const exclude = [
|
|
427
457
|
...config.exclude,
|
|
@@ -430,17 +460,18 @@ var main = defineCommand3({
|
|
|
430
460
|
`^${relative(cwd2(), folderStructure.media)}`,
|
|
431
461
|
`^${relative(cwd2(), folderStructure.accounts)}`,
|
|
432
462
|
`^${relative(cwd2(), folderStructure.sessions)}`,
|
|
433
|
-
`^${relative(cwd2(), folderStructure.cache)}
|
|
463
|
+
`^${relative(cwd2(), folderStructure.cache)}`,
|
|
464
|
+
`^${relative(cwd2(), join6(folderStructure.site, "languages"))}`
|
|
434
465
|
];
|
|
435
466
|
const excludeGlob = [...config.excludeGlob, ".*", ".*/"];
|
|
436
467
|
const include = config.include;
|
|
437
|
-
const includeGlob = [...config.includeGlob, ".htaccess"];
|
|
468
|
+
const includeGlob = [...config.includeGlob, ".htaccess", ".vite/"];
|
|
438
469
|
const branch = getBranch();
|
|
439
|
-
const displaySource = branch ?
|
|
440
|
-
const displayDestination =
|
|
441
|
-
|
|
470
|
+
const displaySource = branch ? colors6.cyan(` ${branch} `) : " ";
|
|
471
|
+
const displayDestination = colors6.magenta(
|
|
472
|
+
join6(config.host, config.remoteDir)
|
|
442
473
|
);
|
|
443
|
-
|
|
474
|
+
consola9.log(`\u{1F680} Deploy${displaySource}to ${displayDestination}
|
|
444
475
|
`);
|
|
445
476
|
if (config.checkComposerLock) {
|
|
446
477
|
const localComposerLock = readFileSync("./composer.lock", {
|
|
@@ -450,7 +481,7 @@ var main = defineCommand3({
|
|
|
450
481
|
const skipVendor = localComposerLock === remoteComposerLock;
|
|
451
482
|
if (skipVendor) {
|
|
452
483
|
exclude.push("^vendor/", "^kirby/");
|
|
453
|
-
|
|
484
|
+
consola9.info("Skipping vendor\n");
|
|
454
485
|
}
|
|
455
486
|
}
|
|
456
487
|
await sync("./", "push", {
|
|
@@ -465,7 +496,9 @@ var main = defineCommand3({
|
|
|
465
496
|
["content-push"]: contentPush,
|
|
466
497
|
["content-pull"]: contentPull,
|
|
467
498
|
["accounts-push"]: accountsPush,
|
|
468
|
-
["accounts-pull"]: accountsPull
|
|
499
|
+
["accounts-pull"]: accountsPull,
|
|
500
|
+
["languages-push"]: languagesPush,
|
|
501
|
+
["languages-pull"]: languagesPull
|
|
469
502
|
}
|
|
470
503
|
});
|
|
471
504
|
|
package/dist/index.d.ts
CHANGED
|
@@ -1,82 +1,34 @@
|
|
|
1
1
|
import * as valibot from 'valibot';
|
|
2
|
-
import {
|
|
2
|
+
import { InferInput } from 'valibot';
|
|
3
3
|
|
|
4
4
|
declare const ConfigSchema: valibot.ObjectSchema<{
|
|
5
|
-
host: valibot.StringSchema<
|
|
6
|
-
user: valibot.StringSchema<
|
|
7
|
-
password: valibot.StringSchema<
|
|
8
|
-
url: valibot.OptionalSchema<valibot.StringSchema<
|
|
9
|
-
token: valibot.OptionalSchema<valibot.StringSchema<
|
|
10
|
-
remoteDir: valibot.OptionalSchema<valibot.StringSchema<
|
|
11
|
-
folderStructure: valibot.OptionalSchema<valibot.UnionSchema<
|
|
12
|
-
content: valibot.StringSchema<
|
|
13
|
-
media: valibot.StringSchema<
|
|
14
|
-
accounts: valibot.StringSchema<
|
|
15
|
-
sessions: valibot.StringSchema<
|
|
16
|
-
cache: valibot.StringSchema<
|
|
17
|
-
|
|
18
|
-
|
|
19
|
-
|
|
20
|
-
|
|
21
|
-
|
|
22
|
-
|
|
23
|
-
|
|
24
|
-
|
|
25
|
-
|
|
26
|
-
|
|
27
|
-
|
|
28
|
-
|
|
29
|
-
|
|
30
|
-
|
|
31
|
-
|
|
32
|
-
accounts: string;
|
|
33
|
-
sessions: string;
|
|
34
|
-
cache: string;
|
|
35
|
-
} | undefined>;
|
|
36
|
-
checkComposerLock: valibot.OptionalSchema<valibot.BooleanSchema<boolean>, undefined, boolean | undefined>;
|
|
37
|
-
callWebhooks: valibot.OptionalSchema<valibot.BooleanSchema<boolean>, undefined, boolean | undefined>;
|
|
38
|
-
dryRun: valibot.OptionalSchema<valibot.BooleanSchema<boolean>, undefined, boolean | undefined>;
|
|
39
|
-
verbose: valibot.OptionalSchema<valibot.BooleanSchema<boolean>, undefined, boolean | undefined>;
|
|
40
|
-
parallel: valibot.OptionalSchema<valibot.NumberSchema<number>, undefined, number | undefined>;
|
|
41
|
-
exclude: valibot.OptionalSchema<valibot.ArraySchema<valibot.StringSchema<string>, string[]>, undefined, string[] | undefined>;
|
|
42
|
-
excludeGlob: valibot.OptionalSchema<valibot.ArraySchema<valibot.StringSchema<string>, string[]>, undefined, string[] | undefined>;
|
|
43
|
-
include: valibot.OptionalSchema<valibot.ArraySchema<valibot.StringSchema<string>, string[]>, undefined, string[] | undefined>;
|
|
44
|
-
includeGlob: valibot.OptionalSchema<valibot.ArraySchema<valibot.StringSchema<string>, string[]>, undefined, string[] | undefined>;
|
|
45
|
-
lftpSettings: valibot.OptionalSchema<valibot.RecordSchema<valibot.StringSchema<string>, valibot.AnySchema<any>, {
|
|
46
|
-
[x: string]: any;
|
|
47
|
-
}>, undefined, {
|
|
48
|
-
[x: string]: any;
|
|
49
|
-
} | undefined>;
|
|
50
|
-
lftpFlags: valibot.OptionalSchema<valibot.ArraySchema<valibot.StringSchema<string>, string[]>, undefined, string[] | undefined>;
|
|
51
|
-
}, undefined, {
|
|
52
|
-
host: string;
|
|
53
|
-
user: string;
|
|
54
|
-
password: string;
|
|
55
|
-
url?: string | undefined;
|
|
56
|
-
token?: string | undefined;
|
|
57
|
-
remoteDir?: string | undefined;
|
|
58
|
-
folderStructure?: "flat" | "public" | {
|
|
59
|
-
content: string;
|
|
60
|
-
media: string;
|
|
61
|
-
accounts: string;
|
|
62
|
-
sessions: string;
|
|
63
|
-
cache: string;
|
|
64
|
-
} | undefined;
|
|
65
|
-
checkComposerLock?: boolean | undefined;
|
|
66
|
-
callWebhooks?: boolean | undefined;
|
|
67
|
-
dryRun?: boolean | undefined;
|
|
68
|
-
verbose?: boolean | undefined;
|
|
69
|
-
parallel?: number | undefined;
|
|
70
|
-
exclude?: string[] | undefined;
|
|
71
|
-
excludeGlob?: string[] | undefined;
|
|
72
|
-
include?: string[] | undefined;
|
|
73
|
-
includeGlob?: string[] | undefined;
|
|
74
|
-
lftpSettings?: {
|
|
75
|
-
[x: string]: any;
|
|
76
|
-
} | undefined;
|
|
77
|
-
lftpFlags?: string[] | undefined;
|
|
78
|
-
}>;
|
|
79
|
-
type Config = Output<typeof ConfigSchema>;
|
|
5
|
+
readonly host: valibot.StringSchema<undefined>;
|
|
6
|
+
readonly user: valibot.StringSchema<undefined>;
|
|
7
|
+
readonly password: valibot.StringSchema<undefined>;
|
|
8
|
+
readonly url: valibot.OptionalSchema<valibot.StringSchema<undefined>, never>;
|
|
9
|
+
readonly token: valibot.OptionalSchema<valibot.StringSchema<undefined>, never>;
|
|
10
|
+
readonly remoteDir: valibot.OptionalSchema<valibot.StringSchema<undefined>, never>;
|
|
11
|
+
readonly folderStructure: valibot.OptionalSchema<valibot.UnionSchema<[valibot.LiteralSchema<"flat", undefined>, valibot.LiteralSchema<"public", undefined>, valibot.ObjectSchema<{
|
|
12
|
+
readonly content: valibot.StringSchema<undefined>;
|
|
13
|
+
readonly media: valibot.StringSchema<undefined>;
|
|
14
|
+
readonly accounts: valibot.StringSchema<undefined>;
|
|
15
|
+
readonly sessions: valibot.StringSchema<undefined>;
|
|
16
|
+
readonly cache: valibot.StringSchema<undefined>;
|
|
17
|
+
readonly site: valibot.StringSchema<undefined>;
|
|
18
|
+
}, undefined>], undefined>, never>;
|
|
19
|
+
readonly checkComposerLock: valibot.OptionalSchema<valibot.BooleanSchema<undefined>, never>;
|
|
20
|
+
readonly callWebhooks: valibot.OptionalSchema<valibot.BooleanSchema<undefined>, never>;
|
|
21
|
+
readonly dryRun: valibot.OptionalSchema<valibot.BooleanSchema<undefined>, never>;
|
|
22
|
+
readonly verbose: valibot.OptionalSchema<valibot.BooleanSchema<undefined>, never>;
|
|
23
|
+
readonly parallel: valibot.OptionalSchema<valibot.NumberSchema<undefined>, never>;
|
|
24
|
+
readonly exclude: valibot.OptionalSchema<valibot.ArraySchema<valibot.StringSchema<undefined>, undefined>, never>;
|
|
25
|
+
readonly excludeGlob: valibot.OptionalSchema<valibot.ArraySchema<valibot.StringSchema<undefined>, undefined>, never>;
|
|
26
|
+
readonly include: valibot.OptionalSchema<valibot.ArraySchema<valibot.StringSchema<undefined>, undefined>, never>;
|
|
27
|
+
readonly includeGlob: valibot.OptionalSchema<valibot.ArraySchema<valibot.StringSchema<undefined>, undefined>, never>;
|
|
28
|
+
readonly lftpSettings: valibot.OptionalSchema<valibot.RecordSchema<valibot.StringSchema<undefined>, valibot.AnySchema, undefined>, never>;
|
|
29
|
+
readonly lftpFlags: valibot.OptionalSchema<valibot.ArraySchema<valibot.StringSchema<undefined>, undefined>, never>;
|
|
30
|
+
}, undefined>;
|
|
31
|
+
type Config = InferInput<typeof ConfigSchema>;
|
|
80
32
|
|
|
81
33
|
declare const defineConfig: (config: Config) => {
|
|
82
34
|
host: string;
|
|
@@ -91,6 +43,7 @@ declare const defineConfig: (config: Config) => {
|
|
|
91
43
|
accounts: string;
|
|
92
44
|
sessions: string;
|
|
93
45
|
cache: string;
|
|
46
|
+
site: string;
|
|
94
47
|
} | undefined;
|
|
95
48
|
checkComposerLock?: boolean | undefined;
|
|
96
49
|
callWebhooks?: boolean | undefined;
|
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "kirby-deploy",
|
|
3
|
-
"version": "0.0
|
|
3
|
+
"version": "0.1.0",
|
|
4
4
|
"main": "./dist/index.js",
|
|
5
5
|
"type": "module",
|
|
6
6
|
"bin": {
|
|
@@ -11,16 +11,16 @@
|
|
|
11
11
|
"license": "MIT",
|
|
12
12
|
"devDependencies": {
|
|
13
13
|
"@prettier/plugin-php": "^0.22.2",
|
|
14
|
-
"@types/node": "^20.
|
|
15
|
-
"prettier": "^3.
|
|
16
|
-
"tsup": "^8.0
|
|
17
|
-
"typescript": "^5.
|
|
14
|
+
"@types/node": "^20.16.10",
|
|
15
|
+
"prettier": "^3.3.3",
|
|
16
|
+
"tsup": "^8.3.0",
|
|
17
|
+
"typescript": "^5.6.2"
|
|
18
18
|
},
|
|
19
19
|
"dependencies": {
|
|
20
|
-
"c12": "^
|
|
20
|
+
"c12": "^2.0.0",
|
|
21
21
|
"citty": "^0.1.6",
|
|
22
22
|
"consola": "^3.2.3",
|
|
23
|
-
"valibot": "^0.
|
|
23
|
+
"valibot": "^0.42.1"
|
|
24
24
|
},
|
|
25
25
|
"scripts": {
|
|
26
26
|
"build": "tsup src/index.ts src/cli.ts --format esm --dts",
|
|
@@ -0,0 +1,40 @@
|
|
|
1
|
+
import { defineCommand } from 'citty'
|
|
2
|
+
import consola from 'consola'
|
|
3
|
+
import { colors } from 'consola/utils'
|
|
4
|
+
import { join } from 'path/posix'
|
|
5
|
+
import { loadConfig } from '../config'
|
|
6
|
+
import { sync } from '../sync'
|
|
7
|
+
import { getBranch, upperFirst } from '../utils'
|
|
8
|
+
|
|
9
|
+
const syncLanguages = async (mode: 'pull' | 'push') => {
|
|
10
|
+
const config = await loadConfig()
|
|
11
|
+
if (!config) return
|
|
12
|
+
|
|
13
|
+
const { site } = config.folderStructure
|
|
14
|
+
const source = `./${site}/languages/`
|
|
15
|
+
|
|
16
|
+
const branch = getBranch()
|
|
17
|
+
const displaySource = colors.magenta(
|
|
18
|
+
`${source}${branch ? colors.cyan(` (${branch})`) : ''}`,
|
|
19
|
+
)
|
|
20
|
+
const displayDestination = colors.magenta(
|
|
21
|
+
join(config.host, config.remoteDir, source),
|
|
22
|
+
)
|
|
23
|
+
const direction = mode === 'pull' ? 'from' : 'to'
|
|
24
|
+
consola.log(
|
|
25
|
+
`🔑 ${upperFirst(mode)} ${displaySource} ${direction} ${displayDestination}\n`,
|
|
26
|
+
)
|
|
27
|
+
|
|
28
|
+
return sync(source, mode, {
|
|
29
|
+
...config,
|
|
30
|
+
// User provided includes/excludes can only be used in the main command
|
|
31
|
+
// because they are relative to the base directory, so we reset them.
|
|
32
|
+
exclude: [],
|
|
33
|
+
excludeGlob: ['.*', '.*/'],
|
|
34
|
+
include: [],
|
|
35
|
+
includeGlob: [],
|
|
36
|
+
})
|
|
37
|
+
}
|
|
38
|
+
|
|
39
|
+
export const languagesPush = defineCommand({ run: () => syncLanguages('push') })
|
|
40
|
+
export const languagesPull = defineCommand({ run: () => syncLanguages('pull') })
|
package/src/commands/main.ts
CHANGED
|
@@ -10,6 +10,7 @@ import { sync } from '../sync'
|
|
|
10
10
|
import { getBranch } from '../utils'
|
|
11
11
|
import { accountsPull, accountsPush } from './accounts'
|
|
12
12
|
import { contentPull, contentPush } from './content'
|
|
13
|
+
import { languagesPull, languagesPush } from './languages'
|
|
13
14
|
|
|
14
15
|
export const main = defineCommand({
|
|
15
16
|
run: async ({ rawArgs, cmd }) => {
|
|
@@ -32,10 +33,11 @@ export const main = defineCommand({
|
|
|
32
33
|
`^${relative(cwd(), folderStructure.accounts)}`,
|
|
33
34
|
`^${relative(cwd(), folderStructure.sessions)}`,
|
|
34
35
|
`^${relative(cwd(), folderStructure.cache)}`,
|
|
36
|
+
`^${relative(cwd(), join(folderStructure.site, 'languages'))}`,
|
|
35
37
|
]
|
|
36
38
|
const excludeGlob = [...config.excludeGlob, '.*', '.*/']
|
|
37
39
|
const include = config.include
|
|
38
|
-
const includeGlob = [...config.includeGlob, '.htaccess']
|
|
40
|
+
const includeGlob = [...config.includeGlob, '.htaccess', '.vite/']
|
|
39
41
|
|
|
40
42
|
const branch = getBranch()
|
|
41
43
|
const displaySource = branch ? colors.cyan(` ${branch} `) : ' '
|
|
@@ -67,7 +69,11 @@ export const main = defineCommand({
|
|
|
67
69
|
subCommands: {
|
|
68
70
|
['content-push']: contentPush,
|
|
69
71
|
['content-pull']: contentPull,
|
|
72
|
+
|
|
70
73
|
['accounts-push']: accountsPush,
|
|
71
74
|
['accounts-pull']: accountsPull,
|
|
75
|
+
|
|
76
|
+
['languages-push']: languagesPush,
|
|
77
|
+
['languages-pull']: languagesPull,
|
|
72
78
|
},
|
|
73
79
|
})
|
package/src/config.ts
CHANGED
|
@@ -19,8 +19,9 @@ export const loadConfig = async (): Promise<ConfigResolved | null> => {
|
|
|
19
19
|
parse(ConfigSchema, config)
|
|
20
20
|
} catch (e: any) {
|
|
21
21
|
const issues = flatten<typeof ConfigSchema>(e).nested
|
|
22
|
+
if (!issues) return null
|
|
22
23
|
const info = Object.entries(issues)
|
|
23
|
-
.map(([key, messages]) => ` - ${key} (${messages.join(', ')})`)
|
|
24
|
+
.map(([key, messages = []]) => ` - ${key} (${messages.join(', ')})`)
|
|
24
25
|
.join('\n')
|
|
25
26
|
consola.error(`Invalid properties in ${configFile}\n${info}`)
|
|
26
27
|
return null
|
|
@@ -37,6 +38,7 @@ export const loadConfig = async (): Promise<ConfigResolved | null> => {
|
|
|
37
38
|
accounts: 'storage/accounts',
|
|
38
39
|
sessions: 'storage/sessions',
|
|
39
40
|
cache: 'storage/cache',
|
|
41
|
+
site: 'site',
|
|
40
42
|
}
|
|
41
43
|
} else if (config.folderStructure === 'flat') {
|
|
42
44
|
// 'flat' structure is the default.
|
|
@@ -46,6 +48,7 @@ export const loadConfig = async (): Promise<ConfigResolved | null> => {
|
|
|
46
48
|
accounts: 'site/accounts',
|
|
47
49
|
sessions: 'site/sessions',
|
|
48
50
|
cache: 'site/cache',
|
|
51
|
+
site: 'site',
|
|
49
52
|
}
|
|
50
53
|
} else {
|
|
51
54
|
folderStructure = config.folderStructure
|
|
@@ -69,7 +72,6 @@ export const loadConfig = async (): Promise<ConfigResolved | null> => {
|
|
|
69
72
|
...config.lftpSettings,
|
|
70
73
|
},
|
|
71
74
|
lftpFlags: ['--parallel=10', '--dereference', ...(config.lftpFlags ?? [])],
|
|
72
|
-
url: 'fu',
|
|
73
75
|
} satisfies ConfigResolved
|
|
74
76
|
|
|
75
77
|
return configResolved
|
package/src/types.ts
CHANGED
|
@@ -1,8 +1,8 @@
|
|
|
1
1
|
import {
|
|
2
|
-
Output,
|
|
3
2
|
any,
|
|
4
3
|
array,
|
|
5
4
|
boolean,
|
|
5
|
+
InferInput,
|
|
6
6
|
literal,
|
|
7
7
|
number,
|
|
8
8
|
object,
|
|
@@ -18,9 +18,10 @@ export const FolderStructureSchema = object({
|
|
|
18
18
|
accounts: string(),
|
|
19
19
|
sessions: string(),
|
|
20
20
|
cache: string(),
|
|
21
|
+
site: string(),
|
|
21
22
|
})
|
|
22
23
|
|
|
23
|
-
export type FolderStructure =
|
|
24
|
+
export type FolderStructure = InferInput<typeof FolderStructureSchema>
|
|
24
25
|
|
|
25
26
|
export const ConfigSchema = object({
|
|
26
27
|
host: string(),
|
|
@@ -45,7 +46,7 @@ export const ConfigSchema = object({
|
|
|
45
46
|
lftpFlags: optional(array(string())),
|
|
46
47
|
})
|
|
47
48
|
|
|
48
|
-
export type Config =
|
|
49
|
+
export type Config = InferInput<typeof ConfigSchema>
|
|
49
50
|
|
|
50
51
|
type ConfigWithDefaults = Pick<Config, 'url' | 'token'> &
|
|
51
52
|
Required<Omit<Config, 'url' | 'token'>>
|