4 releases (breaking)

0.5.0 Mar 12, 2022
0.4.0 Feb 21, 2022
0.2.0 Feb 8, 2022
0.1.0 Jan 31, 2022

#1429 in WebAssembly


Used in ts-bindgen

MIT/Apache

485KB
13K SLoC

ts-bindgen-gen   CI Latest Version Rust Documentation Crates.io

ts-bindgen-gen contains the typescript parsing and rust wasm-bindgen binding generation logic for ts-bindgen.

For usage information about ts-bindgen, check out the ts-bindgen docs, online playground, or repo.

Status

ts-bindgen is currently alpha software and it should be expected that any or all of the following might change significantly from version to version:

  1. Generated bindings
  2. Exposed interfaces
  3. Internal implementation

There are currently known issues that will prevent generation of reasonable bindings for some typescript idioms.

We welcome contributions and issues!

Overview

The overall flow is:

  1. Parse typescript from swc_ecma_ast into our base ir
  2. Transform our base ir into a flattened ir and then into a target-enriched ir. The flattened ir takes types that are inlined and unnamed in typescript (e.g. the implied number | string enum in interface { a: number | string }) and "flattens" them to named, top-level types while fixing up references. The target-enriched ir propagates file and namespace context down through the AST.
  3. Construct a Module Definition hierarchy representing the rust modules and types in each module.
  4. Generate our rust bindings by walking the ModDef hierarchy and generating a proc_macro2::TokenStream.

Todo

  • Lots of todos in the code to address.
  • We should generate better async bindings.
  • We don't yet handle tsconfig typeRoots.
  • The implicit assumption that every x.d.ts has a corresponding x.js is incorrect - we need to separately resolve .js and .d.ts files and preserve the .js path in generated bindings.
  • Issues with typescript modules and name resolution (e.g. referencing A.B in a typescript module should look for A.B in all ancestors but, as implemented, looks for B in all ancestors).
  • Rarely used typescript namespaces are not properly handled yet (they should result in js_namespace attrs in wasm-bindgen) and require special handling in bundling to work (see the paperjs example.
  • Improve performance
  • Functions passed to js are leaked without interface type support
  • Functions don't handle this parameters properly

Needed refactorings

  • Codegen is too complex and would be much better served by another ir transformation pass to convert to a data representation of the rust code we want to generate and then generating a TokenStream more straightforwardly from that representation. This would enable, for example, references to a single generated name instead of hoping to re-generate the same name in multiple places.
  • Automatically generate bindings for all typescript test cases and ensure the generated bindings compile.
  • The ir transformation pipeline could be better served by something like frunk::Generic.

License

Copyright 2022 Adam Berger, Ratchet Designs.

ts-bindgen is licensed under either of the MIT or Apache licenses, at your option.

Credit

ts-bindgen is crafted thoughtfully by Ratchet Designs

Dependencies

~17–31MB
~510K SLoC