pushwork 1.0.4 → 1.0.7

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 (195) hide show
  1. package/README.md +87 -328
  2. package/dist/.pushwork/automerge/3P/Dm3ekE2pmjGnWvDaG3vSR7ww98/snapshot/aa2349c94955ea561f698720142f9d884a6872d9f82dc332d578c216beb0df0e +0 -0
  3. package/dist/.pushwork/automerge/st/orage-adapter-id +1 -0
  4. package/dist/.pushwork/config.json +15 -0
  5. package/dist/.pushwork/snapshot.json +7 -0
  6. package/dist/cli.js +231 -170
  7. package/dist/cli.js.map +1 -1
  8. package/dist/commands.d.ts +51 -0
  9. package/dist/commands.d.ts.map +1 -0
  10. package/dist/commands.js +799 -0
  11. package/dist/commands.js.map +1 -0
  12. package/dist/core/change-detection.d.ts +6 -19
  13. package/dist/core/change-detection.d.ts.map +1 -1
  14. package/dist/core/change-detection.js +101 -80
  15. package/dist/core/change-detection.js.map +1 -1
  16. package/dist/{config/index.d.ts → core/config.d.ts} +13 -3
  17. package/dist/core/config.d.ts.map +1 -0
  18. package/dist/{config/index.js → core/config.js} +55 -73
  19. package/dist/core/config.js.map +1 -0
  20. package/dist/core/index.d.ts +1 -0
  21. package/dist/core/index.d.ts.map +1 -1
  22. package/dist/core/index.js +1 -1
  23. package/dist/core/index.js.map +1 -1
  24. package/dist/core/move-detection.d.ts +12 -50
  25. package/dist/core/move-detection.d.ts.map +1 -1
  26. package/dist/core/move-detection.js +58 -139
  27. package/dist/core/move-detection.js.map +1 -1
  28. package/dist/core/snapshot.d.ts +0 -4
  29. package/dist/core/snapshot.d.ts.map +1 -1
  30. package/dist/core/snapshot.js +2 -11
  31. package/dist/core/snapshot.js.map +1 -1
  32. package/dist/core/sync-engine.d.ts +5 -11
  33. package/dist/core/sync-engine.d.ts.map +1 -1
  34. package/dist/core/sync-engine.js +220 -362
  35. package/dist/core/sync-engine.js.map +1 -1
  36. package/dist/index.d.ts +0 -1
  37. package/dist/index.d.ts.map +1 -1
  38. package/dist/index.js +0 -6
  39. package/dist/index.js.map +1 -1
  40. package/dist/types/config.d.ts +43 -67
  41. package/dist/types/config.d.ts.map +1 -1
  42. package/dist/types/config.js +6 -0
  43. package/dist/types/config.js.map +1 -1
  44. package/dist/types/documents.d.ts +15 -3
  45. package/dist/types/documents.d.ts.map +1 -1
  46. package/dist/types/documents.js.map +1 -1
  47. package/dist/types/index.d.ts.map +1 -1
  48. package/dist/types/index.js +0 -3
  49. package/dist/types/index.js.map +1 -1
  50. package/dist/types/snapshot.d.ts +3 -21
  51. package/dist/types/snapshot.d.ts.map +1 -1
  52. package/dist/types/snapshot.js +0 -14
  53. package/dist/types/snapshot.js.map +1 -1
  54. package/dist/utils/content.d.ts.map +1 -1
  55. package/dist/utils/content.js +2 -6
  56. package/dist/utils/content.js.map +1 -1
  57. package/dist/utils/directory.d.ts +10 -0
  58. package/dist/utils/directory.d.ts.map +1 -0
  59. package/dist/utils/directory.js +37 -0
  60. package/dist/utils/directory.js.map +1 -0
  61. package/dist/utils/fs.d.ts +15 -2
  62. package/dist/utils/fs.d.ts.map +1 -1
  63. package/dist/utils/fs.js +63 -53
  64. package/dist/utils/fs.js.map +1 -1
  65. package/dist/utils/index.d.ts +1 -1
  66. package/dist/utils/index.d.ts.map +1 -1
  67. package/dist/utils/index.js +1 -4
  68. package/dist/utils/index.js.map +1 -1
  69. package/dist/utils/mime-types.d.ts.map +1 -1
  70. package/dist/utils/mime-types.js +11 -4
  71. package/dist/utils/mime-types.js.map +1 -1
  72. package/dist/utils/network-sync.d.ts +0 -6
  73. package/dist/utils/network-sync.d.ts.map +1 -1
  74. package/dist/utils/network-sync.js +55 -99
  75. package/dist/utils/network-sync.js.map +1 -1
  76. package/dist/utils/output.d.ts +129 -0
  77. package/dist/utils/output.d.ts.map +1 -0
  78. package/dist/utils/output.js +375 -0
  79. package/dist/utils/output.js.map +1 -0
  80. package/dist/utils/repo-factory.d.ts +2 -6
  81. package/dist/utils/repo-factory.d.ts.map +1 -1
  82. package/dist/utils/repo-factory.js +8 -22
  83. package/dist/utils/repo-factory.js.map +1 -1
  84. package/dist/utils/string-similarity.d.ts +14 -0
  85. package/dist/utils/string-similarity.d.ts.map +1 -0
  86. package/dist/utils/string-similarity.js +43 -0
  87. package/dist/utils/string-similarity.js.map +1 -0
  88. package/dist/utils/trace.d.ts +19 -0
  89. package/dist/utils/trace.d.ts.map +1 -0
  90. package/dist/utils/trace.js +68 -0
  91. package/dist/utils/trace.js.map +1 -0
  92. package/package.json +17 -12
  93. package/src/cli.ts +326 -252
  94. package/src/commands.ts +988 -0
  95. package/src/core/change-detection.ts +199 -162
  96. package/src/{config/index.ts → core/config.ts} +65 -82
  97. package/src/core/index.ts +1 -1
  98. package/src/core/move-detection.ts +74 -180
  99. package/src/core/snapshot.ts +2 -12
  100. package/src/core/sync-engine.ts +248 -499
  101. package/src/index.ts +0 -10
  102. package/src/types/config.ts +50 -72
  103. package/src/types/documents.ts +16 -3
  104. package/src/types/index.ts +0 -5
  105. package/src/types/snapshot.ts +1 -23
  106. package/src/utils/content.ts +2 -6
  107. package/src/utils/directory.ts +50 -0
  108. package/src/utils/fs.ts +67 -56
  109. package/src/utils/index.ts +1 -6
  110. package/src/utils/mime-types.ts +12 -4
  111. package/src/utils/network-sync.ts +79 -137
  112. package/src/utils/output.ts +450 -0
  113. package/src/utils/repo-factory.ts +13 -31
  114. package/src/utils/string-similarity.ts +54 -0
  115. package/src/utils/trace.ts +70 -0
  116. package/test/integration/exclude-patterns.test.ts +6 -15
  117. package/test/integration/fuzzer.test.ts +308 -391
  118. package/test/integration/init-sync.test.ts +89 -0
  119. package/test/integration/sync-deletion.test.ts +2 -61
  120. package/test/integration/sync-flow.test.ts +4 -24
  121. package/test/jest.setup.ts +34 -0
  122. package/test/unit/deletion-behavior.test.ts +3 -14
  123. package/test/unit/enhanced-mime-detection.test.ts +0 -22
  124. package/test/unit/snapshot.test.ts +2 -29
  125. package/test/unit/sync-convergence.test.ts +3 -198
  126. package/test/unit/sync-timing.test.ts +0 -44
  127. package/test/unit/utils.test.ts +0 -2
  128. package/tsconfig.json +3 -3
  129. package/dist/browser/browser-sync-engine.d.ts +0 -64
  130. package/dist/browser/browser-sync-engine.d.ts.map +0 -1
  131. package/dist/browser/browser-sync-engine.js +0 -303
  132. package/dist/browser/browser-sync-engine.js.map +0 -1
  133. package/dist/browser/filesystem-adapter.d.ts +0 -84
  134. package/dist/browser/filesystem-adapter.d.ts.map +0 -1
  135. package/dist/browser/filesystem-adapter.js +0 -413
  136. package/dist/browser/filesystem-adapter.js.map +0 -1
  137. package/dist/browser/index.d.ts +0 -36
  138. package/dist/browser/index.d.ts.map +0 -1
  139. package/dist/browser/index.js +0 -90
  140. package/dist/browser/index.js.map +0 -1
  141. package/dist/browser/types.d.ts +0 -70
  142. package/dist/browser/types.d.ts.map +0 -1
  143. package/dist/browser/types.js +0 -6
  144. package/dist/browser/types.js.map +0 -1
  145. package/dist/cli/commands.d.ts +0 -77
  146. package/dist/cli/commands.d.ts.map +0 -1
  147. package/dist/cli/commands.js +0 -904
  148. package/dist/cli/commands.js.map +0 -1
  149. package/dist/cli/index.d.ts +0 -2
  150. package/dist/cli/index.d.ts.map +0 -1
  151. package/dist/cli/index.js +0 -19
  152. package/dist/cli/index.js.map +0 -1
  153. package/dist/config/index.d.ts.map +0 -1
  154. package/dist/config/index.js.map +0 -1
  155. package/dist/core/isomorphic-snapshot.d.ts +0 -58
  156. package/dist/core/isomorphic-snapshot.d.ts.map +0 -1
  157. package/dist/core/isomorphic-snapshot.js +0 -204
  158. package/dist/core/isomorphic-snapshot.js.map +0 -1
  159. package/dist/platform/browser-filesystem.d.ts +0 -26
  160. package/dist/platform/browser-filesystem.d.ts.map +0 -1
  161. package/dist/platform/browser-filesystem.js +0 -91
  162. package/dist/platform/browser-filesystem.js.map +0 -1
  163. package/dist/platform/filesystem.d.ts +0 -29
  164. package/dist/platform/filesystem.d.ts.map +0 -1
  165. package/dist/platform/filesystem.js +0 -65
  166. package/dist/platform/filesystem.js.map +0 -1
  167. package/dist/platform/node-filesystem.d.ts +0 -21
  168. package/dist/platform/node-filesystem.d.ts.map +0 -1
  169. package/dist/platform/node-filesystem.js +0 -93
  170. package/dist/platform/node-filesystem.js.map +0 -1
  171. package/dist/utils/content-similarity.d.ts +0 -53
  172. package/dist/utils/content-similarity.d.ts.map +0 -1
  173. package/dist/utils/content-similarity.js +0 -155
  174. package/dist/utils/content-similarity.js.map +0 -1
  175. package/dist/utils/fs-browser.d.ts +0 -57
  176. package/dist/utils/fs-browser.d.ts.map +0 -1
  177. package/dist/utils/fs-browser.js +0 -311
  178. package/dist/utils/fs-browser.js.map +0 -1
  179. package/dist/utils/fs-node.d.ts +0 -53
  180. package/dist/utils/fs-node.d.ts.map +0 -1
  181. package/dist/utils/fs-node.js +0 -220
  182. package/dist/utils/fs-node.js.map +0 -1
  183. package/dist/utils/isomorphic.d.ts +0 -29
  184. package/dist/utils/isomorphic.d.ts.map +0 -1
  185. package/dist/utils/isomorphic.js +0 -139
  186. package/dist/utils/isomorphic.js.map +0 -1
  187. package/dist/utils/pure.d.ts +0 -25
  188. package/dist/utils/pure.d.ts.map +0 -1
  189. package/dist/utils/pure.js +0 -112
  190. package/dist/utils/pure.js.map +0 -1
  191. package/src/cli/commands.ts +0 -1207
  192. package/src/cli/index.ts +0 -2
  193. package/src/utils/content-similarity.ts +0 -194
  194. package/test/README-TESTING-GAPS.md +0 -174
  195. package/test/unit/content-similarity.test.ts +0 -236
@@ -2,56 +2,38 @@ import { Repo, StorageId } from "@automerge/automerge-repo";
2
2
  import { NodeFSStorageAdapter } from "@automerge/automerge-repo-storage-nodefs";
3
3
  import { BrowserWebSocketClientAdapter } from "@automerge/automerge-repo-network-websocket";
4
4
  import * as path from "path";
5
- import chalk from "chalk";
6
- import { ConfigManager } from "../config";
7
-
8
- export interface RepoFactoryOptions {
9
- enableNetwork?: boolean;
10
- syncServer?: string;
11
- syncServerStorageId?: string;
12
- }
5
+ import { DirectoryConfig } from "../types";
13
6
 
14
7
  /**
15
8
  * Create an Automerge repository with configuration-based setup
16
9
  */
17
10
  export async function createRepo(
18
11
  workingDir: string,
19
- options: RepoFactoryOptions = {}
12
+ config: DirectoryConfig
20
13
  ): Promise<Repo> {
21
- const configManager = new ConfigManager(workingDir);
22
- const config = await configManager.getMerged();
23
-
24
14
  const syncToolDir = path.join(workingDir, ".pushwork");
25
15
  const storage = new NodeFSStorageAdapter(path.join(syncToolDir, "automerge"));
26
16
 
27
17
  const repoConfig: any = { storage };
28
18
 
29
- // Determine network settings - options override config
30
- const enableNetwork = options.enableNetwork ?? true;
31
- const syncServer = options.syncServer ?? config.sync_server;
32
- const syncServerStorageId =
33
- options.syncServerStorageId ?? config.sync_server_storage_id;
34
-
35
- // Add network adapter only if explicitly enabled and sync server is configured
36
- if (enableNetwork && syncServer) {
37
- const networkAdapter = new BrowserWebSocketClientAdapter(syncServer);
19
+ // Add network adapter only if sync is enabled and server is configured
20
+ if (config.sync_enabled && config.sync_server) {
21
+ const networkAdapter = new BrowserWebSocketClientAdapter(
22
+ config.sync_server
23
+ );
38
24
  repoConfig.network = [networkAdapter];
39
25
  repoConfig.enableRemoteHeadsGossiping = true;
40
- console.log(chalk.gray(` ✓ Network sync enabled: ${syncServer}`));
41
- } else {
42
- console.log(chalk.gray(" ✓ Local-only mode (network sync disabled)"));
43
26
  }
44
27
 
45
28
  const repo = new Repo(repoConfig);
46
29
 
47
30
  // Subscribe to the sync server storage for network sync
48
- if (enableNetwork && syncServer && syncServerStorageId) {
49
- repo.subscribeToRemotes([syncServerStorageId as StorageId]);
50
- console.log(
51
- chalk.gray(
52
- ` Subscribed to sync server storage: ${syncServerStorageId}`
53
- )
54
- );
31
+ if (
32
+ config.sync_enabled &&
33
+ config.sync_server &&
34
+ config.sync_server_storage_id
35
+ ) {
36
+ repo.subscribeToRemotes([config.sync_server_storage_id as StorageId]);
55
37
  }
56
38
 
57
39
  return repo;
@@ -0,0 +1,54 @@
1
+ /* Based on the Sørensen–Dice coefficient, code from https://github.com/stephenjjbrown/string-similarity-js */
2
+
3
+ /**
4
+
5
+ * Calculate similarity between two strings
6
+
7
+ * @param {string} str1 First string to match
8
+ * @param {string} str2 Second string to match
9
+ * @param {number} [substringLength=2] Optional. Length of substring to be used in calculating similarity. Default 2.
10
+ * @param {boolean} [caseSensitive=false] Optional. Whether you want to consider case in string matching. Default false;
11
+
12
+ * @returns Number between 0 and 1, with 0 being a low match score.
13
+
14
+ */
15
+
16
+ export const stringSimilarity = (
17
+ str1: string,
18
+ str2: string,
19
+ substringLength: number = 2,
20
+ caseSensitive: boolean = false
21
+ ) => {
22
+ if (str1 === str2) return 1;
23
+ if (!caseSensitive) {
24
+ str1 = str1.toLowerCase();
25
+
26
+ str2 = str2.toLowerCase();
27
+ }
28
+
29
+ if (str1.length < substringLength || str2.length < substringLength) return 0;
30
+
31
+ const map = new Map();
32
+
33
+ for (let i = 0; i < str1.length - (substringLength - 1); i++) {
34
+ const substr1 = str1.substring(i, i + substringLength);
35
+
36
+ map.set(substr1, map.has(substr1) ? map.get(substr1) + 1 : 1);
37
+ }
38
+
39
+ let match = 0;
40
+
41
+ for (let j = 0; j < str2.length - (substringLength - 1); j++) {
42
+ const substr2 = str2.substring(j, j + substringLength);
43
+
44
+ const count = map.has(substr2) ? map.get(substr2) : 0;
45
+
46
+ if (count > 0) {
47
+ map.set(substr2, count - 1);
48
+
49
+ match++;
50
+ }
51
+ }
52
+
53
+ return (match * 2) / (str1.length + str2.length - (substringLength - 1) * 2);
54
+ };
@@ -0,0 +1,70 @@
1
+ import { out } from "./output";
2
+
3
+ /**
4
+ * Global tracing state
5
+ */
6
+ let tracingEnabled = false;
7
+
8
+ /**
9
+ * Enable or disable tracing
10
+ */
11
+ export function setTracingEnabled(enabled: boolean): void {
12
+ tracingEnabled = enabled;
13
+ }
14
+
15
+ /**
16
+ * Check if tracing is enabled
17
+ */
18
+ export function isTracingEnabled(): boolean {
19
+ return tracingEnabled;
20
+ }
21
+
22
+ /**
23
+ * Trace a span of work by outputting to console
24
+ * Works for both sync and async functions
25
+ * Only outputs if tracing is enabled
26
+ *
27
+ * Usage:
28
+ * await span("operation", async () => { ... })
29
+ * span("operation", () => { ... })
30
+ */
31
+ export function span<T>(
32
+ name: string,
33
+ fn: () => T | Promise<T>
34
+ ): T | Promise<T> {
35
+ if (!tracingEnabled) {
36
+ return fn();
37
+ }
38
+
39
+ const start = performance.now();
40
+ const result = fn();
41
+
42
+ // Check if it's a promise (async)
43
+ if (result instanceof Promise) {
44
+ return result.then((value) => {
45
+ const duration = performance.now() - start;
46
+ out.taskLine(`${name} (${formatDuration(duration)})`, true);
47
+ return value;
48
+ }) as T;
49
+ }
50
+
51
+ // Sync case
52
+ const duration = performance.now() - start;
53
+ out.taskLine(`${name} (${formatDuration(duration)})`, true);
54
+ return result;
55
+ }
56
+
57
+ /**
58
+ * Format duration for display
59
+ */
60
+ function formatDuration(ms: number): string {
61
+ if (ms < 1) {
62
+ return `${ms.toFixed(2)}ms`;
63
+ } else if (ms < 1000) {
64
+ return `${Math.round(ms)}ms`;
65
+ } else if (ms < 2000) {
66
+ return `${(ms / 1000).toFixed(2)}s`;
67
+ } else {
68
+ return `${(ms / 1000).toFixed(1)}s`;
69
+ }
70
+ }
@@ -1,7 +1,7 @@
1
1
  import * as path from "path";
2
2
  import * as fs from "fs/promises";
3
3
  import { tmpdir } from "os";
4
- import { ConfigManager } from "../../src/config";
4
+ import { ConfigManager } from "../../src/core";
5
5
  import { DirectoryConfig } from "../../src/types";
6
6
  import {
7
7
  ensureDirectoryExists,
@@ -105,18 +105,9 @@ describe("Exclude Patterns", () => {
105
105
  const localConfig: DirectoryConfig = {
106
106
  sync_server: "wss://test.server.com",
107
107
  sync_enabled: true,
108
- defaults: {
109
- exclude_patterns: [".git", "*.tmp", ".pushwork", "*.env"],
110
- large_file_threshold: "100MB",
111
- },
112
- diff: {
113
- show_binary: false,
114
- },
108
+ exclude_patterns: [".git", "*.tmp", ".pushwork", "*.env"],
115
109
  sync: {
116
110
  move_detection_threshold: 0.8,
117
- prompt_threshold: 0.5,
118
- auto_sync: false,
119
- parallel_operations: 4,
120
111
  },
121
112
  };
122
113
  await configManager.save(localConfig);
@@ -125,9 +116,9 @@ describe("Exclude Patterns", () => {
125
116
  const mergedConfig = await configManager.getMerged();
126
117
 
127
118
  // Verify .pushwork is in the exclude patterns
128
- expect(mergedConfig.defaults.exclude_patterns).toContain(".pushwork");
129
- expect(mergedConfig.defaults.exclude_patterns).toContain("*.env");
130
- expect(mergedConfig.defaults.exclude_patterns).toContain(".git");
119
+ expect(mergedConfig.exclude_patterns).toContain(".pushwork");
120
+ expect(mergedConfig.exclude_patterns).toContain("*.env");
121
+ expect(mergedConfig.exclude_patterns).toContain(".git");
131
122
 
132
123
  // Create test files
133
124
  await writeFileContent(path.join(tmpDir, "include.txt"), "include me");
@@ -141,7 +132,7 @@ describe("Exclude Patterns", () => {
141
132
  const entries = await listDirectory(
142
133
  tmpDir,
143
134
  true,
144
- mergedConfig.defaults.exclude_patterns
135
+ mergedConfig.exclude_patterns
145
136
  );
146
137
  const filePaths = entries.map((entry) => path.relative(tmpDir, entry.path));
147
138