@sylphx/flow 1.0.2 → 1.0.4

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 (229) hide show
  1. package/CHANGELOG.md +12 -0
  2. package/package.json +10 -9
  3. package/src/commands/codebase-command.ts +168 -0
  4. package/src/commands/flow-command.ts +1137 -0
  5. package/src/commands/flow-orchestrator.ts +296 -0
  6. package/src/commands/hook-command.ts +444 -0
  7. package/src/commands/init-command.ts +92 -0
  8. package/src/commands/init-core.ts +322 -0
  9. package/src/commands/knowledge-command.ts +161 -0
  10. package/src/commands/run-command.ts +120 -0
  11. package/src/components/benchmark-monitor.tsx +331 -0
  12. package/src/components/reindex-progress.tsx +261 -0
  13. package/src/composables/functional/index.ts +14 -0
  14. package/src/composables/functional/useEnvironment.ts +171 -0
  15. package/src/composables/functional/useFileSystem.ts +139 -0
  16. package/src/composables/index.ts +5 -0
  17. package/src/composables/useEnv.ts +13 -0
  18. package/src/composables/useRuntimeConfig.ts +27 -0
  19. package/src/composables/useTargetConfig.ts +45 -0
  20. package/src/config/ai-config.ts +376 -0
  21. package/src/config/constants.ts +35 -0
  22. package/src/config/index.ts +27 -0
  23. package/src/config/rules.ts +43 -0
  24. package/src/config/servers.ts +371 -0
  25. package/src/config/targets.ts +126 -0
  26. package/src/core/agent-loader.ts +141 -0
  27. package/src/core/agent-manager.ts +174 -0
  28. package/src/core/ai-sdk.ts +603 -0
  29. package/src/core/app-factory.ts +381 -0
  30. package/src/core/builtin-agents.ts +9 -0
  31. package/src/core/command-system.ts +550 -0
  32. package/src/core/config-system.ts +550 -0
  33. package/src/core/connection-pool.ts +390 -0
  34. package/src/core/di-container.ts +155 -0
  35. package/src/core/error-handling.ts +519 -0
  36. package/src/core/formatting/bytes.test.ts +115 -0
  37. package/src/core/formatting/bytes.ts +64 -0
  38. package/src/core/functional/async.ts +313 -0
  39. package/src/core/functional/either.ts +109 -0
  40. package/src/core/functional/error-handler.ts +135 -0
  41. package/src/core/functional/error-types.ts +311 -0
  42. package/src/core/functional/index.ts +19 -0
  43. package/src/core/functional/option.ts +142 -0
  44. package/src/core/functional/pipe.ts +189 -0
  45. package/src/core/functional/result.ts +204 -0
  46. package/src/core/functional/validation.ts +138 -0
  47. package/src/core/headless-display.ts +96 -0
  48. package/src/core/index.ts +6 -0
  49. package/src/core/installers/file-installer.ts +303 -0
  50. package/src/core/installers/mcp-installer.ts +213 -0
  51. package/src/core/interfaces/index.ts +22 -0
  52. package/src/core/interfaces/repository.interface.ts +91 -0
  53. package/src/core/interfaces/service.interface.ts +133 -0
  54. package/src/core/interfaces.ts +129 -0
  55. package/src/core/loop-controller.ts +200 -0
  56. package/src/core/result.ts +351 -0
  57. package/src/core/rule-loader.ts +147 -0
  58. package/src/core/rule-manager.ts +240 -0
  59. package/src/core/service-config.ts +252 -0
  60. package/src/core/session-service.ts +121 -0
  61. package/src/core/state-detector.ts +393 -0
  62. package/src/core/storage-factory.ts +115 -0
  63. package/src/core/stream-handler.ts +288 -0
  64. package/src/core/target-manager.ts +161 -0
  65. package/src/core/type-utils.ts +427 -0
  66. package/src/core/unified-storage.ts +456 -0
  67. package/src/core/upgrade-manager.ts +300 -0
  68. package/src/core/validation/limit.test.ts +155 -0
  69. package/src/core/validation/limit.ts +46 -0
  70. package/src/core/validation/query.test.ts +44 -0
  71. package/src/core/validation/query.ts +20 -0
  72. package/src/db/auto-migrate.ts +322 -0
  73. package/src/db/base-database-client.ts +144 -0
  74. package/src/db/cache-db.ts +218 -0
  75. package/src/db/cache-schema.ts +75 -0
  76. package/src/db/database.ts +70 -0
  77. package/src/db/index.ts +252 -0
  78. package/src/db/memory-db.ts +153 -0
  79. package/src/db/memory-schema.ts +29 -0
  80. package/src/db/schema.ts +289 -0
  81. package/src/db/session-repository.ts +733 -0
  82. package/src/domains/codebase/index.ts +5 -0
  83. package/src/domains/codebase/tools.ts +139 -0
  84. package/src/domains/index.ts +8 -0
  85. package/src/domains/knowledge/index.ts +10 -0
  86. package/src/domains/knowledge/resources.ts +537 -0
  87. package/src/domains/knowledge/tools.ts +174 -0
  88. package/src/domains/utilities/index.ts +6 -0
  89. package/src/domains/utilities/time/index.ts +5 -0
  90. package/src/domains/utilities/time/tools.ts +291 -0
  91. package/src/index.ts +211 -0
  92. package/src/services/agent-service.ts +273 -0
  93. package/src/services/claude-config-service.ts +252 -0
  94. package/src/services/config-service.ts +258 -0
  95. package/src/services/evaluation-service.ts +271 -0
  96. package/src/services/functional/evaluation-logic.ts +296 -0
  97. package/src/services/functional/file-processor.ts +273 -0
  98. package/src/services/functional/index.ts +12 -0
  99. package/src/services/index.ts +13 -0
  100. package/src/services/mcp-service.ts +432 -0
  101. package/src/services/memory.service.ts +476 -0
  102. package/src/services/search/base-indexer.ts +156 -0
  103. package/src/services/search/codebase-indexer-types.ts +38 -0
  104. package/src/services/search/codebase-indexer.ts +647 -0
  105. package/src/services/search/embeddings-provider.ts +455 -0
  106. package/src/services/search/embeddings.ts +316 -0
  107. package/src/services/search/functional-indexer.ts +323 -0
  108. package/src/services/search/index.ts +27 -0
  109. package/src/services/search/indexer.ts +380 -0
  110. package/src/services/search/knowledge-indexer.ts +422 -0
  111. package/src/services/search/semantic-search.ts +244 -0
  112. package/src/services/search/tfidf.ts +559 -0
  113. package/src/services/search/unified-search-service.ts +888 -0
  114. package/src/services/smart-config-service.ts +385 -0
  115. package/src/services/storage/cache-storage.ts +487 -0
  116. package/src/services/storage/drizzle-storage.ts +581 -0
  117. package/src/services/storage/index.ts +15 -0
  118. package/src/services/storage/lancedb-vector-storage.ts +494 -0
  119. package/src/services/storage/memory-storage.ts +268 -0
  120. package/src/services/storage/separated-storage.ts +467 -0
  121. package/src/services/storage/vector-storage.ts +13 -0
  122. package/src/shared/agents/index.ts +63 -0
  123. package/src/shared/files/index.ts +99 -0
  124. package/src/shared/index.ts +32 -0
  125. package/src/shared/logging/index.ts +24 -0
  126. package/src/shared/processing/index.ts +153 -0
  127. package/src/shared/types/index.ts +25 -0
  128. package/src/targets/claude-code.ts +574 -0
  129. package/src/targets/functional/claude-code-logic.ts +185 -0
  130. package/src/targets/functional/index.ts +6 -0
  131. package/src/targets/opencode.ts +529 -0
  132. package/src/types/agent.types.ts +32 -0
  133. package/src/types/api/batch.ts +108 -0
  134. package/src/types/api/errors.ts +118 -0
  135. package/src/types/api/index.ts +55 -0
  136. package/src/types/api/requests.ts +76 -0
  137. package/src/types/api/responses.ts +180 -0
  138. package/src/types/api/websockets.ts +85 -0
  139. package/src/types/api.types.ts +9 -0
  140. package/src/types/benchmark.ts +49 -0
  141. package/src/types/cli.types.ts +87 -0
  142. package/src/types/common.types.ts +35 -0
  143. package/src/types/database.types.ts +510 -0
  144. package/src/types/mcp-config.types.ts +448 -0
  145. package/src/types/mcp.types.ts +69 -0
  146. package/src/types/memory-types.ts +63 -0
  147. package/src/types/provider.types.ts +28 -0
  148. package/src/types/rule.types.ts +24 -0
  149. package/src/types/session.types.ts +214 -0
  150. package/src/types/target-config.types.ts +295 -0
  151. package/src/types/target.types.ts +140 -0
  152. package/src/types/todo.types.ts +25 -0
  153. package/src/types.ts +40 -0
  154. package/src/utils/advanced-tokenizer.ts +191 -0
  155. package/src/utils/agent-enhancer.ts +114 -0
  156. package/src/utils/ai-model-fetcher.ts +19 -0
  157. package/src/utils/async-file-operations.ts +516 -0
  158. package/src/utils/audio-player.ts +345 -0
  159. package/src/utils/cli-output.ts +266 -0
  160. package/src/utils/codebase-helpers.ts +211 -0
  161. package/src/utils/console-ui.ts +79 -0
  162. package/src/utils/database-errors.ts +140 -0
  163. package/src/utils/debug-logger.ts +49 -0
  164. package/src/utils/error-handler.ts +53 -0
  165. package/src/utils/file-operations.ts +310 -0
  166. package/src/utils/file-scanner.ts +259 -0
  167. package/src/utils/functional/array.ts +355 -0
  168. package/src/utils/functional/index.ts +15 -0
  169. package/src/utils/functional/object.ts +279 -0
  170. package/src/utils/functional/string.ts +281 -0
  171. package/src/utils/functional.ts +543 -0
  172. package/src/utils/help.ts +20 -0
  173. package/src/utils/immutable-cache.ts +106 -0
  174. package/src/utils/index.ts +78 -0
  175. package/src/utils/jsonc.ts +158 -0
  176. package/src/utils/logger.ts +396 -0
  177. package/src/utils/mcp-config.ts +249 -0
  178. package/src/utils/memory-tui.ts +414 -0
  179. package/src/utils/models-dev.ts +91 -0
  180. package/src/utils/notifications.ts +169 -0
  181. package/src/utils/object-utils.ts +51 -0
  182. package/src/utils/parallel-operations.ts +487 -0
  183. package/src/utils/paths.ts +143 -0
  184. package/src/utils/process-manager.ts +155 -0
  185. package/src/utils/prompts.ts +120 -0
  186. package/src/utils/search-tool-builder.ts +214 -0
  187. package/src/utils/secret-utils.ts +179 -0
  188. package/src/utils/security.ts +537 -0
  189. package/src/utils/session-manager.ts +168 -0
  190. package/src/utils/session-title.ts +87 -0
  191. package/src/utils/settings.ts +182 -0
  192. package/src/utils/simplified-errors.ts +410 -0
  193. package/src/utils/sync-utils.ts +159 -0
  194. package/src/utils/target-config.ts +570 -0
  195. package/src/utils/target-utils.ts +394 -0
  196. package/src/utils/template-engine.ts +94 -0
  197. package/src/utils/test-audio.ts +71 -0
  198. package/src/utils/todo-context.ts +46 -0
  199. package/src/utils/token-counter.ts +288 -0
  200. package/dist/index.d.ts +0 -10
  201. package/dist/index.js +0 -59554
  202. package/dist/lancedb.linux-x64-gnu-b7f0jgsz.node +0 -0
  203. package/dist/lancedb.linux-x64-musl-tgcv22rx.node +0 -0
  204. package/dist/shared/chunk-25dwp0dp.js +0 -89
  205. package/dist/shared/chunk-3pjb6063.js +0 -208
  206. package/dist/shared/chunk-4d6ydpw7.js +0 -2854
  207. package/dist/shared/chunk-4wjcadjk.js +0 -225
  208. package/dist/shared/chunk-5j4w74t6.js +0 -30
  209. package/dist/shared/chunk-5j8m3dh3.js +0 -58
  210. package/dist/shared/chunk-5thh3qem.js +0 -91
  211. package/dist/shared/chunk-6g9xy73m.js +0 -252
  212. package/dist/shared/chunk-7eq34c42.js +0 -23
  213. package/dist/shared/chunk-c2gwgx3r.js +0 -115
  214. package/dist/shared/chunk-cjd3mk4c.js +0 -1320
  215. package/dist/shared/chunk-g5cv6703.js +0 -368
  216. package/dist/shared/chunk-hpkhykhq.js +0 -574
  217. package/dist/shared/chunk-m2322pdk.js +0 -122
  218. package/dist/shared/chunk-nd5fdvaq.js +0 -26
  219. package/dist/shared/chunk-pgd3m6zf.js +0 -108
  220. package/dist/shared/chunk-qk8n91hw.js +0 -494
  221. package/dist/shared/chunk-rkkn8szp.js +0 -16855
  222. package/dist/shared/chunk-t16rfxh0.js +0 -61
  223. package/dist/shared/chunk-t4fbfa5v.js +0 -19
  224. package/dist/shared/chunk-t77h86w6.js +0 -276
  225. package/dist/shared/chunk-v0ez4aef.js +0 -71
  226. package/dist/shared/chunk-v29j2r3s.js +0 -32051
  227. package/dist/shared/chunk-vfbc6ew5.js +0 -765
  228. package/dist/shared/chunk-vmeqwm1c.js +0 -204
  229. package/dist/shared/chunk-x66eh37x.js +0 -137
@@ -0,0 +1,543 @@
1
+ /**
2
+ * Functional Programming Utilities
3
+ * Core utilities for functional composition and transformation
4
+ *
5
+ * Principles:
6
+ * - Pure functions (no side effects)
7
+ * - Immutable data
8
+ * - Function composition
9
+ * - Point-free style support
10
+ */
11
+
12
+ // ============================================================================
13
+ // FUNCTION COMPOSITION
14
+ // ============================================================================
15
+
16
+ /**
17
+ * Pipe - Left-to-right function composition
18
+ * Applies functions sequentially from left to right
19
+ *
20
+ * @example
21
+ * const result = pipe(
22
+ * 5,
23
+ * x => x * 2, // 10
24
+ * x => x + 3, // 13
25
+ * x => x.toString() // "13"
26
+ * );
27
+ */
28
+ export const pipe = <T>(value: T, ...fns: Array<(arg: any) => any>): any =>
29
+ fns.reduce((acc, fn) => fn(acc), value);
30
+
31
+ /**
32
+ * Compose - Right-to-left function composition
33
+ * Applies functions sequentially from right to left
34
+ *
35
+ * @example
36
+ * const addThenMultiply = compose(
37
+ * (x: number) => x * 2, // Applied second
38
+ * (x: number) => x + 3 // Applied first
39
+ * );
40
+ * addThenMultiply(5); // (5 + 3) * 2 = 16
41
+ */
42
+ export const compose =
43
+ <T>(...fns: Array<(arg: any) => any>) =>
44
+ (value: T): any =>
45
+ fns.reduceRight((acc, fn) => fn(acc), value);
46
+
47
+ /**
48
+ * Flow - Alias for pipe (for function composition without initial value)
49
+ *
50
+ * @example
51
+ * const transform = flow(
52
+ * (x: number) => x * 2,
53
+ * (x: number) => x + 3,
54
+ * (x: number) => x.toString()
55
+ * );
56
+ * transform(5); // "13"
57
+ */
58
+ export const flow =
59
+ <A, B>(...fns: Array<(arg: any) => any>) =>
60
+ (value: A): B =>
61
+ pipe(value, ...fns);
62
+
63
+ // ============================================================================
64
+ // CURRYING & PARTIAL APPLICATION
65
+ // ============================================================================
66
+
67
+ /**
68
+ * Curry - Transform multi-argument function to curried form
69
+ *
70
+ * @example
71
+ * const add = (a: number, b: number) => a + b;
72
+ * const curriedAdd = curry(add);
73
+ * curriedAdd(5)(3); // 8
74
+ */
75
+ export const curry =
76
+ <A, B, C>(fn: (a: A, b: B) => C) =>
77
+ (a: A) =>
78
+ (b: B): C =>
79
+ fn(a, b);
80
+
81
+ /**
82
+ * Curry3 - Curry function with 3 arguments
83
+ */
84
+ export const curry3 =
85
+ <A, B, C, D>(fn: (a: A, b: B, c: C) => D) =>
86
+ (a: A) =>
87
+ (b: B) =>
88
+ (c: C): D =>
89
+ fn(a, b, c);
90
+
91
+ /**
92
+ * Partial - Partial application of function arguments
93
+ *
94
+ * @example
95
+ * const add = (a: number, b: number, c: number) => a + b + c;
96
+ * const add5 = partial(add, 5);
97
+ * add5(3, 2); // 10
98
+ */
99
+ export const partial =
100
+ <A extends any[], R>(fn: (...args: A) => R, ...partialArgs: Partial<A>) =>
101
+ (...remainingArgs: any[]): R =>
102
+ fn(...([...partialArgs, ...remainingArgs] as A));
103
+
104
+ // ============================================================================
105
+ // ARRAY TRANSFORMATIONS (Point-free style)
106
+ // ============================================================================
107
+
108
+ /**
109
+ * Map - Transform array elements
110
+ *
111
+ * @example
112
+ * pipe(
113
+ * [1, 2, 3],
114
+ * map((x: number) => x * 2)
115
+ * ); // [2, 4, 6]
116
+ */
117
+ export const map =
118
+ <A, B>(fn: (item: A, index: number) => B) =>
119
+ (items: readonly A[]): B[] =>
120
+ items.map(fn);
121
+
122
+ /**
123
+ * Filter - Keep elements matching predicate
124
+ *
125
+ * @example
126
+ * pipe(
127
+ * [1, 2, 3, 4],
128
+ * filter((x: number) => x > 2)
129
+ * ); // [3, 4]
130
+ */
131
+ export const filter =
132
+ <A>(predicate: (item: A, index: number) => boolean) =>
133
+ (items: readonly A[]): A[] =>
134
+ items.filter(predicate);
135
+
136
+ /**
137
+ * Reduce - Accumulate array to single value
138
+ *
139
+ * @example
140
+ * pipe(
141
+ * [1, 2, 3, 4],
142
+ * reduce((acc: number, x: number) => acc + x, 0)
143
+ * ); // 10
144
+ */
145
+ export const reduce =
146
+ <A, B>(fn: (acc: B, item: A, index: number) => B, initial: B) =>
147
+ (items: readonly A[]): B =>
148
+ items.reduce(fn, initial);
149
+
150
+ /**
151
+ * FlatMap - Map then flatten
152
+ *
153
+ * @example
154
+ * pipe(
155
+ * [1, 2, 3],
156
+ * flatMap((x: number) => [x, x * 2])
157
+ * ); // [1, 2, 2, 4, 3, 6]
158
+ */
159
+ export const flatMap =
160
+ <A, B>(fn: (item: A, index: number) => B[]) =>
161
+ (items: readonly A[]): B[] =>
162
+ items.flatMap(fn);
163
+
164
+ /**
165
+ * Sort - Sort array (returns new array)
166
+ *
167
+ * @example
168
+ * pipe(
169
+ * [3, 1, 2],
170
+ * sort((a: number, b: number) => a - b)
171
+ * ); // [1, 2, 3]
172
+ */
173
+ export const sort =
174
+ <A>(compareFn: (a: A, b: A) => number) =>
175
+ (items: readonly A[]): A[] =>
176
+ [...items].sort(compareFn);
177
+
178
+ /**
179
+ * SortBy - Sort by property
180
+ *
181
+ * @example
182
+ * pipe(
183
+ * [{ age: 30 }, { age: 20 }, { age: 25 }],
184
+ * sortBy('age')
185
+ * ); // [{ age: 20 }, { age: 25 }, { age: 30 }]
186
+ */
187
+ export const sortBy =
188
+ <A>(key: keyof A) =>
189
+ (items: readonly A[]): A[] =>
190
+ [...items].sort((a, b) => {
191
+ if (a[key] < b[key]) {
192
+ return -1;
193
+ }
194
+ if (a[key] > b[key]) {
195
+ return 1;
196
+ }
197
+ return 0;
198
+ });
199
+
200
+ /**
201
+ * Reverse - Reverse array (returns new array)
202
+ */
203
+ export const reverse = <A>(items: readonly A[]): A[] => [...items].reverse();
204
+
205
+ /**
206
+ * Take - Take first n elements
207
+ *
208
+ * @example
209
+ * pipe([1, 2, 3, 4, 5], take(3)); // [1, 2, 3]
210
+ */
211
+ export const take =
212
+ (n: number) =>
213
+ <A>(items: readonly A[]): A[] =>
214
+ items.slice(0, n);
215
+
216
+ /**
217
+ * Drop - Drop first n elements
218
+ *
219
+ * @example
220
+ * pipe([1, 2, 3, 4, 5], drop(2)); // [3, 4, 5]
221
+ */
222
+ export const drop =
223
+ (n: number) =>
224
+ <A>(items: readonly A[]): A[] =>
225
+ items.slice(n);
226
+
227
+ /**
228
+ * Unique - Remove duplicates
229
+ *
230
+ * @example
231
+ * pipe([1, 2, 2, 3, 3, 3], unique); // [1, 2, 3]
232
+ */
233
+ export const unique = <A>(items: readonly A[]): A[] => [...new Set(items)];
234
+
235
+ /**
236
+ * UniqueBy - Remove duplicates by key
237
+ *
238
+ * @example
239
+ * pipe(
240
+ * [{ id: 1 }, { id: 2 }, { id: 1 }],
241
+ * uniqueBy('id')
242
+ * ); // [{ id: 1 }, { id: 2 }]
243
+ */
244
+ export const uniqueBy =
245
+ <A>(key: keyof A) =>
246
+ (items: readonly A[]): A[] => {
247
+ const seen = new Set();
248
+ return items.filter((item) => {
249
+ const value = item[key];
250
+ if (seen.has(value)) {
251
+ return false;
252
+ }
253
+ seen.add(value);
254
+ return true;
255
+ });
256
+ };
257
+
258
+ /**
259
+ * Partition - Split array by predicate
260
+ *
261
+ * @example
262
+ * pipe(
263
+ * [1, 2, 3, 4, 5],
264
+ * partition((x: number) => x > 3)
265
+ * ); // [[4, 5], [1, 2, 3]]
266
+ */
267
+ export const partition =
268
+ <A>(predicate: (item: A) => boolean) =>
269
+ (items: readonly A[]): [A[], A[]] => {
270
+ const pass: A[] = [];
271
+ const fail: A[] = [];
272
+ for (const item of items) {
273
+ (predicate(item) ? pass : fail).push(item);
274
+ }
275
+ return [pass, fail];
276
+ };
277
+
278
+ /**
279
+ * GroupBy - Group items by key
280
+ *
281
+ * @example
282
+ * pipe(
283
+ * [{ type: 'a', val: 1 }, { type: 'b', val: 2 }, { type: 'a', val: 3 }],
284
+ * groupBy('type')
285
+ * ); // { a: [...], b: [...] }
286
+ */
287
+ export const groupBy =
288
+ <A>(key: keyof A) =>
289
+ (items: readonly A[]): Record<string, A[]> =>
290
+ items.reduce(
291
+ (acc, item) => {
292
+ const groupKey = String(item[key]);
293
+ if (!acc[groupKey]) {
294
+ acc[groupKey] = [];
295
+ }
296
+ acc[groupKey].push(item);
297
+ return acc;
298
+ },
299
+ {} as Record<string, A[]>
300
+ );
301
+
302
+ // ============================================================================
303
+ // ASYNC TRANSFORMATIONS
304
+ // ============================================================================
305
+
306
+ /**
307
+ * MapAsync - Map with async function
308
+ *
309
+ * @example
310
+ * await pipe(
311
+ * [1, 2, 3],
312
+ * mapAsync(async (x) => x * 2)
313
+ * ); // [2, 4, 6]
314
+ */
315
+ export const mapAsync =
316
+ <A, B>(fn: (item: A, index: number) => Promise<B>) =>
317
+ (items: readonly A[]): Promise<B[]> =>
318
+ Promise.all(items.map(fn));
319
+
320
+ /**
321
+ * FilterAsync - Filter with async predicate
322
+ */
323
+ export const filterAsync =
324
+ <A>(predicate: (item: A, index: number) => Promise<boolean>) =>
325
+ async (items: readonly A[]): Promise<A[]> => {
326
+ const results = await Promise.all(items.map(predicate));
327
+ return items.filter((_, i) => results[i]);
328
+ };
329
+
330
+ /**
331
+ * ReduceAsync - Reduce with async function
332
+ */
333
+ export const reduceAsync =
334
+ <A, B>(fn: (acc: B, item: A, index: number) => Promise<B>, initial: B) =>
335
+ async (items: readonly A[]): Promise<B> => {
336
+ let acc = initial;
337
+ for (let i = 0; i < items.length; i++) {
338
+ acc = await fn(acc, items[i], i);
339
+ }
340
+ return acc;
341
+ };
342
+
343
+ // ============================================================================
344
+ // SIDE EFFECTS & DEBUGGING
345
+ // ============================================================================
346
+
347
+ /**
348
+ * Tap - Execute side effect without changing value
349
+ *
350
+ * @example
351
+ * pipe(
352
+ * 5,
353
+ * x => x * 2,
354
+ * tap((x) => console.log('Debug:', x)), // Logs: Debug: 10
355
+ * x => x + 3
356
+ * ); // 13
357
+ */
358
+ export const tap =
359
+ <T>(fn: (value: T) => void) =>
360
+ (value: T): T => {
361
+ fn(value);
362
+ return value;
363
+ };
364
+
365
+ /**
366
+ * TapAsync - Execute async side effect
367
+ */
368
+ export const tapAsync =
369
+ <T>(fn: (value: T) => Promise<void>) =>
370
+ async (value: T): Promise<T> => {
371
+ await fn(value);
372
+ return value;
373
+ };
374
+
375
+ /**
376
+ * Trace - Log value with label
377
+ *
378
+ * @example
379
+ * pipe(
380
+ * 5,
381
+ * x => x * 2,
382
+ * trace('After multiply'), // Logs: "After multiply: 10"
383
+ * x => x + 3
384
+ * );
385
+ */
386
+ export const trace =
387
+ (label: string) =>
388
+ <T>(value: T): T => {
389
+ console.log(`${label}:`, value);
390
+ return value;
391
+ };
392
+
393
+ // ============================================================================
394
+ // ERROR HANDLING
395
+ // ============================================================================
396
+
397
+ /**
398
+ * Result type - Represents success or failure
399
+ */
400
+ export type Result<T, E = Error> = { ok: true; value: T } | { ok: false; error: E };
401
+
402
+ /**
403
+ * TryCatch - Convert exception to Result type
404
+ *
405
+ * @example
406
+ * const result = tryCatch(() => JSON.parse(input));
407
+ * if (result.ok) {
408
+ * console.log(result.value);
409
+ * } else {
410
+ * console.error(result.error);
411
+ * }
412
+ */
413
+ export const tryCatch = <T, E = Error>(fn: () => T): Result<T, E> => {
414
+ try {
415
+ return { ok: true, value: fn() };
416
+ } catch (error) {
417
+ return { ok: false, error: error as E };
418
+ }
419
+ };
420
+
421
+ /**
422
+ * TryCatchAsync - Async version of tryCatch
423
+ */
424
+ export const tryCatchAsync = async <T, E = Error>(fn: () => Promise<T>): Promise<Result<T, E>> => {
425
+ try {
426
+ return { ok: true, value: await fn() };
427
+ } catch (error) {
428
+ return { ok: false, error: error as E };
429
+ }
430
+ };
431
+
432
+ /**
433
+ * UnwrapResult - Extract value from Result or throw error
434
+ */
435
+ export const unwrapResult = <T, E>(result: Result<T, E>): T => {
436
+ if (result.ok) {
437
+ return result.value;
438
+ }
439
+ throw result.error;
440
+ };
441
+
442
+ /**
443
+ * MapResult - Transform Result value
444
+ */
445
+ export const mapResult =
446
+ <T, U, E>(fn: (value: T) => U) =>
447
+ (result: Result<T, E>): Result<U, E> => {
448
+ if (result.ok) {
449
+ return { ok: true, value: fn(result.value) };
450
+ }
451
+ return result;
452
+ };
453
+
454
+ // ============================================================================
455
+ // PREDICATES & LOGIC
456
+ // ============================================================================
457
+
458
+ /**
459
+ * Not - Negate predicate
460
+ */
461
+ export const not =
462
+ <A>(predicate: (item: A) => boolean) =>
463
+ (item: A): boolean =>
464
+ !predicate(item);
465
+
466
+ /**
467
+ * And - Combine predicates with AND
468
+ */
469
+ export const and =
470
+ <A>(...predicates: Array<(item: A) => boolean>) =>
471
+ (item: A): boolean =>
472
+ predicates.every((p) => p(item));
473
+
474
+ /**
475
+ * Or - Combine predicates with OR
476
+ */
477
+ export const or =
478
+ <A>(...predicates: Array<(item: A) => boolean>) =>
479
+ (item: A): boolean =>
480
+ predicates.some((p) => p(item));
481
+
482
+ // ============================================================================
483
+ // UTILITIES
484
+ // ============================================================================
485
+
486
+ /**
487
+ * Identity - Return value as-is
488
+ */
489
+ export const identity = <T>(value: T): T => value;
490
+
491
+ /**
492
+ * Constant - Always return same value
493
+ */
494
+ export const constant =
495
+ <T>(value: T) =>
496
+ (): T =>
497
+ value;
498
+
499
+ /**
500
+ * Noop - Do nothing
501
+ */
502
+ export const noop = (): void => {};
503
+
504
+ /**
505
+ * Prop - Extract property value
506
+ *
507
+ * @example
508
+ * pipe(
509
+ * [{ name: 'Alice' }, { name: 'Bob' }],
510
+ * map(prop('name'))
511
+ * ); // ['Alice', 'Bob']
512
+ */
513
+ export const prop =
514
+ <K extends string | number | symbol>(key: K) =>
515
+ <T extends Record<K, any>>(obj: T): T[K] =>
516
+ obj[key];
517
+
518
+ /**
519
+ * Pick - Pick properties from object
520
+ */
521
+ export const pick =
522
+ <T, K extends keyof T>(keys: K[]) =>
523
+ (obj: T): Pick<T, K> =>
524
+ keys.reduce(
525
+ (acc, key) => {
526
+ acc[key] = obj[key];
527
+ return acc;
528
+ },
529
+ {} as Pick<T, K>
530
+ );
531
+
532
+ /**
533
+ * Omit - Omit properties from object
534
+ */
535
+ export const omit =
536
+ <T, K extends keyof T>(keys: K[]) =>
537
+ (obj: T): Omit<T, K> => {
538
+ const result = { ...obj };
539
+ for (const key of keys) {
540
+ delete result[key];
541
+ }
542
+ return result;
543
+ };
@@ -0,0 +1,20 @@
1
+ export function showDefaultHelp(): void {
2
+ console.log('🚀 Sylphx Flow CLI - Legacy project initialization and flow management');
3
+ console.log('=========================================');
4
+ console.log('');
5
+ console.log('Available commands:');
6
+ console.log(' init Initialize project with Sylphx Flow');
7
+ console.log(' run Run workflows and flows');
8
+ console.log(' codebase Search and analyze codebase');
9
+ console.log(' knowledge Manage knowledge base');
10
+ console.log(' hook Load dynamic content for hooks');
11
+ console.log('');
12
+ console.log('Examples:');
13
+ console.log(' sylphx-flow init');
14
+ console.log(' sylphx-flow init --target claude-code');
15
+ console.log(' sylphx-flow run "your prompt"');
16
+ console.log(' sylphx-flow codebase search "function"');
17
+ console.log(' sylphx-flow knowledge search "React patterns"');
18
+ console.log('');
19
+ console.log('Run "sylphx-flow <command> --help" for more information about a command.');
20
+ }
@@ -0,0 +1,106 @@
1
+ /**
2
+ * Immutable Cache
3
+ * Functional cache abstraction that returns new state on mutations
4
+ */
5
+
6
+ export interface CacheState<K, V> {
7
+ readonly entries: ReadonlyMap<K, V>;
8
+ readonly size: number;
9
+ }
10
+
11
+ /**
12
+ * Create an empty cache state
13
+ */
14
+ export const createCache = <K, V>(): CacheState<K, V> => ({
15
+ entries: new Map(),
16
+ size: 0,
17
+ });
18
+
19
+ /**
20
+ * Set a value in the cache, returning new cache state
21
+ */
22
+ export const cacheSet = <K, V>(cache: CacheState<K, V>, key: K, value: V): CacheState<K, V> => {
23
+ const newEntries = new Map(cache.entries);
24
+ newEntries.set(key, value);
25
+ return {
26
+ entries: newEntries,
27
+ size: newEntries.size,
28
+ };
29
+ };
30
+
31
+ /**
32
+ * Get a value from the cache
33
+ */
34
+ export const cacheGet = <K, V>(cache: CacheState<K, V>, key: K): V | undefined => {
35
+ return cache.entries.get(key);
36
+ };
37
+
38
+ /**
39
+ * Delete a key from the cache, returning new cache state
40
+ */
41
+ export const cacheDelete = <K, V>(cache: CacheState<K, V>, key: K): CacheState<K, V> => {
42
+ const newEntries = new Map(cache.entries);
43
+ newEntries.delete(key);
44
+ return {
45
+ entries: newEntries,
46
+ size: newEntries.size,
47
+ };
48
+ };
49
+
50
+ /**
51
+ * Delete multiple keys matching a predicate, returning new cache state
52
+ */
53
+ export const cacheDeleteWhere = <K, V>(
54
+ cache: CacheState<K, V>,
55
+ predicate: (key: K, value: V) => boolean
56
+ ): CacheState<K, V> => {
57
+ const newEntries = new Map<K, V>();
58
+ for (const [key, value] of cache.entries) {
59
+ if (!predicate(key, value)) {
60
+ newEntries.set(key, value);
61
+ }
62
+ }
63
+ return {
64
+ entries: newEntries,
65
+ size: newEntries.size,
66
+ };
67
+ };
68
+
69
+ /**
70
+ * Clear all entries from the cache, returning new cache state
71
+ */
72
+ export const cacheClear = <K, V>(): CacheState<K, V> => createCache();
73
+
74
+ /**
75
+ * Get all keys from the cache
76
+ */
77
+ export const cacheKeys = <K, V>(cache: CacheState<K, V>): K[] => {
78
+ return Array.from(cache.entries.keys());
79
+ };
80
+
81
+ /**
82
+ * Enforce maximum cache size by removing oldest entries (FIFO)
83
+ * Returns new cache state
84
+ */
85
+ export const cacheEnforceLimit = <K, V>(
86
+ cache: CacheState<K, V>,
87
+ maxSize: number
88
+ ): CacheState<K, V> => {
89
+ if (cache.size <= maxSize) {
90
+ return cache;
91
+ }
92
+
93
+ const entriesToRemove = cache.size - maxSize;
94
+ const keys = Array.from(cache.entries.keys());
95
+ const keysToRemove = keys.slice(0, entriesToRemove);
96
+
97
+ const newEntries = new Map(cache.entries);
98
+ for (const key of keysToRemove) {
99
+ newEntries.delete(key);
100
+ }
101
+
102
+ return {
103
+ entries: newEntries,
104
+ size: newEntries.size,
105
+ };
106
+ };