@pithos/core 2.3.0 → 2.4.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 (99) hide show
  1. package/dist/.tsbuildinfo +1 -1
  2. package/dist/autocompletion.d.ts +129 -1
  3. package/dist/eidos/abstract-factory/abstract-factory.d.ts +125 -0
  4. package/dist/eidos/abstract-factory/abstract-factory.d.ts.map +1 -0
  5. package/dist/eidos/abstract-factory/abstract-factory.js +128 -0
  6. package/dist/eidos/abstract-factory/abstract-factory.js.map +1 -0
  7. package/dist/eidos/adapter/adapter.d.ts +97 -0
  8. package/dist/eidos/adapter/adapter.d.ts.map +1 -0
  9. package/dist/eidos/adapter/adapter.js +90 -0
  10. package/dist/eidos/adapter/adapter.js.map +1 -0
  11. package/dist/eidos/bridge/bridge.d.ts +81 -0
  12. package/dist/eidos/bridge/bridge.d.ts.map +1 -0
  13. package/dist/eidos/bridge/bridge.js +75 -0
  14. package/dist/eidos/bridge/bridge.js.map +1 -0
  15. package/dist/eidos/builder/builder.d.ts +181 -0
  16. package/dist/eidos/builder/builder.d.ts.map +1 -0
  17. package/dist/eidos/builder/builder.js +139 -0
  18. package/dist/eidos/builder/builder.js.map +1 -0
  19. package/dist/eidos/chain/chain.d.ts +99 -0
  20. package/dist/eidos/chain/chain.d.ts.map +1 -0
  21. package/dist/eidos/chain/chain.js +111 -0
  22. package/dist/eidos/chain/chain.js.map +1 -0
  23. package/dist/eidos/command/command.d.ts +267 -0
  24. package/dist/eidos/command/command.d.ts.map +1 -0
  25. package/dist/eidos/command/command.js +298 -0
  26. package/dist/eidos/command/command.js.map +1 -0
  27. package/dist/eidos/composite/composite.d.ts +168 -0
  28. package/dist/eidos/composite/composite.d.ts.map +1 -0
  29. package/dist/eidos/composite/composite.js +157 -0
  30. package/dist/eidos/composite/composite.js.map +1 -0
  31. package/dist/eidos/decorator/decorator.d.ts +138 -0
  32. package/dist/eidos/decorator/decorator.d.ts.map +1 -0
  33. package/dist/eidos/decorator/decorator.js +143 -0
  34. package/dist/eidos/decorator/decorator.js.map +1 -0
  35. package/dist/eidos/facade/facade.d.ts +61 -0
  36. package/dist/eidos/facade/facade.d.ts.map +1 -0
  37. package/dist/eidos/facade/facade.js +63 -0
  38. package/dist/eidos/facade/facade.js.map +1 -0
  39. package/dist/eidos/factory-method/factory-method.d.ts +76 -0
  40. package/dist/eidos/factory-method/factory-method.d.ts.map +1 -0
  41. package/dist/eidos/factory-method/factory-method.js +60 -0
  42. package/dist/eidos/factory-method/factory-method.js.map +1 -0
  43. package/dist/eidos/flyweight/flyweight.d.ts +40 -0
  44. package/dist/eidos/flyweight/flyweight.d.ts.map +1 -0
  45. package/dist/eidos/flyweight/flyweight.js +41 -0
  46. package/dist/eidos/flyweight/flyweight.js.map +1 -0
  47. package/dist/eidos/interpreter/interpreter.d.ts +82 -0
  48. package/dist/eidos/interpreter/interpreter.d.ts.map +1 -0
  49. package/dist/eidos/interpreter/interpreter.js +84 -0
  50. package/dist/eidos/interpreter/interpreter.js.map +1 -0
  51. package/dist/eidos/iterator/iterator.d.ts +164 -0
  52. package/dist/eidos/iterator/iterator.d.ts.map +1 -0
  53. package/dist/eidos/iterator/iterator.js +258 -0
  54. package/dist/eidos/iterator/iterator.js.map +1 -0
  55. package/dist/eidos/mediator/mediator.d.ts +102 -0
  56. package/dist/eidos/mediator/mediator.d.ts.map +1 -0
  57. package/dist/eidos/mediator/mediator.js +112 -0
  58. package/dist/eidos/mediator/mediator.js.map +1 -0
  59. package/dist/eidos/memento/memento.d.ts +103 -0
  60. package/dist/eidos/memento/memento.d.ts.map +1 -0
  61. package/dist/eidos/memento/memento.js +114 -0
  62. package/dist/eidos/memento/memento.js.map +1 -0
  63. package/dist/eidos/observer/observer.d.ts +96 -0
  64. package/dist/eidos/observer/observer.d.ts.map +1 -0
  65. package/dist/eidos/observer/observer.js +117 -0
  66. package/dist/eidos/observer/observer.js.map +1 -0
  67. package/dist/eidos/prototype/prototype.d.ts +32 -0
  68. package/dist/eidos/prototype/prototype.d.ts.map +1 -0
  69. package/dist/eidos/prototype/prototype.js +33 -0
  70. package/dist/eidos/prototype/prototype.js.map +1 -0
  71. package/dist/eidos/proxy/proxy.d.ts +108 -0
  72. package/dist/eidos/proxy/proxy.d.ts.map +1 -0
  73. package/dist/eidos/proxy/proxy.js +121 -0
  74. package/dist/eidos/proxy/proxy.js.map +1 -0
  75. package/dist/eidos/singleton/singleton.d.ts +76 -0
  76. package/dist/eidos/singleton/singleton.d.ts.map +1 -0
  77. package/dist/eidos/singleton/singleton.js +77 -0
  78. package/dist/eidos/singleton/singleton.js.map +1 -0
  79. package/dist/eidos/state/state.d.ts +152 -0
  80. package/dist/eidos/state/state.d.ts.map +1 -0
  81. package/dist/eidos/state/state.js +85 -0
  82. package/dist/eidos/state/state.js.map +1 -0
  83. package/dist/eidos/strategy/strategy.d.ts +148 -0
  84. package/dist/eidos/strategy/strategy.d.ts.map +1 -0
  85. package/dist/eidos/strategy/strategy.js +167 -0
  86. package/dist/eidos/strategy/strategy.js.map +1 -0
  87. package/dist/eidos/template/template.d.ts +95 -0
  88. package/dist/eidos/template/template.d.ts.map +1 -0
  89. package/dist/eidos/template/template.js +110 -0
  90. package/dist/eidos/template/template.js.map +1 -0
  91. package/dist/eidos/visitor/visitor.d.ts +78 -0
  92. package/dist/eidos/visitor/visitor.d.ts.map +1 -0
  93. package/dist/eidos/visitor/visitor.js +80 -0
  94. package/dist/eidos/visitor/visitor.js.map +1 -0
  95. package/dist/zygos/result/index.d.ts +19 -0
  96. package/dist/zygos/result/index.d.ts.map +1 -0
  97. package/dist/zygos/result/index.js +29 -0
  98. package/dist/zygos/result/index.js.map +1 -0
  99. package/package.json +28 -3
@@ -0,0 +1,167 @@
1
+ /**
2
+ * Functional Strategy Pattern.
3
+ *
4
+ * In OOP, the Strategy pattern requires an interface, concrete classes, and a
5
+ * context class to swap algorithms at runtime. In functional TypeScript, a
6
+ * strategy is simply a function - the pattern becomes composition.
7
+ *
8
+ * @module eidos/strategy
9
+ * @since 2.4.0
10
+ *
11
+ * @see {@link https://pithos.dev/api/eidos/strategy/ | Explanations, examples and live demo}
12
+ *
13
+ * @example
14
+ * ```ts
15
+ * import { type Strategy, createStrategies, safeStrategy } from "@pithos/core/eidos/strategy";
16
+ *
17
+ * const sorting = createStrategies({
18
+ * asc: (data: number[]) => [...data].sort((a, b) => a - b),
19
+ * desc: (data: number[]) => [...data].sort((a, b) => b - a),
20
+ * });
21
+ *
22
+ * sorting.execute("asc", [3, 1, 2]); // [1, 2, 3]
23
+ * sorting.use("desc")([3, 1, 2]); // [3, 2, 1]
24
+ * ```
25
+ */
26
+ import { ok, err } from "../../zygos/result/result.js";
27
+ import { some, none } from "../../zygos/option.js";
28
+ import { ensure } from "../../bridges/ensure.js";
29
+ /**
30
+ * Creates a strategy resolver from a record of named strategies.
31
+ * Replaces the GoF Context class - instead of `setStrategy()` + `execute()`,
32
+ * you simply pick a function by key and call it.
33
+ *
34
+ * @template K - Union of strategy keys
35
+ * @template In - The input type
36
+ * @template Out - The output type
37
+ * @param strategies - Record mapping keys to strategy functions
38
+ * @returns Resolver with `use` (get fn) and `execute` (run by key)
39
+ * @since 2.4.0
40
+ *
41
+ * @example
42
+ * ```ts
43
+ * const pricing = createStrategies({
44
+ * regular: (price: number) => price,
45
+ * vip: (price: number) => price * 0.8,
46
+ * premium: (price: number) => price * 0.7,
47
+ * });
48
+ *
49
+ * const applyVip = pricing.use("vip");
50
+ * applyVip(100); // 80
51
+ *
52
+ * pricing.execute("premium", 100); // 70
53
+ *
54
+ * // Safe lookup for dynamic keys (e.g. from config)
55
+ * const key: string = getFromConfig();
56
+ * pricing.get(key); // Option<Strategy<number, number>>
57
+ * ```
58
+ */
59
+ export function createStrategies(strategies) {
60
+ return {
61
+ /** Get a strategy by key. Typed keys only. */
62
+ use: (key) => strategies[key],
63
+ /** Execute a strategy by key with the given input. */
64
+ execute: (key, input) => strategies[key](input),
65
+ /** Safe lookup for dynamic/runtime keys. Returns `Option<Strategy>`. */
66
+ get: (key) => {
67
+ if (key in strategies) {
68
+ // INTENTIONAL: key validated by `in` check, TS can't narrow string to K
69
+ return some(strategies[key]);
70
+ }
71
+ return none;
72
+ },
73
+ };
74
+ }
75
+ /**
76
+ * Wraps a strategy to return a zygos `Result` instead of throwing.
77
+ * Catches any exception and wraps it in `Err<Error>`.
78
+ *
79
+ * @deprecated Use `Result.fromThrowable` from `@zygos/result/result` instead.
80
+ *
81
+ * ```ts
82
+ * import { Result } from "../../zygos/result/result.js";
83
+ *
84
+ * const safeParseJson = Result.fromThrowable(
85
+ * (input: string) => JSON.parse(input),
86
+ * (e) => e instanceof Error ? e : new Error(String(e)),
87
+ * );
88
+ * safeParseJson('{"ok":true}'); // Ok({ ok: true })
89
+ * safeParseJson("invalid"); // Err(SyntaxError(...))
90
+ * ```
91
+ *
92
+ * @see {@link https://pithos.dev/api/eidos/strategy/ | Full explanation, examples and live demo}
93
+ * @template In - The input type
94
+ * @template Out - The output type
95
+ * @param strategy - The strategy to make safe
96
+ * @returns A new strategy returning `Result<Out, Error>`
97
+ * @since 2.4.0
98
+ */
99
+ export function safeStrategy(strategy) {
100
+ return (input) => {
101
+ try {
102
+ return ok(strategy(input));
103
+ }
104
+ catch (error) {
105
+ return err(error instanceof Error ? error : new Error(String(error)));
106
+ }
107
+ };
108
+ }
109
+ /**
110
+ * Composes a primary strategy with a fallback.
111
+ * If the primary throws, the fallback is executed instead.
112
+ *
113
+ * @template In - The input type
114
+ * @template Out - The output type
115
+ * @param primary - The strategy to try first
116
+ * @param fallback - The strategy to use if primary throws
117
+ * @returns A new combined strategy
118
+ * @since 2.4.0
119
+ *
120
+ * @example
121
+ * ```ts
122
+ * const fromCache: Strategy<string, Data> = (key) => cache.get(key);
123
+ * const fromApi: Strategy<string, Data> = (key) => api.fetch(key);
124
+ *
125
+ * const fetchData = withFallback(fromCache, fromApi);
126
+ * fetchData("user:123"); // tries cache, falls back to API
127
+ * ```
128
+ */
129
+ export function withFallback(primary, fallback) {
130
+ return (input) => {
131
+ try {
132
+ return primary(input);
133
+ }
134
+ catch {
135
+ return fallback(input);
136
+ }
137
+ };
138
+ }
139
+ /**
140
+ * Validates input against a kanon schema before executing the strategy.
141
+ * Bridges kanon validation, zygos Result, and the strategy pattern.
142
+ *
143
+ * @template S - The kanon schema type
144
+ * @template Out - The output type of the strategy
145
+ * @param schema - Kanon schema to validate input against
146
+ * @param strategy - Strategy to execute on validated input
147
+ * @returns A function accepting unknown input and returning `Result<Out, string>`
148
+ * @since 2.4.0
149
+ *
150
+ * @example
151
+ * ```ts
152
+ * import { number } from "@pithos/core/kanon";
153
+ *
154
+ * const double = withValidation(
155
+ * number().min(0),
156
+ * (n) => n * 2,
157
+ * );
158
+ *
159
+ * double(5); // Ok(10)
160
+ * double(-1); // Err("Number must be >= 0")
161
+ * double("hello"); // Err("Expected number")
162
+ * ```
163
+ */
164
+ export function withValidation(schema, strategy) {
165
+ return (input) => ensure(schema, input).map(strategy);
166
+ }
167
+ //# sourceMappingURL=strategy.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"strategy.js","sourceRoot":"","sources":["../../../src/eidos/strategy/strategy.ts"],"names":[],"mappings":"AAAA;;;;;;;;;;;;;;;;;;;;;;;;GAwBG;AAEH,OAAO,EAAE,EAAE,EAAE,GAAG,EAAE,MAAM,sBAAsB,CAAC;AAC/C,OAAO,EAAE,IAAI,EAAE,IAAI,EAAE,MAAM,eAAe,CAAC;AAC3C,OAAO,EAAE,MAAM,EAAE,MAAM,iBAAiB,CAAC;AAezC;;;;;;;;;;;;;;;;;;;;;;;;;;;;;GA6BG;AACH,MAAM,UAAU,gBAAgB,CAC9B,UAAwC;IAExC,OAAO;QACL,8CAA8C;QAC9C,GAAG,EAAE,CAAC,GAAM,EAAqB,EAAE,CAAC,UAAU,CAAC,GAAG,CAAC;QACnD,sDAAsD;QACtD,OAAO,EAAE,CAAC,GAAM,EAAE,KAAS,EAAO,EAAE,CAAC,UAAU,CAAC,GAAG,CAAC,CAAC,KAAK,CAAC;QAC3D,wEAAwE;QACxE,GAAG,EAAE,CAAC,GAAW,EAA6B,EAAE;YAC9C,IAAI,GAAG,IAAI,UAAU,EAAE,CAAC;gBACtB,wEAAwE;gBACxE,OAAO,IAAI,CAAC,UAAU,CAAC,GAAQ,CAAC,CAAC,CAAC;YACpC,CAAC;YACD,OAAO,IAAI,CAAC;QACd,CAAC;KACF,CAAC;AACJ,CAAC;AAED;;;;;;;;;;;;;;;;;;;;;;;GAuBG;AACH,MAAM,UAAU,YAAY,CAC1B,QAA2B;IAE3B,OAAO,CAAC,KAAS,EAAE,EAAE;QACnB,IAAI,CAAC;YACH,OAAO,EAAE,CAAC,QAAQ,CAAC,KAAK,CAAC,CAAC,CAAC;QAC7B,CAAC;QAAC,OAAO,KAAK,EAAE,CAAC;YACf,OAAO,GAAG,CAAC,KAAK,YAAY,KAAK,CAAC,CAAC,CAAC,KAAK,CAAC,CAAC,CAAC,IAAI,KAAK,CAAC,MAAM,CAAC,KAAK,CAAC,CAAC,CAAC,CAAC;QACxE,CAAC;IACH,CAAC,CAAC;AACJ,CAAC;AAED;;;;;;;;;;;;;;;;;;;GAmBG;AACH,MAAM,UAAU,YAAY,CAC1B,OAA0B,EAC1B,QAA2B;IAE3B,OAAO,CAAC,KAAS,EAAO,EAAE;QACxB,IAAI,CAAC;YACH,OAAO,OAAO,CAAC,KAAK,CAAC,CAAC;QACxB,CAAC;QAAC,MAAM,CAAC;YACP,OAAO,QAAQ,CAAC,KAAK,CAAC,CAAC;QACzB,CAAC;IACH,CAAC,CAAC;AACJ,CAAC;AAED;;;;;;;;;;;;;;;;;;;;;;;;GAwBG;AACH,MAAM,UAAU,cAAc,CAC5B,MAAS,EACT,QAAiC;IAEjC,OAAO,CAAC,KAAc,EAAE,EAAE,CAAC,MAAM,CAAC,MAAM,EAAE,KAAK,CAAC,CAAC,GAAG,CAAC,QAAQ,CAAC,CAAC;AACjE,CAAC"}
@@ -0,0 +1,95 @@
1
+ /**
2
+ * Functional Template Method Pattern.
3
+ *
4
+ * In OOP, the Template Method pattern requires an abstract class that defines
5
+ * the algorithm skeleton with abstract/hook methods, and concrete subclasses
6
+ * that override specific steps.
7
+ *
8
+ * In functional TypeScript, a template is just `(steps) => algorithm`.
9
+ * The base pattern is absorbed by the language — no wrapper needed.
10
+ *
11
+ * However, {@link templateWithDefaults} provides real value: it handles
12
+ * merging default step implementations with caller overrides.
13
+ *
14
+ * @module eidos/template
15
+ * @since 2.4.0
16
+ *
17
+ * @see {@link https://pithos.dev/api/eidos/template/ | Explanations, examples and live demo}
18
+ *
19
+ * @example
20
+ * ```ts
21
+ * // No import needed for basic templates — just write a function:
22
+ * const processData = (steps: { parse: (raw: string) => number[]; analyze: (data: number[]) => string }) =>
23
+ * (raw: string) => steps.analyze(steps.parse(raw));
24
+ *
25
+ * const csvProcessor = processData({
26
+ * parse: (raw) => raw.split(",").map(Number),
27
+ * analyze: (data) => `sum: ${data.reduce((a, b) => a + b, 0)}`,
28
+ * });
29
+ *
30
+ * // For templates with defaults, use templateWithDefaults:
31
+ * import { templateWithDefaults } from "@pithos/core/eidos/template/template";
32
+ *
33
+ * const report = templateWithDefaults(
34
+ * (steps: { header: () => string; body: (d: string) => string }) =>
35
+ * (data: string) => `${steps.header()}\n${steps.body(data)}`,
36
+ * { header: () => "=== Report ===", body: (d) => d },
37
+ * );
38
+ *
39
+ * report({ header: () => "Custom" })("content");
40
+ * ```
41
+ *
42
+ * @deprecated **Pattern absorbed by the language.**
43
+ *
44
+ * In functional TypeScript, a template is just `(steps) => algorithm`.
45
+ * This function is the identity — it exists only so you find this message.
46
+ *
47
+ * Write your template directly:
48
+ * ```ts
49
+ * const gameAI = (steps: { collect: () => number; attack: (n: number) => string }) =>
50
+ * () => steps.attack(steps.collect());
51
+ * ```
52
+ *
53
+ * For templates with default steps, use {@link templateWithDefaults} which
54
+ * provides actual value (merging defaults with overrides).
55
+ *
56
+ * @see {@link https://pithos.dev/api/eidos/template/ | Full explanation, examples and live demo}
57
+ */
58
+ export declare function template<Steps extends Record<string, (...args: any[]) => unknown>, Fn>(skeleton: (steps: Steps) => Fn): (steps: Steps) => Fn;
59
+ /**
60
+ * Creates a template method with default steps that can be partially overridden.
61
+ *
62
+ * This is the functional equivalent of an abstract class with hook methods
63
+ * that have default implementations. Only the steps you want to customize
64
+ * need to be provided.
65
+ *
66
+ * @template Steps - The record type describing the customizable steps
67
+ * @template Fn - The resulting algorithm function type
68
+ * @param skeleton - A function that wires the steps into an algorithm
69
+ * @param defaults - Default implementations for all steps
70
+ * @returns A function that accepts partial step overrides and returns the algorithm
71
+ * @since 2.4.0
72
+ *
73
+ * @example
74
+ * ```ts
75
+ * const report = templateWithDefaults(
76
+ * (steps: {
77
+ * header: () => string;
78
+ * body: (data: string) => string;
79
+ * footer: () => string;
80
+ * }) =>
81
+ * (data: string) => [steps.header(), steps.body(data), steps.footer()].join("\n"),
82
+ * {
83
+ * header: () => "=== Report ===",
84
+ * body: (data) => data,
85
+ * footer: () => "=== End ===",
86
+ * },
87
+ * );
88
+ *
89
+ * // Only override what you need
90
+ * const custom = report({ header: () => "** Custom **" });
91
+ * custom("content"); // "** Custom **\ncontent\n=== End ==="
92
+ * ```
93
+ */
94
+ export declare function templateWithDefaults<Steps extends object, Fn>(skeleton: (steps: Steps) => Fn, defaults: NoInfer<Steps>): (overrides?: Partial<NoInfer<Steps>>) => Fn;
95
+ //# sourceMappingURL=template.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"template.d.ts","sourceRoot":"","sources":["../../../src/eidos/template/template.ts"],"names":[],"mappings":"AAAA;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;GAwDG;AACH,wBAAgB,QAAQ,CAGtB,KAAK,SAAS,MAAM,CAAC,MAAM,EAAE,CAAC,GAAG,IAAI,EAAE,GAAG,EAAE,KAAK,OAAO,CAAC,EACzD,EAAE,EAEF,QAAQ,EAAE,CAAC,KAAK,EAAE,KAAK,KAAK,EAAE,GAC7B,CAAC,KAAK,EAAE,KAAK,KAAK,EAAE,CAEtB;AAED;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;GAkCG;AACH,wBAAgB,oBAAoB,CAAC,KAAK,SAAS,MAAM,EAAE,EAAE,EAC3D,QAAQ,EAAE,CAAC,KAAK,EAAE,KAAK,KAAK,EAAE,EAC9B,QAAQ,EAAE,OAAO,CAAC,KAAK,CAAC,GACvB,CAAC,SAAS,CAAC,EAAE,OAAO,CAAC,OAAO,CAAC,KAAK,CAAC,CAAC,KAAK,EAAE,CAY7C"}
@@ -0,0 +1,110 @@
1
+ /**
2
+ * Functional Template Method Pattern.
3
+ *
4
+ * In OOP, the Template Method pattern requires an abstract class that defines
5
+ * the algorithm skeleton with abstract/hook methods, and concrete subclasses
6
+ * that override specific steps.
7
+ *
8
+ * In functional TypeScript, a template is just `(steps) => algorithm`.
9
+ * The base pattern is absorbed by the language — no wrapper needed.
10
+ *
11
+ * However, {@link templateWithDefaults} provides real value: it handles
12
+ * merging default step implementations with caller overrides.
13
+ *
14
+ * @module eidos/template
15
+ * @since 2.4.0
16
+ *
17
+ * @see {@link https://pithos.dev/api/eidos/template/ | Explanations, examples and live demo}
18
+ *
19
+ * @example
20
+ * ```ts
21
+ * // No import needed for basic templates — just write a function:
22
+ * const processData = (steps: { parse: (raw: string) => number[]; analyze: (data: number[]) => string }) =>
23
+ * (raw: string) => steps.analyze(steps.parse(raw));
24
+ *
25
+ * const csvProcessor = processData({
26
+ * parse: (raw) => raw.split(",").map(Number),
27
+ * analyze: (data) => `sum: ${data.reduce((a, b) => a + b, 0)}`,
28
+ * });
29
+ *
30
+ * // For templates with defaults, use templateWithDefaults:
31
+ * import { templateWithDefaults } from "@pithos/core/eidos/template/template";
32
+ *
33
+ * const report = templateWithDefaults(
34
+ * (steps: { header: () => string; body: (d: string) => string }) =>
35
+ * (data: string) => `${steps.header()}\n${steps.body(data)}`,
36
+ * { header: () => "=== Report ===", body: (d) => d },
37
+ * );
38
+ *
39
+ * report({ header: () => "Custom" })("content");
40
+ * ```
41
+ *
42
+ * @deprecated **Pattern absorbed by the language.**
43
+ *
44
+ * In functional TypeScript, a template is just `(steps) => algorithm`.
45
+ * This function is the identity — it exists only so you find this message.
46
+ *
47
+ * Write your template directly:
48
+ * ```ts
49
+ * const gameAI = (steps: { collect: () => number; attack: (n: number) => string }) =>
50
+ * () => steps.attack(steps.collect());
51
+ * ```
52
+ *
53
+ * For templates with default steps, use {@link templateWithDefaults} which
54
+ * provides actual value (merging defaults with overrides).
55
+ *
56
+ * @see {@link https://pithos.dev/api/eidos/template/ | Full explanation, examples and live demo}
57
+ */
58
+ export function template(skeleton) {
59
+ return skeleton;
60
+ }
61
+ /**
62
+ * Creates a template method with default steps that can be partially overridden.
63
+ *
64
+ * This is the functional equivalent of an abstract class with hook methods
65
+ * that have default implementations. Only the steps you want to customize
66
+ * need to be provided.
67
+ *
68
+ * @template Steps - The record type describing the customizable steps
69
+ * @template Fn - The resulting algorithm function type
70
+ * @param skeleton - A function that wires the steps into an algorithm
71
+ * @param defaults - Default implementations for all steps
72
+ * @returns A function that accepts partial step overrides and returns the algorithm
73
+ * @since 2.4.0
74
+ *
75
+ * @example
76
+ * ```ts
77
+ * const report = templateWithDefaults(
78
+ * (steps: {
79
+ * header: () => string;
80
+ * body: (data: string) => string;
81
+ * footer: () => string;
82
+ * }) =>
83
+ * (data: string) => [steps.header(), steps.body(data), steps.footer()].join("\n"),
84
+ * {
85
+ * header: () => "=== Report ===",
86
+ * body: (data) => data,
87
+ * footer: () => "=== End ===",
88
+ * },
89
+ * );
90
+ *
91
+ * // Only override what you need
92
+ * const custom = report({ header: () => "** Custom **" });
93
+ * custom("content"); // "** Custom **\ncontent\n=== End ==="
94
+ * ```
95
+ */
96
+ export function templateWithDefaults(skeleton, defaults) {
97
+ return (overrides) => {
98
+ // Stryker disable next-line ConditionalExpression: Stryker can't find related tests due to vitest.related config
99
+ if (!overrides)
100
+ return skeleton(defaults);
101
+ const merged = { ...defaults };
102
+ for (const key of Object.keys(overrides)) {
103
+ if (overrides[key] !== undefined) {
104
+ merged[key] = overrides[key];
105
+ }
106
+ }
107
+ return skeleton(merged);
108
+ };
109
+ }
110
+ //# sourceMappingURL=template.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"template.js","sourceRoot":"","sources":["../../../src/eidos/template/template.ts"],"names":[],"mappings":"AAAA;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;GAwDG;AACH,MAAM,UAAU,QAAQ,CAMtB,QAA8B;IAE9B,OAAO,QAAQ,CAAC;AAClB,CAAC;AAED;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;GAkCG;AACH,MAAM,UAAU,oBAAoB,CAClC,QAA8B,EAC9B,QAAwB;IAExB,OAAO,CAAC,SAAS,EAAE,EAAE;QACnB,iHAAiH;QACjH,IAAI,CAAC,SAAS;YAAE,OAAO,QAAQ,CAAC,QAAQ,CAAC,CAAC;QAC1C,MAAM,MAAM,GAAG,EAAE,GAAG,QAAQ,EAAE,CAAC;QAC/B,KAAK,MAAM,GAAG,IAAI,MAAM,CAAC,IAAI,CAAC,SAAS,CAAoB,EAAE,CAAC;YAC5D,IAAI,SAAS,CAAC,GAAG,CAAC,KAAK,SAAS,EAAE,CAAC;gBACjC,MAAM,CAAC,GAAG,CAAC,GAAG,SAAS,CAAC,GAAG,CAAuB,CAAC;YACrD,CAAC;QACH,CAAC;QACD,OAAO,QAAQ,CAAC,MAAM,CAAC,CAAC;IAC1B,CAAC,CAAC;AACJ,CAAC"}
@@ -0,0 +1,78 @@
1
+ /**
2
+ * Functional Visitor Pattern.
3
+ *
4
+ * In OOP, the Visitor pattern requires a Component interface with `accept()`,
5
+ * concrete components that call `visitor.visitX(this)`, and Visitor interfaces
6
+ * with a method per component type. This "double dispatch" works around the
7
+ * limitation that OOP languages dispatch only on the receiver type.
8
+ *
9
+ * In functional TypeScript, this is absorbed by discriminated unions + switch:
10
+ * - Define your types as a union with a discriminant (`type`, `kind`, `_tag`)
11
+ * - Use `switch` on the discriminant — TypeScript narrows the type in each case
12
+ * - Exhaustiveness is checked at compile time
13
+ *
14
+ * No wrapper needed — it's native language behavior.
15
+ *
16
+ * @module eidos/visitor
17
+ * @since 2.4.0
18
+ *
19
+ * @see {@link https://pithos.dev/api/eidos/visitor/ | Explanations, examples and live demo}
20
+ *
21
+ * @example
22
+ * ```ts
23
+ * // No import needed — just use discriminated unions + switch:
24
+ *
25
+ * type Shape =
26
+ * | { type: "circle"; radius: number }
27
+ * | { type: "rectangle"; width: number; height: number }
28
+ * | { type: "triangle"; base: number; height: number };
29
+ *
30
+ * // "Visitor 1" - calculate area
31
+ * const area = (shape: Shape): number => {
32
+ * switch (shape.type) {
33
+ * case "circle": return Math.PI * shape.radius ** 2;
34
+ * case "rectangle": return shape.width * shape.height;
35
+ * case "triangle": return (shape.base * shape.height) / 2;
36
+ * }
37
+ * };
38
+ *
39
+ * // "Visitor 2" - describe shape
40
+ * const describe = (shape: Shape): string => {
41
+ * switch (shape.type) {
42
+ * case "circle": return `Circle with radius ${shape.radius}`;
43
+ * case "rectangle": return `Rectangle ${shape.width}x${shape.height}`;
44
+ * case "triangle": return `Triangle base=${shape.base}`;
45
+ * }
46
+ * };
47
+ *
48
+ * // Same data, different "visitors" (functions)
49
+ * const shapes: Shape[] = [
50
+ * { type: "circle", radius: 5 },
51
+ * { type: "rectangle", width: 3, height: 4 },
52
+ * ];
53
+ *
54
+ * shapes.map(area); // [78.54, 12]
55
+ * shapes.map(describe); // ["Circle with radius 5", "Rectangle 3x4"]
56
+ * ```
57
+ *
58
+ * @deprecated **Pattern absorbed by the language.**
59
+ *
60
+ * In functional TypeScript, the Visitor pattern is just a switch on a
61
+ * discriminated union. TypeScript narrows the type in each case branch.
62
+ *
63
+ * Write your visitor directly:
64
+ * ```ts
65
+ * const visit = (shape: Shape): number => {
66
+ * switch (shape.type) {
67
+ * case "circle": return Math.PI * shape.radius ** 2;
68
+ * case "rectangle": return shape.width * shape.height;
69
+ * }
70
+ * };
71
+ * ```
72
+ *
73
+ * This function is the identity — it exists only so you find this message.
74
+ *
75
+ * @see {@link https://pithos.dev/api/eidos/visitor/ | Full explanation, examples and live demo}
76
+ */
77
+ export declare function visit<T, R>(value: T, visitor: (v: T) => R): R;
78
+ //# sourceMappingURL=visitor.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"visitor.d.ts","sourceRoot":"","sources":["../../../src/eidos/visitor/visitor.ts"],"names":[],"mappings":"AAAA;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;GA2EG;AACH,wBAAgB,KAAK,CAAC,CAAC,EAAE,CAAC,EAAE,KAAK,EAAE,CAAC,EAAE,OAAO,EAAE,CAAC,CAAC,EAAE,CAAC,KAAK,CAAC,GAAG,CAAC,CAE7D"}
@@ -0,0 +1,80 @@
1
+ /**
2
+ * Functional Visitor Pattern.
3
+ *
4
+ * In OOP, the Visitor pattern requires a Component interface with `accept()`,
5
+ * concrete components that call `visitor.visitX(this)`, and Visitor interfaces
6
+ * with a method per component type. This "double dispatch" works around the
7
+ * limitation that OOP languages dispatch only on the receiver type.
8
+ *
9
+ * In functional TypeScript, this is absorbed by discriminated unions + switch:
10
+ * - Define your types as a union with a discriminant (`type`, `kind`, `_tag`)
11
+ * - Use `switch` on the discriminant — TypeScript narrows the type in each case
12
+ * - Exhaustiveness is checked at compile time
13
+ *
14
+ * No wrapper needed — it's native language behavior.
15
+ *
16
+ * @module eidos/visitor
17
+ * @since 2.4.0
18
+ *
19
+ * @see {@link https://pithos.dev/api/eidos/visitor/ | Explanations, examples and live demo}
20
+ *
21
+ * @example
22
+ * ```ts
23
+ * // No import needed — just use discriminated unions + switch:
24
+ *
25
+ * type Shape =
26
+ * | { type: "circle"; radius: number }
27
+ * | { type: "rectangle"; width: number; height: number }
28
+ * | { type: "triangle"; base: number; height: number };
29
+ *
30
+ * // "Visitor 1" - calculate area
31
+ * const area = (shape: Shape): number => {
32
+ * switch (shape.type) {
33
+ * case "circle": return Math.PI * shape.radius ** 2;
34
+ * case "rectangle": return shape.width * shape.height;
35
+ * case "triangle": return (shape.base * shape.height) / 2;
36
+ * }
37
+ * };
38
+ *
39
+ * // "Visitor 2" - describe shape
40
+ * const describe = (shape: Shape): string => {
41
+ * switch (shape.type) {
42
+ * case "circle": return `Circle with radius ${shape.radius}`;
43
+ * case "rectangle": return `Rectangle ${shape.width}x${shape.height}`;
44
+ * case "triangle": return `Triangle base=${shape.base}`;
45
+ * }
46
+ * };
47
+ *
48
+ * // Same data, different "visitors" (functions)
49
+ * const shapes: Shape[] = [
50
+ * { type: "circle", radius: 5 },
51
+ * { type: "rectangle", width: 3, height: 4 },
52
+ * ];
53
+ *
54
+ * shapes.map(area); // [78.54, 12]
55
+ * shapes.map(describe); // ["Circle with radius 5", "Rectangle 3x4"]
56
+ * ```
57
+ *
58
+ * @deprecated **Pattern absorbed by the language.**
59
+ *
60
+ * In functional TypeScript, the Visitor pattern is just a switch on a
61
+ * discriminated union. TypeScript narrows the type in each case branch.
62
+ *
63
+ * Write your visitor directly:
64
+ * ```ts
65
+ * const visit = (shape: Shape): number => {
66
+ * switch (shape.type) {
67
+ * case "circle": return Math.PI * shape.radius ** 2;
68
+ * case "rectangle": return shape.width * shape.height;
69
+ * }
70
+ * };
71
+ * ```
72
+ *
73
+ * This function is the identity — it exists only so you find this message.
74
+ *
75
+ * @see {@link https://pithos.dev/api/eidos/visitor/ | Full explanation, examples and live demo}
76
+ */
77
+ export function visit(value, visitor) {
78
+ return visitor(value);
79
+ }
80
+ //# sourceMappingURL=visitor.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"visitor.js","sourceRoot":"","sources":["../../../src/eidos/visitor/visitor.ts"],"names":[],"mappings":"AAAA;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;GA2EG;AACH,MAAM,UAAU,KAAK,CAAO,KAAQ,EAAE,OAAoB;IACxD,OAAO,OAAO,CAAC,KAAK,CAAC,CAAC;AACxB,CAAC"}
@@ -0,0 +1,19 @@
1
+ /**
2
+ * Barrel re-export for Result.
3
+ *
4
+ * Provides a single import point for all Result-related exports.
5
+ *
6
+ * @example
7
+ * ```typescript
8
+ * import { Result, ok, err, Ok, Err, ResultAsync } from '@pithos/core/zygos/result';
9
+ *
10
+ * const r: Result<number, string> = ok(42);
11
+ * const safe = Result.fromThrowable(JSON.parse);
12
+ * const combined = Result.combine([ok(1), ok(2)]);
13
+ * ```
14
+ *
15
+ * @since 2.4.0
16
+ */
17
+ export { Result, Ok, Err, ok, err, safeTry, safeAsyncTry, fromOption, fromEither, toEither, } from "./result.js";
18
+ export { ResultAsync, okAsync, errAsync, } from "./result-async.js";
19
+ //# sourceMappingURL=index.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../../../src/zygos/result/index.ts"],"names":[],"mappings":"AAAA;;;;;;;;;;;;;;;GAeG;AAEH,OAAO,EAEL,MAAM,EAGN,EAAE,EACF,GAAG,EAGH,EAAE,EACF,GAAG,EAGH,OAAO,EACP,YAAY,EAGZ,UAAU,EACV,UAAU,EACV,QAAQ,GACT,MAAM,aAAa,CAAC;AAErB,OAAO,EACL,WAAW,EACX,OAAO,EACP,QAAQ,GACT,MAAM,mBAAmB,CAAC"}
@@ -0,0 +1,29 @@
1
+ /**
2
+ * Barrel re-export for Result.
3
+ *
4
+ * Provides a single import point for all Result-related exports.
5
+ *
6
+ * @example
7
+ * ```typescript
8
+ * import { Result, ok, err, Ok, Err, ResultAsync } from '@pithos/core/zygos/result';
9
+ *
10
+ * const r: Result<number, string> = ok(42);
11
+ * const safe = Result.fromThrowable(JSON.parse);
12
+ * const combined = Result.combine([ok(1), ok(2)]);
13
+ * ```
14
+ *
15
+ * @since 2.4.0
16
+ */
17
+ export {
18
+ // Type + Namespace (declaration merging: works as both)
19
+ Result,
20
+ // Classes
21
+ Ok, Err,
22
+ // Constructors
23
+ ok, err,
24
+ // Utilities
25
+ safeTry, safeAsyncTry,
26
+ // Conversions
27
+ fromOption, fromEither, toEither, } from "./result.js";
28
+ export { ResultAsync, okAsync, errAsync, } from "./result-async.js";
29
+ //# sourceMappingURL=index.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"index.js","sourceRoot":"","sources":["../../../src/zygos/result/index.ts"],"names":[],"mappings":"AAAA;;;;;;;;;;;;;;;GAeG;AAEH,OAAO;AACL,wDAAwD;AACxD,MAAM;AAEN,UAAU;AACV,EAAE,EACF,GAAG;AAEH,eAAe;AACf,EAAE,EACF,GAAG;AAEH,YAAY;AACZ,OAAO,EACP,YAAY;AAEZ,cAAc;AACd,UAAU,EACV,UAAU,EACV,QAAQ,GACT,MAAM,aAAa,CAAC;AAErB,OAAO,EACL,WAAW,EACX,OAAO,EACP,QAAQ,GACT,MAAM,mBAAmB,CAAC"}
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@pithos/core",
3
- "version": "2.3.0",
3
+ "version": "2.4.0",
4
4
  "description": "Advanced JavaScript/TypeScript superset providing utilities, validation, and functional patterns",
5
5
  "type": "module",
6
6
  "publishConfig": {
@@ -27,6 +27,29 @@
27
27
  "./arkhe/types/utilities/*": "./dist/arkhe/types/utilities/*.js",
28
28
  "./arkhe/util/*": "./dist/arkhe/util/*.js",
29
29
  "./bridges/*": "./dist/bridges/*.js",
30
+ "./eidos/abstract-factory/*": "./dist/eidos/abstract-factory/*.js",
31
+ "./eidos/adapter/*": "./dist/eidos/adapter/*.js",
32
+ "./eidos/bridge/*": "./dist/eidos/bridge/*.js",
33
+ "./eidos/builder/*": "./dist/eidos/builder/*.js",
34
+ "./eidos/chain/*": "./dist/eidos/chain/*.js",
35
+ "./eidos/command/*": "./dist/eidos/command/*.js",
36
+ "./eidos/composite/*": "./dist/eidos/composite/*.js",
37
+ "./eidos/decorator/*": "./dist/eidos/decorator/*.js",
38
+ "./eidos/facade/*": "./dist/eidos/facade/*.js",
39
+ "./eidos/factory-method/*": "./dist/eidos/factory-method/*.js",
40
+ "./eidos/flyweight/*": "./dist/eidos/flyweight/*.js",
41
+ "./eidos/interpreter/*": "./dist/eidos/interpreter/*.js",
42
+ "./eidos/iterator/*": "./dist/eidos/iterator/*.js",
43
+ "./eidos/mediator/*": "./dist/eidos/mediator/*.js",
44
+ "./eidos/memento/*": "./dist/eidos/memento/*.js",
45
+ "./eidos/observer/*": "./dist/eidos/observer/*.js",
46
+ "./eidos/prototype/*": "./dist/eidos/prototype/*.js",
47
+ "./eidos/proxy/*": "./dist/eidos/proxy/*.js",
48
+ "./eidos/singleton/*": "./dist/eidos/singleton/*.js",
49
+ "./eidos/state/*": "./dist/eidos/state/*.js",
50
+ "./eidos/strategy/*": "./dist/eidos/strategy/*.js",
51
+ "./eidos/template/*": "./dist/eidos/template/*.js",
52
+ "./eidos/visitor/*": "./dist/eidos/visitor/*.js",
30
53
  "./kanon/core/consts/*": "./dist/kanon/core/consts/*.js",
31
54
  "./kanon/core/*": "./dist/kanon/core/*.js",
32
55
  "./kanon/helpers/*": "./dist/kanon/helpers/*.js",
@@ -60,7 +83,8 @@
60
83
  "./taphos/string/*": "./dist/taphos/string/*.js",
61
84
  "./taphos/util/*": "./dist/taphos/util/*.js",
62
85
  "./zygos/*": "./dist/zygos/*.js",
63
- "./zygos/result/*": "./dist/zygos/result/*.js"
86
+ "./zygos/result/*": "./dist/zygos/result/*.js",
87
+ "./zygos/result": "./dist/zygos/result/index.js"
64
88
  },
65
89
  "files": [
66
90
  "dist",
@@ -77,7 +101,8 @@
77
101
  "lodash-alternative",
78
102
  "zod-alternative",
79
103
  "neverthrow-alternative",
80
- "fp-ts-alternative"
104
+ "fp-ts-alternative",
105
+ "effect-alternative"
81
106
  ],
82
107
  "author": "Pierre Moati <mopi1402>",
83
108
  "license": "MIT",