tywrap 0.2.0 → 0.2.1

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 (88) hide show
  1. package/README.md +1 -1
  2. package/dist/index.d.ts +20 -4
  3. package/dist/index.d.ts.map +1 -1
  4. package/dist/index.js +22 -2
  5. package/dist/index.js.map +1 -1
  6. package/dist/runtime/base.d.ts +17 -7
  7. package/dist/runtime/base.d.ts.map +1 -1
  8. package/dist/runtime/base.js +18 -1
  9. package/dist/runtime/base.js.map +1 -1
  10. package/dist/runtime/bounded-context.d.ts +252 -0
  11. package/dist/runtime/bounded-context.d.ts.map +1 -0
  12. package/dist/runtime/bounded-context.js +454 -0
  13. package/dist/runtime/bounded-context.js.map +1 -0
  14. package/dist/runtime/bridge-protocol.d.ts +167 -0
  15. package/dist/runtime/bridge-protocol.d.ts.map +1 -0
  16. package/dist/runtime/bridge-protocol.js +247 -0
  17. package/dist/runtime/bridge-protocol.js.map +1 -0
  18. package/dist/runtime/disposable.d.ts +40 -0
  19. package/dist/runtime/disposable.d.ts.map +1 -0
  20. package/dist/runtime/disposable.js +49 -0
  21. package/dist/runtime/disposable.js.map +1 -0
  22. package/dist/runtime/http-io.d.ts +91 -0
  23. package/dist/runtime/http-io.d.ts.map +1 -0
  24. package/dist/runtime/http-io.js +195 -0
  25. package/dist/runtime/http-io.js.map +1 -0
  26. package/dist/runtime/http.d.ts +47 -13
  27. package/dist/runtime/http.d.ts.map +1 -1
  28. package/dist/runtime/http.js +55 -74
  29. package/dist/runtime/http.js.map +1 -1
  30. package/dist/runtime/node.d.ts +97 -130
  31. package/dist/runtime/node.d.ts.map +1 -1
  32. package/dist/runtime/node.js +256 -523
  33. package/dist/runtime/node.js.map +1 -1
  34. package/dist/runtime/pooled-transport.d.ts +131 -0
  35. package/dist/runtime/pooled-transport.d.ts.map +1 -0
  36. package/dist/runtime/pooled-transport.js +175 -0
  37. package/dist/runtime/pooled-transport.js.map +1 -0
  38. package/dist/runtime/process-io.d.ts +204 -0
  39. package/dist/runtime/process-io.d.ts.map +1 -0
  40. package/dist/runtime/process-io.js +695 -0
  41. package/dist/runtime/process-io.js.map +1 -0
  42. package/dist/runtime/pyodide-io.d.ts +155 -0
  43. package/dist/runtime/pyodide-io.d.ts.map +1 -0
  44. package/dist/runtime/pyodide-io.js +397 -0
  45. package/dist/runtime/pyodide-io.js.map +1 -0
  46. package/dist/runtime/pyodide.d.ts +51 -19
  47. package/dist/runtime/pyodide.d.ts.map +1 -1
  48. package/dist/runtime/pyodide.js +57 -186
  49. package/dist/runtime/pyodide.js.map +1 -1
  50. package/dist/runtime/safe-codec.d.ts +81 -0
  51. package/dist/runtime/safe-codec.d.ts.map +1 -0
  52. package/dist/runtime/safe-codec.js +345 -0
  53. package/dist/runtime/safe-codec.js.map +1 -0
  54. package/dist/runtime/transport.d.ts +186 -0
  55. package/dist/runtime/transport.d.ts.map +1 -0
  56. package/dist/runtime/transport.js +86 -0
  57. package/dist/runtime/transport.js.map +1 -0
  58. package/dist/runtime/validators.d.ts +131 -0
  59. package/dist/runtime/validators.d.ts.map +1 -0
  60. package/dist/runtime/validators.js +219 -0
  61. package/dist/runtime/validators.js.map +1 -0
  62. package/dist/runtime/worker-pool.d.ts +196 -0
  63. package/dist/runtime/worker-pool.d.ts.map +1 -0
  64. package/dist/runtime/worker-pool.js +371 -0
  65. package/dist/runtime/worker-pool.js.map +1 -0
  66. package/dist/utils/codec.d.ts.map +1 -1
  67. package/dist/utils/codec.js +120 -1
  68. package/dist/utils/codec.js.map +1 -1
  69. package/package.json +2 -2
  70. package/runtime/python_bridge.py +30 -3
  71. package/runtime/safe_codec.py +344 -0
  72. package/src/index.ts +48 -5
  73. package/src/runtime/base.ts +18 -26
  74. package/src/runtime/bounded-context.ts +608 -0
  75. package/src/runtime/bridge-protocol.ts +319 -0
  76. package/src/runtime/disposable.ts +65 -0
  77. package/src/runtime/http-io.ts +244 -0
  78. package/src/runtime/http.ts +71 -117
  79. package/src/runtime/node.ts +358 -691
  80. package/src/runtime/pooled-transport.ts +252 -0
  81. package/src/runtime/process-io.ts +902 -0
  82. package/src/runtime/pyodide-io.ts +485 -0
  83. package/src/runtime/pyodide.ts +75 -215
  84. package/src/runtime/safe-codec.ts +443 -0
  85. package/src/runtime/transport.ts +273 -0
  86. package/src/runtime/validators.ts +241 -0
  87. package/src/runtime/worker-pool.ts +498 -0
  88. package/src/utils/codec.ts +126 -1
package/README.md CHANGED
@@ -7,7 +7,7 @@
7
7
 
8
8
  TypeScript wrapper for Python libraries with full type safety.
9
9
 
10
- > **⚠️ Experimental Software (v0.2.0)** - APIs may change between versions. Not recommended for production use until v1.0.0.
10
+ > **⚠️ Experimental Software (v0.2.1)** - APIs may change between versions. Not recommended for production use until v1.0.0.
11
11
 
12
12
  ## Features
13
13
 
package/dist/index.d.ts CHANGED
@@ -7,18 +7,34 @@
7
7
  import { tywrap } from './tywrap.js';
8
8
  export type { TywrapConfig } from './config/index.js';
9
9
  export { defineConfig, resolveConfig } from './config/index.js';
10
+ export { BoundedContext, type ContextState, type ExecuteOptions } from './runtime/bounded-context.js';
11
+ export { BridgeProtocol, type BridgeProtocolOptions } from './runtime/bridge-protocol.js';
12
+ export { SafeCodec, type CodecOptions } from './runtime/safe-codec.js';
13
+ export type { Transport, TransportOptions, ProtocolMessage, ProtocolResponse } from './runtime/transport.js';
14
+ export { PROTOCOL_ID, isTransport, isProtocolMessage, isProtocolResponse } from './runtime/transport.js';
15
+ export { ProcessIO, type ProcessIOOptions } from './runtime/process-io.js';
16
+ export { HttpIO, type HttpIOOptions } from './runtime/http-io.js';
17
+ export { PyodideIO, type PyodideIOOptions } from './runtime/pyodide-io.js';
18
+ export { WorkerPool, type WorkerPoolOptions, type PooledWorker } from './runtime/worker-pool.js';
19
+ export { PooledTransport, type PooledTransportOptions } from './runtime/pooled-transport.js';
20
+ export type { Disposable } from './runtime/disposable.js';
21
+ export { isDisposable, safeDispose, disposeAll } from './runtime/disposable.js';
22
+ export { ValidationError, isFiniteNumber, isPositiveNumber, isNonNegativeNumber, isNonEmptyString, isPlainObject, assertFiniteNumber, assertPositive, assertNonNegative, assertString, assertNonEmptyString, assertArray, assertObject, containsSpecialFloat, assertNoSpecialFloats, sanitizeForFilename, containsPathTraversal, } from './runtime/validators.js';
23
+ /**
24
+ * @deprecated Use BoundedContext instead. RuntimeBridge will be removed in the next major version.
25
+ */
10
26
  export { RuntimeBridge } from './runtime/base.js';
11
27
  export { BridgeError, BridgeProtocolError, BridgeTimeoutError, BridgeDisposedError, BridgeExecutionError, } from './runtime/errors.js';
12
28
  export { getRuntimeBridge, setRuntimeBridge, clearRuntimeBridge } from './runtime/index.js';
13
- export { NodeBridge } from './runtime/node.js';
14
- export { PyodideBridge } from './runtime/pyodide.js';
15
- export { HttpBridge } from './runtime/http.js';
29
+ export { NodeBridge, type NodeBridgeOptions } from './runtime/node.js';
30
+ export { PyodideBridge, type PyodideBridgeOptions } from './runtime/pyodide.js';
31
+ export { HttpBridge, type HttpBridgeOptions } from './runtime/http.js';
16
32
  export type { PythonModule, PythonFunction, PythonClass, PythonType, PrimitiveType, CollectionType, UnionType, OptionalType, CustomType, GenericType, Parameter, Property, PythonImport, TypescriptType, RuntimeStrategy, TywrapOptions, PythonModuleConfig, OutputConfig, RuntimeConfig, PyodideConfig, NodeConfig, HttpConfig, PerformanceConfig, DevelopmentConfig, TypeMappingConfig, TypePreset, BridgeInfo, AnalysisResult, AnalysisError, AnalysisWarning, AnalysisStatistics, GeneratedCode, } from './types/index.js';
17
33
  export { tywrap } from './tywrap.js';
18
34
  export { generate } from './tywrap.js';
19
35
  export { detectRuntime, isNodejs, isDeno, isBun, isBrowser } from './utils/runtime.js';
20
36
  export { decodeValue, decodeValueAsync, autoRegisterArrowDecoder, registerArrowDecoder, clearArrowDecoder, } from './utils/codec.js';
21
- export declare const VERSION = "0.2.0";
37
+ export declare const VERSION = "0.2.1";
22
38
  /**
23
39
  * Quick setup function for getting started
24
40
  */
@@ -1 +1 @@
1
- {"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../src/index.ts"],"names":[],"mappings":"AAAA;;;;;GAKG;AAEH,OAAO,EAAE,MAAM,EAAE,MAAM,aAAa,CAAC;AAErC,YAAY,EAAE,YAAY,EAAE,MAAM,mBAAmB,CAAC;AACtD,OAAO,EAAE,YAAY,EAAE,aAAa,EAAE,MAAM,mBAAmB,CAAC;AAChE,OAAO,EAAE,aAAa,EAAE,MAAM,mBAAmB,CAAC;AAClD,OAAO,EACL,WAAW,EACX,mBAAmB,EACnB,kBAAkB,EAClB,mBAAmB,EACnB,oBAAoB,GACrB,MAAM,qBAAqB,CAAC;AAC7B,OAAO,EAAE,gBAAgB,EAAE,gBAAgB,EAAE,kBAAkB,EAAE,MAAM,oBAAoB,CAAC;AAG5F,OAAO,EAAE,UAAU,EAAE,MAAM,mBAAmB,CAAC;AAC/C,OAAO,EAAE,aAAa,EAAE,MAAM,sBAAsB,CAAC;AACrD,OAAO,EAAE,UAAU,EAAE,MAAM,mBAAmB,CAAC;AAG/C,YAAY,EACV,YAAY,EACZ,cAAc,EACd,WAAW,EACX,UAAU,EACV,aAAa,EACb,cAAc,EACd,SAAS,EACT,YAAY,EACZ,UAAU,EACV,WAAW,EACX,SAAS,EACT,QAAQ,EACR,YAAY,EACZ,cAAc,EACd,eAAe,EACf,aAAa,EACb,kBAAkB,EAClB,YAAY,EACZ,aAAa,EACb,aAAa,EACb,UAAU,EACV,UAAU,EACV,iBAAiB,EACjB,iBAAiB,EACjB,iBAAiB,EACjB,UAAU,EACV,UAAU,EACV,cAAc,EACd,aAAa,EACb,eAAe,EACf,kBAAkB,EAClB,aAAa,GACd,MAAM,kBAAkB,CAAC;AAG1B,OAAO,EAAE,MAAM,EAAE,MAAM,aAAa,CAAC;AACrC,OAAO,EAAE,QAAQ,EAAE,MAAM,aAAa,CAAC;AAGvC,OAAO,EAAE,aAAa,EAAE,QAAQ,EAAE,MAAM,EAAE,KAAK,EAAE,SAAS,EAAE,MAAM,oBAAoB,CAAC;AACvF,OAAO,EACL,WAAW,EACX,gBAAgB,EAChB,wBAAwB,EACxB,oBAAoB,EACpB,iBAAiB,GAClB,MAAM,kBAAkB,CAAC;AAG1B,eAAO,MAAM,OAAO,UAAU,CAAC;AAE/B;;GAEG;AAEH,eAAe,MAAM,CAAC"}
1
+ {"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../src/index.ts"],"names":[],"mappings":"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"}
package/dist/index.js CHANGED
@@ -6,10 +6,30 @@
6
6
  */
7
7
  import { tywrap } from './tywrap.js';
8
8
  export { defineConfig, resolveConfig } from './config/index.js';
9
+ // BoundedContext - unified abstraction for cross-boundary concerns
10
+ export { BoundedContext } from './runtime/bounded-context.js';
11
+ // BridgeProtocol - unified BoundedContext + SafeCodec + Transport
12
+ export { BridgeProtocol } from './runtime/bridge-protocol.js';
13
+ // SafeCodec - validation and serialization for JS<->Python boundary
14
+ export { SafeCodec } from './runtime/safe-codec.js';
15
+ export { PROTOCOL_ID, isTransport, isProtocolMessage, isProtocolResponse } from './runtime/transport.js';
16
+ // Transport implementations
17
+ export { ProcessIO } from './runtime/process-io.js';
18
+ export { HttpIO } from './runtime/http-io.js';
19
+ export { PyodideIO } from './runtime/pyodide-io.js';
20
+ // WorkerPool - concurrent transport management
21
+ export { WorkerPool } from './runtime/worker-pool.js';
22
+ // PooledTransport - Transport adapter that wraps WorkerPool
23
+ export { PooledTransport } from './runtime/pooled-transport.js';
24
+ export { isDisposable, safeDispose, disposeAll } from './runtime/disposable.js';
25
+ export { ValidationError, isFiniteNumber, isPositiveNumber, isNonNegativeNumber, isNonEmptyString, isPlainObject, assertFiniteNumber, assertPositive, assertNonNegative, assertString, assertNonEmptyString, assertArray, assertObject, containsSpecialFloat, assertNoSpecialFloats, sanitizeForFilename, containsPathTraversal, } from './runtime/validators.js';
26
+ /**
27
+ * @deprecated Use BoundedContext instead. RuntimeBridge will be removed in the next major version.
28
+ */
9
29
  export { RuntimeBridge } from './runtime/base.js';
10
30
  export { BridgeError, BridgeProtocolError, BridgeTimeoutError, BridgeDisposedError, BridgeExecutionError, } from './runtime/errors.js';
11
31
  export { getRuntimeBridge, setRuntimeBridge, clearRuntimeBridge } from './runtime/index.js';
12
- // Runtime-specific exports
32
+ // Runtime-specific exports (Bridges using new BridgeProtocol architecture)
13
33
  export { NodeBridge } from './runtime/node.js';
14
34
  export { PyodideBridge } from './runtime/pyodide.js';
15
35
  export { HttpBridge } from './runtime/http.js';
@@ -20,7 +40,7 @@ export { generate } from './tywrap.js';
20
40
  export { detectRuntime, isNodejs, isDeno, isBun, isBrowser } from './utils/runtime.js';
21
41
  export { decodeValue, decodeValueAsync, autoRegisterArrowDecoder, registerArrowDecoder, clearArrowDecoder, } from './utils/codec.js';
22
42
  // Version info
23
- export const VERSION = '0.2.0';
43
+ export const VERSION = '0.2.1';
24
44
  /**
25
45
  * Quick setup function for getting started
26
46
  */
package/dist/index.js.map CHANGED
@@ -1 +1 @@
1
- {"version":3,"file":"index.js","sourceRoot":"","sources":["../src/index.ts"],"names":[],"mappings":"AAAA;;;;;GAKG;AAEH,OAAO,EAAE,MAAM,EAAE,MAAM,aAAa,CAAC;AAGrC,OAAO,EAAE,YAAY,EAAE,aAAa,EAAE,MAAM,mBAAmB,CAAC;AAChE,OAAO,EAAE,aAAa,EAAE,MAAM,mBAAmB,CAAC;AAClD,OAAO,EACL,WAAW,EACX,mBAAmB,EACnB,kBAAkB,EAClB,mBAAmB,EACnB,oBAAoB,GACrB,MAAM,qBAAqB,CAAC;AAC7B,OAAO,EAAE,gBAAgB,EAAE,gBAAgB,EAAE,kBAAkB,EAAE,MAAM,oBAAoB,CAAC;AAE5F,2BAA2B;AAC3B,OAAO,EAAE,UAAU,EAAE,MAAM,mBAAmB,CAAC;AAC/C,OAAO,EAAE,aAAa,EAAE,MAAM,sBAAsB,CAAC;AACrD,OAAO,EAAE,UAAU,EAAE,MAAM,mBAAmB,CAAC;AAsC/C,WAAW;AACX,OAAO,EAAE,MAAM,EAAE,MAAM,aAAa,CAAC;AACrC,OAAO,EAAE,QAAQ,EAAE,MAAM,aAAa,CAAC;AAEvC,8BAA8B;AAC9B,OAAO,EAAE,aAAa,EAAE,QAAQ,EAAE,MAAM,EAAE,KAAK,EAAE,SAAS,EAAE,MAAM,oBAAoB,CAAC;AACvF,OAAO,EACL,WAAW,EACX,gBAAgB,EAChB,wBAAwB,EACxB,oBAAoB,EACpB,iBAAiB,GAClB,MAAM,kBAAkB,CAAC;AAE1B,eAAe;AACf,MAAM,CAAC,MAAM,OAAO,GAAG,OAAO,CAAC;AAE/B;;GAEG;AACH,iCAAiC;AACjC,eAAe,MAAM,CAAC"}
1
+ {"version":3,"file":"index.js","sourceRoot":"","sources":["../src/index.ts"],"names":[],"mappings":"AAAA;;;;;GAKG;AAEH,OAAO,EAAE,MAAM,EAAE,MAAM,aAAa,CAAC;AAGrC,OAAO,EAAE,YAAY,EAAE,aAAa,EAAE,MAAM,mBAAmB,CAAC;AAChE,mEAAmE;AACnE,OAAO,EAAE,cAAc,EAA0C,MAAM,8BAA8B,CAAC;AACtG,kEAAkE;AAClE,OAAO,EAAE,cAAc,EAA8B,MAAM,8BAA8B,CAAC;AAC1F,oEAAoE;AACpE,OAAO,EAAE,SAAS,EAAqB,MAAM,yBAAyB,CAAC;AAGvE,OAAO,EAAE,WAAW,EAAE,WAAW,EAAE,iBAAiB,EAAE,kBAAkB,EAAE,MAAM,wBAAwB,CAAC;AACzG,4BAA4B;AAC5B,OAAO,EAAE,SAAS,EAAyB,MAAM,yBAAyB,CAAC;AAC3E,OAAO,EAAE,MAAM,EAAsB,MAAM,sBAAsB,CAAC;AAClE,OAAO,EAAE,SAAS,EAAyB,MAAM,yBAAyB,CAAC;AAC3E,+CAA+C;AAC/C,OAAO,EAAE,UAAU,EAA6C,MAAM,0BAA0B,CAAC;AACjG,4DAA4D;AAC5D,OAAO,EAAE,eAAe,EAA+B,MAAM,+BAA+B,CAAC;AAE7F,OAAO,EAAE,YAAY,EAAE,WAAW,EAAE,UAAU,EAAE,MAAM,yBAAyB,CAAC;AAChF,OAAO,EACL,eAAe,EACf,cAAc,EACd,gBAAgB,EAChB,mBAAmB,EACnB,gBAAgB,EAChB,aAAa,EACb,kBAAkB,EAClB,cAAc,EACd,iBAAiB,EACjB,YAAY,EACZ,oBAAoB,EACpB,WAAW,EACX,YAAY,EACZ,oBAAoB,EACpB,qBAAqB,EACrB,mBAAmB,EACnB,qBAAqB,GACtB,MAAM,yBAAyB,CAAC;AAEjC;;GAEG;AACH,OAAO,EAAE,aAAa,EAAE,MAAM,mBAAmB,CAAC;AAElD,OAAO,EACL,WAAW,EACX,mBAAmB,EACnB,kBAAkB,EAClB,mBAAmB,EACnB,oBAAoB,GACrB,MAAM,qBAAqB,CAAC;AAC7B,OAAO,EAAE,gBAAgB,EAAE,gBAAgB,EAAE,kBAAkB,EAAE,MAAM,oBAAoB,CAAC;AAE5F,2EAA2E;AAC3E,OAAO,EAAE,UAAU,EAA0B,MAAM,mBAAmB,CAAC;AACvE,OAAO,EAAE,aAAa,EAA6B,MAAM,sBAAsB,CAAC;AAChF,OAAO,EAAE,UAAU,EAA0B,MAAM,mBAAmB,CAAC;AAsCvE,WAAW;AACX,OAAO,EAAE,MAAM,EAAE,MAAM,aAAa,CAAC;AACrC,OAAO,EAAE,QAAQ,EAAE,MAAM,aAAa,CAAC;AAEvC,8BAA8B;AAC9B,OAAO,EAAE,aAAa,EAAE,QAAQ,EAAE,MAAM,EAAE,KAAK,EAAE,SAAS,EAAE,MAAM,oBAAoB,CAAC;AACvF,OAAO,EACL,WAAW,EACX,gBAAgB,EAChB,wBAAwB,EACxB,oBAAoB,EACpB,iBAAiB,GAClB,MAAM,kBAAkB,CAAC;AAE1B,eAAe;AACf,MAAM,CAAC,MAAM,OAAO,GAAG,OAAO,CAAC;AAE/B;;GAEG;AACH,iCAAiC;AACjC,eAAe,MAAM,CAAC"}
@@ -1,12 +1,22 @@
1
1
  /**
2
2
  * Base runtime bridge
3
+ *
4
+ * @deprecated Use BoundedContext instead. RuntimeBridge will be removed in the next major version.
3
5
  */
4
- import type { RuntimeExecution } from '../types/index.js';
5
- export declare abstract class RuntimeBridge implements RuntimeExecution {
6
- abstract call<T = unknown>(module: string, functionName: string, args: unknown[], kwargs?: Record<string, unknown>): Promise<T>;
7
- abstract instantiate<T = unknown>(module: string, className: string, args: unknown[], kwargs?: Record<string, unknown>): Promise<T>;
8
- abstract callMethod<T = unknown>(handle: string, methodName: string, args: unknown[], kwargs?: Record<string, unknown>): Promise<T>;
9
- abstract disposeInstance(handle: string): Promise<void>;
10
- abstract dispose(): Promise<void>;
6
+ import { BoundedContext } from './bounded-context.js';
7
+ /**
8
+ * @deprecated Use BoundedContext instead. RuntimeBridge will be removed in the next major version.
9
+ *
10
+ * All bridges now extend BoundedContext which provides:
11
+ * - Lifecycle management (init/dispose state machine)
12
+ * - Validation helpers
13
+ * - Error classification
14
+ * - Bounded execution (timeout, retry)
15
+ * - Resource ownership tracking
16
+ *
17
+ * @see BoundedContext
18
+ */
19
+ export declare abstract class RuntimeBridge extends BoundedContext {
11
20
  }
21
+ export { BoundedContext };
12
22
  //# sourceMappingURL=base.d.ts.map
@@ -1 +1 @@
1
- {"version":3,"file":"base.d.ts","sourceRoot":"","sources":["../../src/runtime/base.ts"],"names":[],"mappings":"AAAA;;GAEG;AAEH,OAAO,KAAK,EAAE,gBAAgB,EAAE,MAAM,mBAAmB,CAAC;AAE1D,8BAAsB,aAAc,YAAW,gBAAgB;IAC7D,QAAQ,CAAC,IAAI,CAAC,CAAC,GAAG,OAAO,EACvB,MAAM,EAAE,MAAM,EACd,YAAY,EAAE,MAAM,EACpB,IAAI,EAAE,OAAO,EAAE,EACf,MAAM,CAAC,EAAE,MAAM,CAAC,MAAM,EAAE,OAAO,CAAC,GAC/B,OAAO,CAAC,CAAC,CAAC;IAEb,QAAQ,CAAC,WAAW,CAAC,CAAC,GAAG,OAAO,EAC9B,MAAM,EAAE,MAAM,EACd,SAAS,EAAE,MAAM,EACjB,IAAI,EAAE,OAAO,EAAE,EACf,MAAM,CAAC,EAAE,MAAM,CAAC,MAAM,EAAE,OAAO,CAAC,GAC/B,OAAO,CAAC,CAAC,CAAC;IAEb,QAAQ,CAAC,UAAU,CAAC,CAAC,GAAG,OAAO,EAC7B,MAAM,EAAE,MAAM,EACd,UAAU,EAAE,MAAM,EAClB,IAAI,EAAE,OAAO,EAAE,EACf,MAAM,CAAC,EAAE,MAAM,CAAC,MAAM,EAAE,OAAO,CAAC,GAC/B,OAAO,CAAC,CAAC,CAAC;IAEb,QAAQ,CAAC,eAAe,CAAC,MAAM,EAAE,MAAM,GAAG,OAAO,CAAC,IAAI,CAAC;IAEvD,QAAQ,CAAC,OAAO,IAAI,OAAO,CAAC,IAAI,CAAC;CAClC"}
1
+ {"version":3,"file":"base.d.ts","sourceRoot":"","sources":["../../src/runtime/base.ts"],"names":[],"mappings":"AAAA;;;;GAIG;AAEH,OAAO,EAAE,cAAc,EAAE,MAAM,sBAAsB,CAAC;AAEtD;;;;;;;;;;;GAWG;AACH,8BAAsB,aAAc,SAAQ,cAAc;CAAG;AAG7D,OAAO,EAAE,cAAc,EAAE,CAAC"}
@@ -1,6 +1,23 @@
1
1
  /**
2
2
  * Base runtime bridge
3
+ *
4
+ * @deprecated Use BoundedContext instead. RuntimeBridge will be removed in the next major version.
3
5
  */
4
- export class RuntimeBridge {
6
+ import { BoundedContext } from './bounded-context.js';
7
+ /**
8
+ * @deprecated Use BoundedContext instead. RuntimeBridge will be removed in the next major version.
9
+ *
10
+ * All bridges now extend BoundedContext which provides:
11
+ * - Lifecycle management (init/dispose state machine)
12
+ * - Validation helpers
13
+ * - Error classification
14
+ * - Bounded execution (timeout, retry)
15
+ * - Resource ownership tracking
16
+ *
17
+ * @see BoundedContext
18
+ */
19
+ export class RuntimeBridge extends BoundedContext {
5
20
  }
21
+ // Re-export BoundedContext for backwards compatibility
22
+ export { BoundedContext };
6
23
  //# sourceMappingURL=base.js.map
@@ -1 +1 @@
1
- {"version":3,"file":"base.js","sourceRoot":"","sources":["../../src/runtime/base.ts"],"names":[],"mappings":"AAAA;;GAEG;AAIH,MAAM,OAAgB,aAAa;CAyBlC"}
1
+ {"version":3,"file":"base.js","sourceRoot":"","sources":["../../src/runtime/base.ts"],"names":[],"mappings":"AAAA;;;;GAIG;AAEH,OAAO,EAAE,cAAc,EAAE,MAAM,sBAAsB,CAAC;AAEtD;;;;;;;;;;;GAWG;AACH,MAAM,OAAgB,aAAc,SAAQ,cAAc;CAAG;AAE7D,uDAAuD;AACvD,OAAO,EAAE,cAAc,EAAE,CAAC"}
@@ -0,0 +1,252 @@
1
+ /**
2
+ * BoundedContext - Unified abstraction for cross-boundary concerns.
3
+ *
4
+ * This base class provides consistent handling of:
5
+ * - Lifecycle management (init/dispose state machine)
6
+ * - Validation helpers
7
+ * - Error classification
8
+ * - Bounded execution (timeout, retry)
9
+ * - Resource ownership tracking
10
+ *
11
+ * All runtime bridges (NodeBridge, PyodideBridge, HttpBridge) extend this class.
12
+ *
13
+ * @see https://github.com/bbopen/tywrap/issues/149
14
+ */
15
+ import type { RuntimeExecution } from '../types/index.js';
16
+ import { BridgeError } from './errors.js';
17
+ import type { Disposable } from './disposable.js';
18
+ /**
19
+ * Lifecycle states for a BoundedContext.
20
+ *
21
+ * State transitions:
22
+ * - idle → initializing → ready (on successful init)
23
+ * - idle → initializing → idle (on failed init, allows retry)
24
+ * - ready → disposing → disposed (on dispose)
25
+ * - disposed → (terminal, no further transitions)
26
+ */
27
+ export type ContextState = 'idle' | 'initializing' | 'ready' | 'disposing' | 'disposed';
28
+ /**
29
+ * Options for bounded execution.
30
+ */
31
+ export interface ExecuteOptions<T = unknown> {
32
+ /** Timeout in milliseconds. Default: 30000 (30s). Set to 0 to disable. */
33
+ timeoutMs?: number;
34
+ /** Number of retry attempts on retryable errors. Default: 0. */
35
+ retries?: number;
36
+ /** Base delay between retries in ms. Multiplied by attempt number. Default: 100. */
37
+ retryDelayMs?: number;
38
+ /** Optional validation function applied to the result. */
39
+ validate?: (result: T) => T;
40
+ /** Optional abort signal for external cancellation. */
41
+ signal?: AbortSignal;
42
+ }
43
+ /**
44
+ * Abstract base class for runtime bridges with unified boundary management.
45
+ *
46
+ * Provides lifecycle management, validation, error classification,
47
+ * bounded execution, and resource tracking.
48
+ */
49
+ export declare abstract class BoundedContext implements RuntimeExecution {
50
+ private _state;
51
+ private _initPromise?;
52
+ private readonly _resources;
53
+ /**
54
+ * Current lifecycle state of the context.
55
+ */
56
+ get state(): ContextState;
57
+ /**
58
+ * Whether the context is ready for operations.
59
+ */
60
+ get isReady(): boolean;
61
+ /**
62
+ * Whether the context has been disposed.
63
+ */
64
+ get isDisposed(): boolean;
65
+ /**
66
+ * Initialize the context.
67
+ *
68
+ * This method:
69
+ * - Is idempotent (safe to call multiple times)
70
+ * - Deduplicates concurrent calls (returns the same promise)
71
+ * - Allows retry after failure (resets to idle state)
72
+ * - Throws BridgeDisposedError if already disposed
73
+ *
74
+ * @throws BridgeDisposedError if the context has been disposed
75
+ * @throws BridgeError subclass if initialization fails
76
+ */
77
+ init(): Promise<void>;
78
+ /**
79
+ * Dispose the context and all tracked resources.
80
+ *
81
+ * This method:
82
+ * - Is idempotent (safe to call multiple times)
83
+ * - Disposes all tracked resources before calling doDispose()
84
+ * - Collects errors from resource disposal and reports them
85
+ * - Transitions to disposed state even if disposal errors occur
86
+ *
87
+ * @throws AggregateError if multiple disposal errors occur
88
+ * @throws Error if a single disposal error occurs
89
+ */
90
+ dispose(): Promise<void>;
91
+ /**
92
+ * Subclass initialization logic.
93
+ * Called during init() after state transitions to 'initializing'.
94
+ */
95
+ protected abstract doInit(): Promise<void>;
96
+ /**
97
+ * Subclass disposal logic.
98
+ * Called during dispose() after tracked resources are disposed.
99
+ */
100
+ protected abstract doDispose(): Promise<void>;
101
+ /**
102
+ * Validate that a value is a finite number.
103
+ * Wraps validation errors in appropriate BridgeError.
104
+ *
105
+ * @param value - The value to validate
106
+ * @param name - Parameter name for error messages
107
+ * @returns The validated number
108
+ * @throws BridgeError if validation fails
109
+ */
110
+ protected validateNumeric(value: unknown, name: string): number;
111
+ /**
112
+ * Validate that a value is a positive number.
113
+ * Wraps validation errors in appropriate BridgeError.
114
+ *
115
+ * @param value - The value to validate
116
+ * @param name - Parameter name for error messages
117
+ * @returns The validated number
118
+ * @throws BridgeError if validation fails
119
+ */
120
+ protected validatePositive(value: unknown, name: string): number;
121
+ /**
122
+ * Validate that a value is a string.
123
+ * Wraps validation errors in appropriate BridgeError.
124
+ *
125
+ * @param value - The value to validate
126
+ * @param name - Parameter name for error messages
127
+ * @returns The validated string
128
+ * @throws BridgeError if validation fails
129
+ */
130
+ protected validateString(value: unknown, name: string): string;
131
+ /**
132
+ * Validate that a value is a non-empty string.
133
+ * Wraps validation errors in appropriate BridgeError.
134
+ *
135
+ * @param value - The value to validate
136
+ * @param name - Parameter name for error messages
137
+ * @returns The validated string
138
+ * @throws BridgeError if validation fails
139
+ */
140
+ protected validateNonEmptyString(value: unknown, name: string): string;
141
+ /**
142
+ * Validate input before processing.
143
+ * Override in subclasses for domain-specific input validation.
144
+ *
145
+ * @param input - The input to validate
146
+ * @returns The validated input
147
+ */
148
+ protected validateInput<T>(input: T): T;
149
+ /**
150
+ * Validate output before returning.
151
+ * Override in subclasses for domain-specific output validation.
152
+ *
153
+ * @param output - The output to validate
154
+ * @returns The validated output
155
+ */
156
+ protected validateOutput<T>(output: T): T;
157
+ /**
158
+ * Classify an error into the appropriate BridgeError subtype.
159
+ *
160
+ * This method:
161
+ * - Passes through existing BridgeError instances
162
+ * - Uses context state to determine appropriate error type
163
+ * - Pattern-matches error messages for classification
164
+ *
165
+ * @param error - The error to classify
166
+ * @returns A BridgeError instance
167
+ */
168
+ protected classifyError(error: unknown): BridgeError;
169
+ /**
170
+ * Execute an operation with bounded execution guarantees.
171
+ *
172
+ * This method:
173
+ * - Auto-initializes if not ready
174
+ * - Enforces timeout limits
175
+ * - Supports retry on retryable errors
176
+ * - Respects abort signals
177
+ * - Validates results if a validator is provided
178
+ *
179
+ * @param operation - The async operation to execute
180
+ * @param options - Execution options (timeout, retries, etc.)
181
+ * @returns The operation result
182
+ * @throws BridgeTimeoutError if the operation times out
183
+ * @throws BridgeDisposedError if the context is disposed
184
+ * @throws BridgeError for other failures
185
+ */
186
+ protected execute<T>(operation: () => Promise<T>, options?: ExecuteOptions<T>): Promise<T>;
187
+ /**
188
+ * Wrap a promise with a timeout.
189
+ *
190
+ * @param promise - The promise to wrap
191
+ * @param ms - Timeout in milliseconds (0 or negative disables timeout)
192
+ * @param signal - Optional abort signal
193
+ * @returns The promise result
194
+ * @throws BridgeTimeoutError if the timeout expires
195
+ */
196
+ private withTimeout;
197
+ /**
198
+ * Determine if an error is retryable.
199
+ * Override in subclasses to customize retry logic.
200
+ *
201
+ * @param error - The error to check
202
+ * @returns True if the operation should be retried
203
+ */
204
+ protected isRetryable(error: BridgeError): boolean;
205
+ /**
206
+ * Delay for a specified duration.
207
+ *
208
+ * @param ms - Milliseconds to delay
209
+ */
210
+ private delay;
211
+ /**
212
+ * Track a disposable resource for automatic cleanup.
213
+ *
214
+ * When the context is disposed, all tracked resources will be
215
+ * disposed automatically.
216
+ *
217
+ * @param resource - The resource to track
218
+ * @returns The same resource (for chaining)
219
+ */
220
+ protected trackResource<T extends Disposable>(resource: T): T;
221
+ /**
222
+ * Stop tracking a resource.
223
+ *
224
+ * Use this when a resource is disposed manually and should
225
+ * not be disposed again during context disposal.
226
+ *
227
+ * @param resource - The resource to untrack
228
+ * @returns True if the resource was being tracked
229
+ */
230
+ protected untrackResource(resource: Disposable): boolean;
231
+ /**
232
+ * Number of currently tracked resources.
233
+ */
234
+ protected get resourceCount(): number;
235
+ /**
236
+ * Call a Python function.
237
+ */
238
+ abstract call<T = unknown>(module: string, functionName: string, args: unknown[], kwargs?: Record<string, unknown>): Promise<T>;
239
+ /**
240
+ * Instantiate a Python class.
241
+ */
242
+ abstract instantiate<T = unknown>(module: string, className: string, args: unknown[], kwargs?: Record<string, unknown>): Promise<T>;
243
+ /**
244
+ * Call a method on a Python instance.
245
+ */
246
+ abstract callMethod<T = unknown>(handle: string, methodName: string, args: unknown[], kwargs?: Record<string, unknown>): Promise<T>;
247
+ /**
248
+ * Dispose a Python instance.
249
+ */
250
+ abstract disposeInstance(handle: string): Promise<void>;
251
+ }
252
+ //# sourceMappingURL=bounded-context.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"bounded-context.d.ts","sourceRoot":"","sources":["../../src/runtime/bounded-context.ts"],"names":[],"mappings":"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"}