@datatruck/cli 0.17.2 → 0.19.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.
Files changed (55) hide show
  1. package/Action/BackupAction.js +4 -2
  2. package/Action/BackupSessionsAction.js +2 -0
  3. package/Action/CleanCacheAction.js +1 -0
  4. package/Action/ConfigAction.js +1 -0
  5. package/Action/InitAction.js +2 -0
  6. package/Action/PruneAction.js +2 -0
  7. package/Action/RestoreAction.js +4 -2
  8. package/Action/RestoreSessionsAction.js +2 -0
  9. package/Action/SnapshotsAction.js +2 -0
  10. package/Command/CommandAbstract.js +2 -0
  11. package/Entity/BackupSessionEntity.js +5 -2
  12. package/Entity/BackupSessionRepositoryEntity.js +5 -2
  13. package/Entity/BackupSessionTaskEntity.js +4 -2
  14. package/Entity/CrudEntityAbstract.js +3 -0
  15. package/Entity/RestoreSessionEntity.js +4 -2
  16. package/Entity/RestoreSessionRepositoryEntity.js +5 -2
  17. package/Entity/RestoreSessionTaskEntity.js +4 -2
  18. package/Entity/StateEntityAbstract.js +5 -0
  19. package/Factory/CommandFactory.js +1 -1
  20. package/JsonSchema/DefinitionEnum.js +1 -1
  21. package/Repository/DatatruckRepository.d.ts +8 -14
  22. package/Repository/DatatruckRepository.js +115 -298
  23. package/Repository/GitRepository.js +1 -1
  24. package/Repository/RepositoryAbstract.js +4 -2
  25. package/Repository/ResticRepository.js +2 -1
  26. package/SessionDriver/ConsoleSessionDriver.js +9 -5
  27. package/SessionDriver/SessionDriverAbstract.js +3 -2
  28. package/SessionDriver/SqliteSessionDriver.js +2 -4
  29. package/SessionManager/BackupSessionManager.js +3 -6
  30. package/SessionManager/RestoreSessionManager.js +3 -6
  31. package/SessionManager/SessionManagerAbstract.js +4 -0
  32. package/Task/GitTask.js +1 -0
  33. package/Task/MariadbTask.d.ts +11 -0
  34. package/Task/MariadbTask.js +234 -51
  35. package/Task/MssqlTask.js +2 -1
  36. package/Task/ScriptTask.js +1 -0
  37. package/Task/SqlDumpTaskAbstract.js +1 -0
  38. package/Task/TaskAbstract.js +2 -1
  39. package/config.schema.json +67 -37
  40. package/index.d.ts +1 -0
  41. package/index.js +1 -0
  42. package/package.json +10 -9
  43. package/utils/DataFormat.js +1 -0
  44. package/utils/Git.js +1 -0
  45. package/utils/ObjectVault.js +3 -5
  46. package/utils/Restic.js +1 -0
  47. package/utils/datatruck/config.d.ts +1 -1
  48. package/utils/fs.d.ts +17 -2
  49. package/utils/fs.js +58 -7
  50. package/utils/process.d.ts +55 -3
  51. package/utils/process.js +159 -19
  52. package/utils/tar.d.ts +32 -0
  53. package/utils/tar.js +92 -0
  54. package/utils/zip.d.ts +0 -97
  55. package/utils/zip.js +0 -238
@@ -11,6 +11,17 @@ export type MariadbTaskConfigType = {
11
11
  excludeTables?: string[];
12
12
  includeDatabases?: string[];
13
13
  excludeDatabases?: string[];
14
+ /**
15
+ * @default "auto"
16
+ */
17
+ parallel?: number | "auto";
18
+ compress?: {
19
+ command: string;
20
+ args?: string[];
21
+ } | {
22
+ type: "gzip" | "pigz";
23
+ args?: string[];
24
+ };
14
25
  };
15
26
  export declare const mariadbTaskName = "mariadb";
16
27
  export declare const mariadbTaskDefinition: JSONSchema7;
@@ -6,11 +6,13 @@ const cli_1 = require("../utils/cli");
6
6
  const fs_1 = require("../utils/fs");
7
7
  const math_1 = require("../utils/math");
8
8
  const process_1 = require("../utils/process");
9
+ const tar_1 = require("../utils/tar");
9
10
  const TaskAbstract_1 = require("./TaskAbstract");
10
11
  const assert_1 = require("assert");
12
+ const fs_2 = require("fs");
11
13
  const promises_1 = require("fs/promises");
14
+ const os_1 = require("os");
12
15
  const path_1 = require("path");
13
- const posix_1 = require("path/posix");
14
16
  exports.mariadbTaskName = "mariadb";
15
17
  exports.mariadbTaskDefinition = {
16
18
  type: "object",
@@ -39,9 +41,67 @@ exports.mariadbTaskDefinition = {
39
41
  excludeTables: (0, DefinitionEnum_1.makeRef)(DefinitionEnum_1.DefinitionEnum.stringListUtil),
40
42
  includeDatabases: (0, DefinitionEnum_1.makeRef)(DefinitionEnum_1.DefinitionEnum.stringListUtil),
41
43
  excludeDatabases: (0, DefinitionEnum_1.makeRef)(DefinitionEnum_1.DefinitionEnum.stringListUtil),
44
+ parallel: {
45
+ anyOf: [{ type: "integer", minimum: 1 }, { enum: ["auto"] }],
46
+ },
47
+ compress: {
48
+ anyOf: [
49
+ {
50
+ type: "object",
51
+ additionalProperties: false,
52
+ properties: {
53
+ command: { type: "string" },
54
+ args: (0, DefinitionEnum_1.makeRef)(DefinitionEnum_1.DefinitionEnum.stringListUtil),
55
+ },
56
+ },
57
+ {
58
+ type: "object",
59
+ additionalProperties: false,
60
+ properties: {
61
+ type: { enum: ["gzip", "pigz"] },
62
+ args: (0, DefinitionEnum_1.makeRef)(DefinitionEnum_1.DefinitionEnum.stringListUtil),
63
+ },
64
+ },
65
+ ],
66
+ },
42
67
  },
43
68
  };
69
+ function normalizeConfig(input) {
70
+ let parallel = input.parallel ?? "auto";
71
+ let cores = (0, os_1.cpus)().length;
72
+ if (parallel === "auto") {
73
+ parallel = input.compress ? Math.round(cores / 2) : cores;
74
+ cores = Math.max(1, cores - parallel);
75
+ }
76
+ let compress;
77
+ if (input.compress && "type" in input.compress) {
78
+ if (input.compress.type === "pigz") {
79
+ compress = { command: "pigz", args: [] };
80
+ if (!input.compress.args?.includes("-p")) {
81
+ compress.args.push("-p", cores.toString());
82
+ }
83
+ }
84
+ else if (input.compress.type === "gzip") {
85
+ compress = { command: "gzip" };
86
+ }
87
+ }
88
+ else {
89
+ compress = input.compress;
90
+ }
91
+ return { parallel, compress };
92
+ }
93
+ const parseLineRegex = /^(?:\[(?<step>\d+)\] )?(?<dateTime>\d{4}-\d{2}-\d{2} \d{2}:\d{2}:\d{2})?\s+(?<text>.+)\s*$/;
94
+ function parseLine(line) {
95
+ const result = parseLineRegex.exec(line);
96
+ if (result) {
97
+ return result.groups;
98
+ }
99
+ else {
100
+ return { text: line };
101
+ }
102
+ }
44
103
  class MariadbTask extends TaskAbstract_1.TaskAbstract {
104
+ verbose;
45
105
  get command() {
46
106
  return this.config.command ?? "mariabackup";
47
107
  }
@@ -58,18 +118,25 @@ class MariadbTask extends TaskAbstract_1.TaskAbstract {
58
118
  const targetPath = data.targetPath;
59
119
  (0, assert_1.ok)(typeof sourcePath === "string");
60
120
  (0, assert_1.ok)(typeof targetPath === "string");
121
+ const { parallel, compress } = normalizeConfig(config);
61
122
  const args = [
62
123
  `--backup`,
63
124
  `--datadir=${sourcePath}`,
64
- `--target-dir=${targetPath}`,
65
125
  `--host=${config.hostname}`,
66
126
  `--user=${config.username}`,
127
+ `--parallel=${parallel}`,
67
128
  `--password=${typeof config.password === "string"
68
129
  ? config.password
69
130
  : config.password
70
131
  ? (await (0, promises_1.readFile)(config.password.path)).toString()
71
132
  : ""}`,
72
133
  ];
134
+ if (compress) {
135
+ args.push(`--stream=xbstream`);
136
+ }
137
+ else {
138
+ args.push(`--target-dir=${targetPath}`);
139
+ }
73
140
  if (config.includeDatabases)
74
141
  args.push(`--databases=${config.includeDatabases.join(" ")}`);
75
142
  if (config.excludeDatabases)
@@ -83,34 +150,23 @@ class MariadbTask extends TaskAbstract_1.TaskAbstract {
83
150
  await (0, fs_1.forEachFile)(sourcePath, () => {
84
151
  total++;
85
152
  });
86
- let childProcess;
87
- const onData = async (strLines) => {
88
- const paths = [];
89
- const pathRegex = /\[\d{1,}\] \d{4}-\d{2}-\d{2} \d{2}:\d{2}:\d{2} Copying (.+) to/;
90
- const lines = strLines.split(/\r?\n/);
91
- let fatalError = false;
92
- for (const line of lines) {
93
- if (line.includes("[ERROR] InnoDB: Unsupported redo log format.") ||
94
- line.includes("Error: cannot read redo log header")) {
95
- fatalError = true;
96
- }
97
- else {
98
- const matches = pathRegex.exec(line);
99
- if (matches) {
100
- current++;
101
- paths.push(matches[1]);
102
- }
103
- }
104
- }
105
- if (fatalError) {
106
- childProcess.kill();
153
+ let p1;
154
+ let lastLineText;
155
+ const pathRegex = /((Copying|Streaming) .+) to/;
156
+ const onData = async (line) => {
157
+ const { text } = parseLine(line);
158
+ lastLineText = text;
159
+ if (line.includes("[ERROR] InnoDB: Unsupported redo log format.") ||
160
+ line.includes("Error: cannot read redo log header")) {
161
+ p1.kill();
107
162
  }
108
- else if (paths.length) {
109
- const path = (0, posix_1.normalize)(paths[0]);
163
+ else {
164
+ const matches = pathRegex.exec(text);
165
+ if (matches)
166
+ current++;
110
167
  await data.onProgress({
111
168
  relative: {
112
- description: "Copying file",
113
- payload: path,
169
+ payload: matches ? matches[1] : text,
114
170
  },
115
171
  absolute: {
116
172
  current,
@@ -120,36 +176,163 @@ class MariadbTask extends TaskAbstract_1.TaskAbstract {
120
176
  });
121
177
  }
122
178
  };
123
- await (0, process_1.exec)(command, args, undefined, {
124
- log: this.verbose,
125
- onSpawn: (p) => {
126
- childProcess = p;
127
- },
128
- stdout: {
129
- onData,
130
- },
131
- stderr: {
132
- onData,
133
- },
134
- });
135
- await (0, process_1.exec)(command, [`--prepare`, `--target-dir=${targetPath}`], undefined, {
136
- log: this.verbose,
137
- stderr: { onData: () => { } },
138
- });
179
+ const stats = { xbFiles: total };
180
+ await (0, promises_1.writeFile)((0, path_1.join)(targetPath, "stats.dtt.json"), JSON.stringify(stats));
181
+ if (compress) {
182
+ const p0 = (0, fs_2.createWriteStream)((0, path_1.join)(targetPath, "db.xb.gz"));
183
+ p1 = (0, process_1.createProcess)(command, args, {
184
+ $log: {
185
+ exec: this.verbose,
186
+ stderr: this.verbose,
187
+ },
188
+ $stderr: {
189
+ parseLines: true,
190
+ onData,
191
+ },
192
+ $onExitCode: (code) => `Exit code: ${code} - ${lastLineText}`,
193
+ });
194
+ const p2 = (0, process_1.createProcess)(compress.command, compress.args);
195
+ p1.stdout.pipe(p2.stdin, { end: true });
196
+ p2.stdout.pipe(p0, { end: true });
197
+ await Promise.all([p1, p2, (0, fs_1.waitForClose)(p0)]);
198
+ }
199
+ else {
200
+ p1 = (0, process_1.createProcess)(command, args, {
201
+ $log: this.verbose,
202
+ $stdout: {
203
+ parseLines: true,
204
+ onData,
205
+ },
206
+ $stderr: {
207
+ parseLines: true,
208
+ onData,
209
+ },
210
+ $onExitCode: (code) => `Exit code: ${code} - ${lastLineText}`,
211
+ });
212
+ await p1;
213
+ await (0, process_1.exec)(command, [`--prepare`, `--target-dir=${targetPath}`], undefined, {
214
+ log: this.verbose,
215
+ stderr: { onData: () => { } },
216
+ });
217
+ }
139
218
  }
140
219
  async onRestore(data) {
141
220
  this.verbose = data.options.verbose;
142
221
  const restorePath = data.package.restorePath;
143
222
  (0, assert_1.ok)(typeof restorePath === "string");
144
223
  await (0, fs_1.mkdirIfNotExists)(restorePath);
145
- const files = await (0, fs_1.readDir)(restorePath);
146
- for (const file of files) {
147
- if (file.startsWith("ib_logfile")) {
148
- const filePath = (0, path_1.join)(restorePath, file);
149
- if (this.verbose)
150
- (0, cli_1.logExec)("rm", [filePath]);
151
- await (0, promises_1.rm)(filePath);
152
- }
224
+ const removeFiles = [];
225
+ let files = [];
226
+ const reloadFiles = async (data = {}) => {
227
+ if (data.removeFile)
228
+ removeFiles.push(data.removeFile);
229
+ return (files = (await (0, fs_1.readDir)(restorePath)).filter((v) => !removeFiles.includes(v)));
230
+ };
231
+ await reloadFiles();
232
+ const absolute = {
233
+ format: "amount",
234
+ total: 3,
235
+ current: 0,
236
+ description: undefined,
237
+ payload: undefined,
238
+ percent: undefined,
239
+ };
240
+ // Stats
241
+ const statsFile = files.find((file) => file === "stats.dtt.json");
242
+ let stats;
243
+ if (statsFile) {
244
+ const statsFilePath = (0, path_1.join)(restorePath, statsFile);
245
+ const statsBuffer = await (0, promises_1.readFile)(statsFilePath);
246
+ stats = JSON.parse(statsBuffer.toString());
247
+ await reloadFiles({ removeFile: statsFile });
248
+ }
249
+ const zipFile = files.find((file) => file.endsWith(".gz"));
250
+ absolute.current++;
251
+ absolute.percent = (0, math_1.progressPercent)(absolute.total, absolute.current);
252
+ // Extract
253
+ if (files.length === 1 && zipFile) {
254
+ absolute.description = "Extracting";
255
+ absolute.payload = zipFile;
256
+ await data.onProgress({
257
+ absolute,
258
+ });
259
+ await (0, tar_1.extractTar)({
260
+ input: (0, path_1.join)(restorePath, zipFile),
261
+ output: restorePath,
262
+ verbose: this.verbose,
263
+ async onEntry(item) {
264
+ await data.onProgress({
265
+ absolute,
266
+ relative: {
267
+ payload: item.path,
268
+ format: "amount",
269
+ percent: item.progress.percent,
270
+ },
271
+ });
272
+ },
273
+ });
274
+ await reloadFiles({ removeFile: zipFile });
275
+ }
276
+ // Extract stream
277
+ const xbFile = files.find((file) => file.endsWith(".xb"));
278
+ absolute.current++;
279
+ absolute.percent = (0, math_1.progressPercent)(absolute.total, absolute.current);
280
+ if (files.length === 1 && xbFile) {
281
+ const xbFilePath = (0, path_1.join)(restorePath, xbFile);
282
+ const xbStream = (0, fs_2.createReadStream)(xbFilePath);
283
+ removeFiles.push(xbFile);
284
+ absolute.description = "Extracting stream";
285
+ absolute.payload = xbFile;
286
+ await data.onProgress({
287
+ absolute,
288
+ });
289
+ let currentXbFiles = 0;
290
+ const { parallel } = normalizeConfig({ parallel: this.config.parallel });
291
+ const p1 = (0, process_1.createProcess)("mbstream", ["-x", "-C", restorePath, "-v", "-p", parallel], {
292
+ $log: this.verbose,
293
+ $stderr: {
294
+ parseLines: true,
295
+ async onData(line) {
296
+ const { text: path } = parseLine(line);
297
+ await data.onProgress({
298
+ absolute,
299
+ relative: {
300
+ payload: path,
301
+ format: "amount",
302
+ current: ++currentXbFiles,
303
+ total: stats?.xbFiles,
304
+ percent: stats?.xbFiles
305
+ ? (0, math_1.progressPercent)(stats.xbFiles, currentXbFiles)
306
+ : undefined,
307
+ },
308
+ });
309
+ },
310
+ },
311
+ });
312
+ xbStream.pipe(p1.stdin, { end: true });
313
+ await Promise.all([(0, fs_1.waitForClose)(xbStream), p1]);
314
+ }
315
+ // Prepare
316
+ absolute.current++;
317
+ absolute.percent = (0, math_1.progressPercent)(absolute.total, absolute.current);
318
+ if (files.length === 1 && xbFile) {
319
+ absolute.description = "Preparing";
320
+ await data.onProgress({
321
+ absolute,
322
+ });
323
+ await (0, process_1.exec)(this.command, [`--prepare`, `--target-dir=${restorePath}`], undefined, {
324
+ log: this.verbose,
325
+ stderr: { onData: () => { } },
326
+ });
327
+ }
328
+ await reloadFiles();
329
+ removeFiles.push(...files.filter((file) => file.startsWith("ib_logfile")));
330
+ // Remove files
331
+ for (const file of removeFiles) {
332
+ const filePath = (0, path_1.join)(restorePath, file);
333
+ if (this.verbose)
334
+ (0, cli_1.logExec)("rm", [filePath]);
335
+ await (0, promises_1.rm)(filePath);
153
336
  }
154
337
  }
155
338
  }
package/Task/MssqlTask.js CHANGED
@@ -25,6 +25,8 @@ exports.mssqlTaskDefinition = {
25
25
  },
26
26
  };
27
27
  class MssqlTask extends TaskAbstract_1.TaskAbstract {
28
+ static SUFFIX = ".BAK";
29
+ verbose;
28
30
  get command() {
29
31
  return this.config.command ?? "sqlcmd";
30
32
  }
@@ -106,4 +108,3 @@ class MssqlTask extends TaskAbstract_1.TaskAbstract {
106
108
  }
107
109
  }
108
110
  exports.MssqlTask = MssqlTask;
109
- MssqlTask.SUFFIX = ".BAK";
@@ -92,6 +92,7 @@ exports.scriptTaskDefinition = {
92
92
  },
93
93
  };
94
94
  class ScriptTask extends TaskAbstract_1.TaskAbstract {
95
+ verbose;
95
96
  async onBeforeBackup() {
96
97
  return {
97
98
  targetPath: await this.mkTmpDir(ScriptTask.name),
@@ -85,6 +85,7 @@ function parseSqlFile(fileName) {
85
85
  }
86
86
  }
87
87
  class SqlDumpTaskAbstract extends TaskAbstract_1.TaskAbstract {
88
+ verbose;
88
89
  async fetchPassword() {
89
90
  if (typeof this.config.password === "string")
90
91
  return this.config.password;
@@ -3,9 +3,10 @@ Object.defineProperty(exports, "__esModule", { value: true });
3
3
  exports.TaskAbstract = void 0;
4
4
  const fs_1 = require("../utils/fs");
5
5
  class TaskAbstract {
6
+ config;
7
+ tmpDirs = [];
6
8
  constructor(config) {
7
9
  this.config = config;
8
- this.tmpDirs = [];
9
10
  }
10
11
  async mkTmpDir(prefix, id) {
11
12
  const dir = await (0, fs_1.mkTmpDir)(prefix, id);
@@ -458,45 +458,31 @@
458
458
  "additionalProperties": false,
459
459
  "properties": {
460
460
  "compress": {
461
- "anyOf": [
462
- {
463
- "type": "boolean"
464
- },
465
- {
466
- "type": "object",
467
- "additionalProperties": false,
468
- "properties": {
469
- "packs": {
470
- "type": "array",
471
- "items": {
472
- "type": "object",
473
- "additionalProperties": false,
474
- "required": [
475
- "include"
476
- ],
477
- "properties": {
478
- "name": {
479
- "type": "string"
480
- },
481
- "include": {
482
- "$ref": "#/definitions/stringlist-util"
483
- },
484
- "exclude": {
485
- "$ref": "#/definitions/stringlist-util"
486
- },
487
- "onePackByResult": {
488
- "type": "boolean"
489
- }
490
- }
491
- }
492
- }
461
+ "type": "boolean"
462
+ },
463
+ "packs": {
464
+ "type": "array",
465
+ "items": {
466
+ "type": "object",
467
+ "additionalProperties": false,
468
+ "required": [
469
+ "include"
470
+ ],
471
+ "properties": {
472
+ "name": {
473
+ "type": "string"
474
+ },
475
+ "include": {
476
+ "$ref": "#/definitions/stringlist-util"
477
+ },
478
+ "exclude": {
479
+ "$ref": "#/definitions/stringlist-util"
480
+ },
481
+ "onePackByResult": {
482
+ "type": "boolean"
493
483
  }
494
484
  }
495
- ]
496
- },
497
- "fileCopyConcurrency": {
498
- "type": "integer",
499
- "minimum": 1
485
+ }
500
486
  }
501
487
  }
502
488
  },
@@ -798,6 +784,50 @@
798
784
  },
799
785
  "excludeDatabases": {
800
786
  "$ref": "#/definitions/stringlist-util"
787
+ },
788
+ "parallel": {
789
+ "anyOf": [
790
+ {
791
+ "type": "integer",
792
+ "minimum": 1
793
+ },
794
+ {
795
+ "enum": [
796
+ "auto"
797
+ ]
798
+ }
799
+ ]
800
+ },
801
+ "compress": {
802
+ "anyOf": [
803
+ {
804
+ "type": "object",
805
+ "additionalProperties": false,
806
+ "properties": {
807
+ "command": {
808
+ "type": "string"
809
+ },
810
+ "args": {
811
+ "$ref": "#/definitions/stringlist-util"
812
+ }
813
+ }
814
+ },
815
+ {
816
+ "type": "object",
817
+ "additionalProperties": false,
818
+ "properties": {
819
+ "type": {
820
+ "enum": [
821
+ "gzip",
822
+ "pigz"
823
+ ]
824
+ },
825
+ "args": {
826
+ "$ref": "#/definitions/stringlist-util"
827
+ }
828
+ }
829
+ }
830
+ ]
801
831
  }
802
832
  }
803
833
  },
package/index.d.ts CHANGED
@@ -0,0 +1 @@
1
+ export {};
package/index.js CHANGED
@@ -1 +1,2 @@
1
1
  "use strict";
2
+ Object.defineProperty(exports, "__esModule", { value: true });
package/package.json CHANGED
@@ -1,23 +1,24 @@
1
1
  {
2
2
  "name": "@datatruck/cli",
3
- "version": "0.17.2",
3
+ "version": "0.19.0",
4
4
  "dependencies": {
5
- "ajv": "^8.11.2",
5
+ "ajv": "^8.12.0",
6
6
  "async": "^3.2.4",
7
7
  "chalk": "^4.1.2",
8
8
  "cli-table3": "^0.6.3",
9
- "commander": "^9.4.1",
10
- "dayjs": "^1.11.7",
11
- "fast-folder-size": "^1.7.1",
12
- "fast-glob": "^3.2.12",
9
+ "commander": "^11.0.0",
10
+ "dayjs": "^1.11.10",
11
+ "fast-folder-size": "^2.2.0",
12
+ "fast-glob": "^3.3.1",
13
13
  "micromatch": "^4.0.5",
14
14
  "pretty-bytes": "^5.6.0",
15
- "sqlite": "^4.1.2",
16
- "sqlite3": "^5.1.4"
15
+ "sqlite": "^5.0.1",
16
+ "sqlite3": "^5.1.6",
17
+ "tar": "^6.2.0"
17
18
  },
18
19
  "optionalDependencies": {
19
20
  "ts-node": "^10.9.1",
20
- "yaml": "^2.2.0"
21
+ "yaml": "^2.3.2"
21
22
  },
22
23
  "engine": {
23
24
  "node": ">=16.0.0"
@@ -10,6 +10,7 @@ const util_1 = require("util");
10
10
  const customPrefix = "custom=";
11
11
  const tplPrefix = "tpl=";
12
12
  class DataFormat {
13
+ options;
13
14
  constructor(options) {
14
15
  this.options = options;
15
16
  }
package/utils/Git.js CHANGED
@@ -4,6 +4,7 @@ exports.Git = void 0;
4
4
  const fs_1 = require("./fs");
5
5
  const process_1 = require("./process");
6
6
  class Git {
7
+ options;
7
8
  constructor(options) {
8
9
  this.options = options;
9
10
  }
@@ -2,11 +2,9 @@
2
2
  Object.defineProperty(exports, "__esModule", { value: true });
3
3
  exports.ObjectVault = void 0;
4
4
  class ObjectVault {
5
- constructor() {
6
- this.counter = 0;
7
- this.ids = {};
8
- this.objects = {};
9
- }
5
+ counter = 0;
6
+ ids = {};
7
+ objects = {};
10
8
  static serializeKeys(keys) {
11
9
  return JSON.stringify(keys);
12
10
  }
package/utils/Restic.js CHANGED
@@ -7,6 +7,7 @@ const string_1 = require("./string");
7
7
  const promises_1 = require("fs/promises");
8
8
  const path_1 = require("path");
9
9
  class Restic {
10
+ options;
10
11
  constructor(options) {
11
12
  this.options = options;
12
13
  }
@@ -59,8 +59,8 @@ export declare const params: {
59
59
  action: string;
60
60
  };
61
61
  pkgRestorePath: {
62
- packageName: string;
63
62
  path: string;
63
+ packageName: string;
64
64
  snapshotId: string;
65
65
  temp: string;
66
66
  snapshotDate: string;
package/utils/fs.d.ts CHANGED
@@ -2,7 +2,9 @@
2
2
  /// <reference types="node" />
3
3
  /// <reference types="node" />
4
4
  /// <reference types="node" />
5
- import { Dirent, Stats } from "fs";
5
+ import { Progress } from "./progress";
6
+ import { Entry, Options } from "fast-glob";
7
+ import { Dirent, ReadStream, Stats } from "fs";
6
8
  import { WriteStream } from "fs";
7
9
  import { Interface } from "readline";
8
10
  export declare const isWSLSystem: boolean;
@@ -51,7 +53,7 @@ export declare function writeGitIgnoreList(options: {
51
53
  paths: NodeJS.ReadableStream | string[];
52
54
  outDir: string;
53
55
  }): Promise<string>;
54
- export declare function waitForClose(stream: WriteStream): Promise<WriteStream>;
56
+ export declare function waitForClose(stream: WriteStream | ReadStream): Promise<void>;
55
57
  export declare function copyFileWithStreams(source: string, target: string): Promise<unknown>;
56
58
  export declare function updateFileStats(path: string, fileInfo: Stats): Promise<void>;
57
59
  export declare function isNotFoundError(error: unknown): boolean;
@@ -97,4 +99,17 @@ export declare function cpy(options: {
97
99
  files: number;
98
100
  dirs: number;
99
101
  }>;
102
+ export declare function createFileScanner(options: {
103
+ glob: Options & {
104
+ include: string[];
105
+ };
106
+ onProgress: (data: Progress) => Promise<void>;
107
+ }): Promise<{
108
+ disposed: boolean;
109
+ total: number;
110
+ current: number;
111
+ progress: (description: string, path?: string) => Promise<void>;
112
+ end: () => Promise<void>;
113
+ start: (cb?: ((entry: Required<Entry>) => any) | undefined) => Promise<void>;
114
+ }>;
100
115
  export {};