Skip to content

bbopen/tywrap

Repository files navigation

tywrap

npm version PyPI version CI Coverage License: MIT npm downloads PRs Welcome Docs

TypeScript wrapper for Python libraries with full type safety.

⚠️ Experimental — APIs may change before v1.0.0. See the releases page for breaking changes.

Features

  • Full Type Safety - TypeScript definitions generated from Python source analysis
  • Multi-Runtime - Node.js (subprocess) and browsers (Pyodide)
  • Rich Data Types - numpy, pandas, scipy, torch, sklearn, and stdlib types
  • Efficient Serialization - Apache Arrow binary format with JSON fallback

Why tywrap?

Feature tywrap pythonia node-calls-python pymport
Auto-generated TypeScript types
Browser / WASM (Pyodide)
numpy / pandas type mappings
Node.js + Bun + Deno All three Node only Node only Node only
Apache Arrow binary transport

Requirements

  • Node.js 20+ (or Bun 1.1+ / Deno 1.46+)

  • Python 3.10+ with tywrap-ir:

    pip install tywrap-ir

Quick Start

npm install tywrap
pip install tywrap-ir  # Python component for code generation
npx tywrap init        # Create config (and package.json scripts if present)
npx tywrap generate    # Generate wrappers

For CI (or to verify a dependency upgrade didn’t change the generated surface):

npx tywrap generate --check
import { NodeBridge } from 'tywrap/node';
import { setRuntimeBridge } from 'tywrap/runtime';
import * as math from './generated/math.generated.js';

const bridge = new NodeBridge({ pythonPath: 'python3' });
setRuntimeBridge(bridge);

const result = await math.sqrt(16); // 4

If tywrap saves you time, a ⭐ on GitHub helps others find it.

Runtime Bridges

Node.js

import { NodeBridge } from 'tywrap/node';
const bridge = new NodeBridge({
  pythonPath: 'python3',
  virtualEnv: './venv',
  timeoutMs: 30000,
});

NodeBridge is the default, correctness-first bridge. OptimizedNodeBridge is a performance-focused prototype (process pooling + optional caching) and is not a drop-in replacement yet. See ROADMAP.md for the unification plan.

Both bridges share a common JSONL core for protocol validation and timeouts.

By default, NodeBridge inherits only PATH/PYTHON*/TYWRAP_* from process.env to keep the subprocess environment minimal. Set inheritProcessEnv: true if you need the full environment.

You can cap payload sizes with TYWRAP_CODEC_MAX_BYTES (responses) and TYWRAP_REQUEST_MAX_BYTES (requests) to keep JSONL traffic bounded.

Browser (Pyodide)

import { PyodideBridge } from 'tywrap/pyodide';
const bridge = new PyodideBridge({
  indexURL: 'https://cdn.jsdelivr.net/pyodide/v0.28.0/full/',
});
await bridge.init();

Deno / Bun

import { NodeBridge } from 'npm:tywrap'; // Deno
import { NodeBridge } from 'tywrap'; // Bun

Configuration

// tywrap.config.ts
import { defineConfig } from 'tywrap';

export default defineConfig({
  pythonModules: {
    pandas: {
      runtime: 'node',
      typeHints: 'strict',
      classes: ['DataFrame'],
      functions: ['read_csv'],
    },
    numpy: {
      runtime: 'node',
      typeHints: 'strict',
      alias: 'np',
    },
  },
  output: { dir: './src/generated' },
});

See Configuration Guide for all options.

Supported Data Types

Python TypeScript Notes
numpy.ndarray Uint8Array / array Arrow or JSON
pandas.DataFrame Arrow Table / object[] Arrow or JSON
scipy.sparse.* SparseMatrix CSR, CSC, COO
torch.Tensor TorchTensor CPU only
sklearn estimator SklearnEstimator Params only
datetime, Decimal, UUID, Path string Standard formats

For Arrow encoding with numpy/pandas:

import { registerArrowDecoder } from 'tywrap';
import { tableFromIPC } from 'apache-arrow';
registerArrowDecoder(bytes => tableFromIPC(bytes));

Documentation

Contributing

npm install
npm test

See CONTRIBUTING.md for guidelines.

License

MIT © tywrap contributors

Links

About

TypeScript wrapper for Python libraries with full type safety and multi-runtime support (Node.js, Deno, Bun, Browser/Pyodide)

Topics

Resources

License

Contributing

Stars

Watchers

Forks

Packages

 
 
 

Contributors