@regressionproof/snapshotter 0.3.6 → 0.3.8

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 (65) hide show
  1. package/build/.spruce/errors/errors.types.d.ts +35 -0
  2. package/build/.spruce/errors/errors.types.js +2 -0
  3. package/build/.spruce/errors/options.types.d.ts +7 -0
  4. package/build/.spruce/errors/options.types.js +2 -0
  5. package/build/.spruce/errors/regressionproofSnapshotter/execCommandFailed.schema.d.ts +3 -0
  6. package/build/.spruce/errors/regressionproofSnapshotter/execCommandFailed.schema.js +29 -0
  7. package/build/.spruce/schemas/fields/fieldClassMap.d.ts +2 -0
  8. package/build/.spruce/schemas/fields/fieldClassMap.js +4 -0
  9. package/{src/.spruce/schemas/fields/fields.types.ts → build/.spruce/schemas/fields/fields.types.d.ts} +1 -1
  10. package/build/.spruce/schemas/fields/fields.types.js +2 -0
  11. package/build/errors/SpruceError.d.ts +6 -0
  12. package/build/errors/SpruceError.js +31 -0
  13. package/build/errors/execCommandFailed.builder.d.ts +18 -0
  14. package/build/errors/execCommandFailed.builder.js +20 -0
  15. package/build/esm/.spruce/errors/errors.types.d.ts +35 -0
  16. package/build/esm/.spruce/errors/errors.types.js +1 -0
  17. package/build/esm/.spruce/errors/options.types.d.ts +7 -0
  18. package/build/esm/.spruce/errors/options.types.js +1 -0
  19. package/build/esm/errors/SpruceError.d.ts +6 -0
  20. package/build/esm/errors/SpruceError.js +26 -0
  21. package/build/esm/errors/execCommandFailed.builder.d.ts +18 -0
  22. package/{src/errors/execCommandFailed.builder.ts → build/esm/errors/execCommandFailed.builder.js} +2 -3
  23. package/build/esm/git.d.ts +4 -0
  24. package/build/esm/git.js +65 -0
  25. package/build/esm/index.d.ts +2 -0
  26. package/build/esm/index.js +2 -0
  27. package/build/esm/scripts/testManual.d.ts +1 -0
  28. package/build/esm/scripts/testManual.js +60 -0
  29. package/build/esm/snapshot.d.ts +2 -0
  30. package/build/esm/snapshot.js +54 -0
  31. package/{src/snapshotter.types.ts → build/esm/snapshotter.types.d.ts} +21 -26
  32. package/build/esm/snapshotter.types.js +1 -0
  33. package/build/esm/sync.d.ts +1 -0
  34. package/build/esm/sync.js +40 -0
  35. package/build/git.d.ts +4 -0
  36. package/build/git.js +56 -0
  37. package/build/index.d.ts +2 -0
  38. package/build/index.js +20 -0
  39. package/build/scripts/testManual.d.ts +1 -0
  40. package/{src/scripts/testManual.ts → build/scripts/testManual.js} +19 -23
  41. package/build/snapshot.d.ts +2 -0
  42. package/build/snapshot.js +46 -0
  43. package/build/snapshotter.types.d.ts +54 -0
  44. package/build/snapshotter.types.js +2 -0
  45. package/build/sync.d.ts +1 -0
  46. package/build/sync.js +35 -0
  47. package/package.json +5 -2
  48. package/.nvmrc +0 -1
  49. package/.vscode/launch.json +0 -58
  50. package/.vscode/settings.json +0 -67
  51. package/.vscode/tasks.json +0 -112
  52. package/CHANGELOG.md +0 -320
  53. package/eslint.config.mjs +0 -3
  54. package/src/.spruce/errors/errors.types.ts +0 -52
  55. package/src/.spruce/errors/options.types.ts +0 -10
  56. package/src/.spruce/errors/regressionproofSnapshotter/execCommandFailed.schema.ts +0 -33
  57. package/src/.spruce/schemas/fields/fieldClassMap.ts +0 -6
  58. package/src/errors/SpruceError.ts +0 -29
  59. package/src/git.ts +0 -75
  60. package/src/index.ts +0 -2
  61. package/src/snapshot.ts +0 -51
  62. package/src/sync.ts +0 -35
  63. package/tsconfig.dist.json +0 -26
  64. package/tsconfig.json +0 -27
  65. /package/{src → build}/.spruce/settings.json +0 -0
@@ -0,0 +1,35 @@
1
+ import { default as SchemaEntity } from '@sprucelabs/schema';
2
+ import * as SpruceSchema from '@sprucelabs/schema';
3
+ export declare namespace SpruceErrors.RegressionproofSnapshotter {
4
+ interface ExecCommandFailed {
5
+ /** . The command that was attempted */
6
+ 'command': string;
7
+ 'stdout'?: string | undefined | null;
8
+ 'stderr'?: string | undefined | null;
9
+ }
10
+ interface ExecCommandFailedSchema extends SpruceSchema.Schema {
11
+ id: 'execCommandFailed';
12
+ namespace: 'RegressionproofSnapshotter';
13
+ name: 'Exec command failed';
14
+ fields: {
15
+ /** . The command that was attempted */
16
+ 'command': {
17
+ type: 'text';
18
+ isRequired: true;
19
+ hint: 'The command that was attempted';
20
+ options: undefined;
21
+ };
22
+ /** . */
23
+ 'stdout': {
24
+ type: 'text';
25
+ options: undefined;
26
+ };
27
+ /** . */
28
+ 'stderr': {
29
+ type: 'text';
30
+ options: undefined;
31
+ };
32
+ };
33
+ }
34
+ type ExecCommandFailedEntity = SchemaEntity<SpruceErrors.RegressionproofSnapshotter.ExecCommandFailedSchema>;
35
+ }
@@ -0,0 +1,2 @@
1
+ "use strict";
2
+ Object.defineProperty(exports, "__esModule", { value: true });
@@ -0,0 +1,7 @@
1
+ import { SpruceErrors } from "./errors.types";
2
+ import { ErrorOptions as ISpruceErrorOptions } from "@sprucelabs/error";
3
+ export interface ExecCommandFailedErrorOptions extends SpruceErrors.RegressionproofSnapshotter.ExecCommandFailed, ISpruceErrorOptions {
4
+ code: 'EXEC_COMMAND_FAILED';
5
+ }
6
+ type ErrorOptions = ExecCommandFailedErrorOptions;
7
+ export default ErrorOptions;
@@ -0,0 +1,2 @@
1
+ "use strict";
2
+ Object.defineProperty(exports, "__esModule", { value: true });
@@ -0,0 +1,3 @@
1
+ import { SpruceErrors } from '../errors.types';
2
+ declare const execCommandFailedSchema: SpruceErrors.RegressionproofSnapshotter.ExecCommandFailedSchema;
3
+ export default execCommandFailedSchema;
@@ -0,0 +1,29 @@
1
+ "use strict";
2
+ Object.defineProperty(exports, "__esModule", { value: true });
3
+ const schema_1 = require("@sprucelabs/schema");
4
+ const execCommandFailedSchema = {
5
+ id: 'execCommandFailed',
6
+ namespace: 'RegressionproofSnapshotter',
7
+ name: 'Exec command failed',
8
+ fields: {
9
+ /** . The command that was attempted */
10
+ 'command': {
11
+ type: 'text',
12
+ isRequired: true,
13
+ hint: 'The command that was attempted',
14
+ options: undefined
15
+ },
16
+ /** . */
17
+ 'stdout': {
18
+ type: 'text',
19
+ options: undefined
20
+ },
21
+ /** . */
22
+ 'stderr': {
23
+ type: 'text',
24
+ options: undefined
25
+ },
26
+ }
27
+ };
28
+ schema_1.SchemaRegistry.getInstance().trackSchema(execCommandFailedSchema);
29
+ exports.default = execCommandFailedSchema;
@@ -0,0 +1,2 @@
1
+ import { fieldClassMap } from '@sprucelabs/schema';
2
+ export default fieldClassMap;
@@ -0,0 +1,4 @@
1
+ "use strict";
2
+ Object.defineProperty(exports, "__esModule", { value: true });
3
+ const schema_1 = require("@sprucelabs/schema");
4
+ exports.default = schema_1.fieldClassMap;
@@ -1 +1 @@
1
- export { FieldDefinitions, FieldDefinitionMap, FieldValueTypeGeneratorMap, FieldMap } from '@sprucelabs/schema'
1
+ export { FieldDefinitions, FieldDefinitionMap, FieldValueTypeGeneratorMap, FieldMap } from '@sprucelabs/schema';
@@ -0,0 +1,2 @@
1
+ "use strict";
2
+ Object.defineProperty(exports, "__esModule", { value: true });
@@ -0,0 +1,6 @@
1
+ import BaseSpruceError from '@sprucelabs/error';
2
+ import ErrorOptions from './../.spruce/errors/options.types';
3
+ export default class SpruceError extends BaseSpruceError<ErrorOptions> {
4
+ /** an easy to understand version of the errors */
5
+ friendlyMessage(): string;
6
+ }
@@ -0,0 +1,31 @@
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
+ const error_1 = __importDefault(require("@sprucelabs/error"));
7
+ class SpruceError extends error_1.default {
8
+ /** an easy to understand version of the errors */
9
+ friendlyMessage() {
10
+ const { options } = this;
11
+ let message;
12
+ switch (options?.code) {
13
+ case 'EXEC_COMMAND_FAILED':
14
+ message = `The command "${options.command}" failed to execute.
15
+
16
+ Stdout:
17
+ ${options.stdout ?? '<no stdout>'}
18
+
19
+ Stderr:
20
+ ${options.stderr ?? '<no stderr>'}`;
21
+ break;
22
+ default:
23
+ message = super.friendlyMessage();
24
+ }
25
+ const fullMessage = options.friendlyMessage
26
+ ? options.friendlyMessage
27
+ : message;
28
+ return fullMessage;
29
+ }
30
+ }
31
+ exports.default = SpruceError;
@@ -0,0 +1,18 @@
1
+ declare const _default: {
2
+ id: string;
3
+ name: string;
4
+ fields: {
5
+ command: {
6
+ type: "text";
7
+ isRequired: true;
8
+ hint: string;
9
+ };
10
+ stdout: {
11
+ type: "text";
12
+ };
13
+ stderr: {
14
+ type: "text";
15
+ };
16
+ };
17
+ };
18
+ export default _default;
@@ -0,0 +1,20 @@
1
+ "use strict";
2
+ Object.defineProperty(exports, "__esModule", { value: true });
3
+ const schema_1 = require("@sprucelabs/schema");
4
+ exports.default = (0, schema_1.buildErrorSchema)({
5
+ id: 'execCommandFailed',
6
+ name: 'Exec command failed',
7
+ fields: {
8
+ command: {
9
+ type: 'text',
10
+ isRequired: true,
11
+ hint: 'The command that was attempted',
12
+ },
13
+ stdout: {
14
+ type: 'text',
15
+ },
16
+ stderr: {
17
+ type: 'text',
18
+ },
19
+ },
20
+ });
@@ -0,0 +1,35 @@
1
+ import { default as SchemaEntity } from '@sprucelabs/schema';
2
+ import * as SpruceSchema from '@sprucelabs/schema';
3
+ export declare namespace SpruceErrors.RegressionproofSnapshotter {
4
+ interface ExecCommandFailed {
5
+ /** . The command that was attempted */
6
+ 'command': string;
7
+ 'stdout'?: string | undefined | null;
8
+ 'stderr'?: string | undefined | null;
9
+ }
10
+ interface ExecCommandFailedSchema extends SpruceSchema.Schema {
11
+ id: 'execCommandFailed';
12
+ namespace: 'RegressionproofSnapshotter';
13
+ name: 'Exec command failed';
14
+ fields: {
15
+ /** . The command that was attempted */
16
+ 'command': {
17
+ type: 'text';
18
+ isRequired: true;
19
+ hint: 'The command that was attempted';
20
+ options: undefined;
21
+ };
22
+ /** . */
23
+ 'stdout': {
24
+ type: 'text';
25
+ options: undefined;
26
+ };
27
+ /** . */
28
+ 'stderr': {
29
+ type: 'text';
30
+ options: undefined;
31
+ };
32
+ };
33
+ }
34
+ type ExecCommandFailedEntity = SchemaEntity<SpruceErrors.RegressionproofSnapshotter.ExecCommandFailedSchema>;
35
+ }
@@ -0,0 +1 @@
1
+ export {};
@@ -0,0 +1,7 @@
1
+ import { SpruceErrors } from "./errors.types";
2
+ import { ErrorOptions as ISpruceErrorOptions } from "@sprucelabs/error";
3
+ export interface ExecCommandFailedErrorOptions extends SpruceErrors.RegressionproofSnapshotter.ExecCommandFailed, ISpruceErrorOptions {
4
+ code: 'EXEC_COMMAND_FAILED';
5
+ }
6
+ type ErrorOptions = ExecCommandFailedErrorOptions;
7
+ export default ErrorOptions;
@@ -0,0 +1 @@
1
+ export {};
@@ -0,0 +1,6 @@
1
+ import BaseSpruceError from '@sprucelabs/error';
2
+ import ErrorOptions from './../.spruce/errors/options.types';
3
+ export default class SpruceError extends BaseSpruceError<ErrorOptions> {
4
+ /** an easy to understand version of the errors */
5
+ friendlyMessage(): string;
6
+ }
@@ -0,0 +1,26 @@
1
+ import BaseSpruceError from '@sprucelabs/error';
2
+ export default class SpruceError extends BaseSpruceError {
3
+ /** an easy to understand version of the errors */
4
+ friendlyMessage() {
5
+ var _a, _b;
6
+ const { options } = this;
7
+ let message;
8
+ switch (options === null || options === void 0 ? void 0 : options.code) {
9
+ case 'EXEC_COMMAND_FAILED':
10
+ message = `The command "${options.command}" failed to execute.
11
+
12
+ Stdout:
13
+ ${(_a = options.stdout) !== null && _a !== void 0 ? _a : '<no stdout>'}
14
+
15
+ Stderr:
16
+ ${(_b = options.stderr) !== null && _b !== void 0 ? _b : '<no stderr>'}`;
17
+ break;
18
+ default:
19
+ message = super.friendlyMessage();
20
+ }
21
+ const fullMessage = options.friendlyMessage
22
+ ? options.friendlyMessage
23
+ : message;
24
+ return fullMessage;
25
+ }
26
+ }
@@ -0,0 +1,18 @@
1
+ declare const _default: {
2
+ id: string;
3
+ name: string;
4
+ fields: {
5
+ command: {
6
+ type: "text";
7
+ isRequired: true;
8
+ hint: string;
9
+ };
10
+ stdout: {
11
+ type: "text";
12
+ };
13
+ stderr: {
14
+ type: "text";
15
+ };
16
+ };
17
+ };
18
+ export default _default;
@@ -1,5 +1,4 @@
1
- import { buildErrorSchema } from '@sprucelabs/schema'
2
-
1
+ import { buildErrorSchema } from '@sprucelabs/schema';
3
2
  export default buildErrorSchema({
4
3
  id: 'execCommandFailed',
5
4
  name: 'Exec command failed',
@@ -16,4 +15,4 @@ export default buildErrorSchema({
16
15
  type: 'text',
17
16
  },
18
17
  },
19
- })
18
+ });
@@ -0,0 +1,4 @@
1
+ import { Log } from '@sprucelabs/spruce-skill-utils';
2
+ import { RemoteOptions } from './snapshotter.types.js';
3
+ export declare function gitCommit(mirrorPath: string, log?: Log): Promise<boolean>;
4
+ export declare function gitPush(mirrorPath: string, remote: RemoteOptions, log?: Log): Promise<void>;
@@ -0,0 +1,65 @@
1
+ var __awaiter = (this && this.__awaiter) || function (thisArg, _arguments, P, generator) {
2
+ function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); }
3
+ return new (P || (P = Promise))(function (resolve, reject) {
4
+ function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } }
5
+ function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } }
6
+ function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); }
7
+ step((generator = generator.apply(thisArg, _arguments || [])).next());
8
+ });
9
+ };
10
+ import { exec } from 'child_process';
11
+ import { existsSync } from 'fs';
12
+ import path from 'path';
13
+ import { promisify } from 'util';
14
+ import SpruceError from './errors/SpruceError.js.js';
15
+ const execAsync = promisify(exec);
16
+ export function gitCommit(mirrorPath, log) {
17
+ return __awaiter(this, void 0, void 0, function* () {
18
+ const gitDir = path.join(mirrorPath, '.git');
19
+ if (!existsSync(gitDir)) {
20
+ yield execOrThrow(`git -C "${mirrorPath}" init`, log);
21
+ }
22
+ yield execOrThrow(`git -C "${mirrorPath}" add -A`, log);
23
+ const { stdout } = yield execOrThrow(`git -C "${mirrorPath}" status --porcelain`);
24
+ if (!stdout.trim()) {
25
+ log === null || log === void 0 ? void 0 : log.info('No changes detected for commit', mirrorPath);
26
+ return false;
27
+ }
28
+ const message = `Snapshot ${new Date().toISOString()}`;
29
+ yield execOrThrow(`git -C "${mirrorPath}" commit -m "${message}"`, log);
30
+ return true;
31
+ });
32
+ }
33
+ export function gitPush(mirrorPath, remote, log) {
34
+ return __awaiter(this, void 0, void 0, function* () {
35
+ const authedUrl = remote.url.replace('://', `://${remote.token}@`);
36
+ try {
37
+ yield execOrThrow(`git -C "${mirrorPath}" remote get-url origin`, log);
38
+ yield execOrThrow(`git -C "${mirrorPath}" remote set-url origin "${authedUrl}"`);
39
+ }
40
+ catch (_a) {
41
+ yield execOrThrow(`git -C "${mirrorPath}" remote add origin "${authedUrl}"`);
42
+ }
43
+ yield execOrThrow(`git -C "${mirrorPath}" push -u origin HEAD`, log);
44
+ });
45
+ }
46
+ function execOrThrow(command, log) {
47
+ return __awaiter(this, void 0, void 0, function* () {
48
+ var _a, _b;
49
+ try {
50
+ return yield execAsync(command);
51
+ }
52
+ catch (err) {
53
+ const error = err;
54
+ const stdout = (_a = error.stdout) !== null && _a !== void 0 ? _a : '';
55
+ const stderr = (_b = error.stderr) !== null && _b !== void 0 ? _b : '';
56
+ log === null || log === void 0 ? void 0 : log.error('Command failed', command, stderr);
57
+ throw new SpruceError({
58
+ code: 'EXEC_COMMAND_FAILED',
59
+ command,
60
+ stdout,
61
+ stderr,
62
+ });
63
+ }
64
+ });
65
+ }
@@ -0,0 +1,2 @@
1
+ export { snapshot } from './snapshot.js';
2
+ export * from './snapshotter.types.js';
@@ -0,0 +1,2 @@
1
+ export { snapshot } from './snapshot.js.js';
2
+ export * from './snapshotter.types.js.js';
@@ -0,0 +1 @@
1
+ export {};
@@ -0,0 +1,60 @@
1
+ var __awaiter = (this && this.__awaiter) || function (thisArg, _arguments, P, generator) {
2
+ function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); }
3
+ return new (P || (P = Promise))(function (resolve, reject) {
4
+ function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } }
5
+ function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } }
6
+ function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); }
7
+ step((generator = generator.apply(thisArg, _arguments || [])).next());
8
+ });
9
+ };
10
+ import { snapshot } from '../index.js';
11
+ function main() {
12
+ return __awaiter(this, void 0, void 0, function* () {
13
+ const sourcePath = process.env.SOURCE_PATH;
14
+ const mirrorPath = process.env.MIRROR_PATH;
15
+ const remoteUrl = process.env.REMOTE_URL;
16
+ const remoteToken = process.env.REMOTE_TOKEN;
17
+ if (!sourcePath || !mirrorPath || !remoteUrl || !remoteToken) {
18
+ console.error('Missing required env vars. See .env.example');
19
+ process.exit(1);
20
+ }
21
+ console.log('Running snapshot...');
22
+ console.log(' Source:', sourcePath);
23
+ console.log(' Mirror:', mirrorPath);
24
+ console.log(' Remote:', remoteUrl);
25
+ const result = yield snapshot({
26
+ sourcePath,
27
+ mirrorPath,
28
+ testResults: {
29
+ timestamp: new Date().toISOString(),
30
+ summary: {
31
+ totalSuites: 1,
32
+ passedSuites: 1,
33
+ failedSuites: 0,
34
+ totalTests: 2,
35
+ passedTests: 2,
36
+ failedTests: 0,
37
+ },
38
+ suites: [
39
+ {
40
+ path: 'src/__tests__/Example.test.ts',
41
+ passed: true,
42
+ tests: [
43
+ { name: 'should work', passed: true },
44
+ { name: 'should also work', passed: true },
45
+ ],
46
+ },
47
+ ],
48
+ },
49
+ remote: {
50
+ url: remoteUrl,
51
+ token: remoteToken,
52
+ },
53
+ });
54
+ console.log('Snapshot created:', result);
55
+ });
56
+ }
57
+ main().catch((err) => {
58
+ console.error('Error:', err.message);
59
+ process.exit(1);
60
+ });
@@ -0,0 +1,2 @@
1
+ import { SnapshotOptions } from './snapshotter.types.js';
2
+ export declare function snapshot(options: SnapshotOptions): Promise<boolean>;
@@ -0,0 +1,54 @@
1
+ var __awaiter = (this && this.__awaiter) || function (thisArg, _arguments, P, generator) {
2
+ function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); }
3
+ return new (P || (P = Promise))(function (resolve, reject) {
4
+ function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } }
5
+ function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } }
6
+ function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); }
7
+ step((generator = generator.apply(thisArg, _arguments || [])).next());
8
+ });
9
+ };
10
+ import { mkdirSync, writeFileSync } from 'fs';
11
+ import path from 'path';
12
+ import { buildLog } from '@sprucelabs/spruce-skill-utils';
13
+ import { gitCommit, gitPush } from './git.js.js';
14
+ import { syncFiles } from './sync.js.js';
15
+ class Snapshotter {
16
+ constructor() {
17
+ this.log = buildLog('Snapshotter');
18
+ }
19
+ snapshot(options) {
20
+ return __awaiter(this, void 0, void 0, function* () {
21
+ var _a;
22
+ const sourcePath = (_a = options.sourcePath) !== null && _a !== void 0 ? _a : process.cwd();
23
+ const { mirrorPath, testResults, remote } = options;
24
+ this.log.info('Starting snapshot', sourcePath, mirrorPath);
25
+ try {
26
+ yield syncFiles(sourcePath, mirrorPath);
27
+ this.log.info('Files synced', mirrorPath);
28
+ const snapshotterDir = path.join(mirrorPath, '.snapshotter');
29
+ mkdirSync(snapshotterDir, { recursive: true });
30
+ writeFileSync(path.join(snapshotterDir, 'testResults.json'), JSON.stringify(testResults, null, 2));
31
+ this.log.info('Test results saved', snapshotterDir);
32
+ const committed = yield gitCommit(mirrorPath, this.log);
33
+ if (!committed) {
34
+ this.log.info('No changes to commit', mirrorPath);
35
+ return false;
36
+ }
37
+ this.log.info('Commit created, pushing', remote.url);
38
+ yield gitPush(mirrorPath, remote, this.log);
39
+ this.log.info('Push completed', remote.url);
40
+ return true;
41
+ }
42
+ catch (err) {
43
+ const message = err instanceof Error ? err.message : String(err);
44
+ this.log.error('Snapshot failed', message);
45
+ throw err;
46
+ }
47
+ });
48
+ }
49
+ }
50
+ export function snapshot(options) {
51
+ return __awaiter(this, void 0, void 0, function* () {
52
+ return new Snapshotter().snapshot(options);
53
+ });
54
+ }
@@ -1,59 +1,54 @@
1
1
  export interface TestResult {
2
2
  /** Name of the individual test */
3
- name: string
3
+ name: string;
4
4
  /** Whether this test passed */
5
- passed: boolean
5
+ passed: boolean;
6
6
  /** Full error message + callstack (only present if failed) */
7
- error?: string
7
+ error?: string;
8
8
  }
9
-
10
9
  export interface SuiteResult {
11
10
  /** Path to test file, relative to project root */
12
- path: string
11
+ path: string;
13
12
  /** Whether all tests in suite passed */
14
- passed: boolean
13
+ passed: boolean;
15
14
  /** Array of test results */
16
- tests: TestResult[]
15
+ tests: TestResult[];
17
16
  }
18
-
19
17
  export interface TestResultsSummary {
20
18
  /** Total number of test suites (files) */
21
- totalSuites: number
19
+ totalSuites: number;
22
20
  /** Number of suites with all tests passing */
23
- passedSuites: number
21
+ passedSuites: number;
24
22
  /** Number of suites with at least one failure */
25
- failedSuites: number
23
+ failedSuites: number;
26
24
  /** Total number of individual tests */
27
- totalTests: number
25
+ totalTests: number;
28
26
  /** Number of passing tests */
29
- passedTests: number
27
+ passedTests: number;
30
28
  /** Number of failing tests */
31
- failedTests: number
29
+ failedTests: number;
32
30
  }
33
-
34
31
  export interface TestResults {
35
32
  /** ISO 8601 timestamp of when test run completed */
36
- timestamp: string
33
+ timestamp: string;
37
34
  /** Summary counts */
38
- summary: TestResultsSummary
35
+ summary: TestResultsSummary;
39
36
  /** Array of suite results */
40
- suites: SuiteResult[]
37
+ suites: SuiteResult[];
41
38
  }
42
-
43
39
  export interface RemoteOptions {
44
40
  /** Gitea repo URL to push to */
45
- url: string
41
+ url: string;
46
42
  /** Gitea access token for authentication */
47
- token: string
43
+ token: string;
48
44
  }
49
-
50
45
  export interface SnapshotOptions {
51
46
  /** Source project path to sync from. Defaults to process.cwd() */
52
- sourcePath?: string
47
+ sourcePath?: string;
53
48
  /** Mirror directory path where the isolated git repo lives */
54
- mirrorPath: string
49
+ mirrorPath: string;
55
50
  /** Test results from the completed test run */
56
- testResults: TestResults
51
+ testResults: TestResults;
57
52
  /** Remote Gitea repo to push to */
58
- remote: RemoteOptions
53
+ remote: RemoteOptions;
59
54
  }
@@ -0,0 +1 @@
1
+ export {};
@@ -0,0 +1 @@
1
+ export declare function syncFiles(sourcePath: string, mirrorPath: string): Promise<void>;
@@ -0,0 +1,40 @@
1
+ var __awaiter = (this && this.__awaiter) || function (thisArg, _arguments, P, generator) {
2
+ function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); }
3
+ return new (P || (P = Promise))(function (resolve, reject) {
4
+ function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } }
5
+ function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } }
6
+ function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); }
7
+ step((generator = generator.apply(thisArg, _arguments || [])).next());
8
+ });
9
+ };
10
+ import { exec } from 'child_process';
11
+ import { existsSync } from 'fs';
12
+ import path from 'path';
13
+ import { promisify } from 'util';
14
+ const execAsync = promisify(exec);
15
+ const DEFAULT_EXCLUDES = [
16
+ 'node_modules',
17
+ 'build',
18
+ '*.env*',
19
+ '*.pem',
20
+ '*.key',
21
+ '*.p12',
22
+ '*.pfx',
23
+ '*credentials*',
24
+ '*secret*',
25
+ '*.local',
26
+ ];
27
+ export function syncFiles(sourcePath, mirrorPath) {
28
+ return __awaiter(this, void 0, void 0, function* () {
29
+ const hasGitIgnore = existsSync(path.join(sourcePath, '.gitignore'));
30
+ const excludes = DEFAULT_EXCLUDES.map((e) => `--exclude='${e}'`).join(' ');
31
+ if (hasGitIgnore) {
32
+ const cmd = `cd "${sourcePath}" && git ls-files --cached --others --exclude-standard -z | rsync -av --files-from=- --from0 ${excludes} . "${mirrorPath}/"`;
33
+ yield execAsync(cmd);
34
+ }
35
+ else {
36
+ const cmd = `rsync -av --delete ${excludes} "${sourcePath}/" "${mirrorPath}/"`;
37
+ yield execAsync(cmd);
38
+ }
39
+ });
40
+ }
package/build/git.d.ts ADDED
@@ -0,0 +1,4 @@
1
+ import { Log } from '@sprucelabs/spruce-skill-utils';
2
+ import { RemoteOptions } from './snapshotter.types.js';
3
+ export declare function gitCommit(mirrorPath: string, log?: Log): Promise<boolean>;
4
+ export declare function gitPush(mirrorPath: string, remote: RemoteOptions, log?: Log): Promise<void>;