Typedoc Converter
This is a typedoc json to C# bindings converter. Can be used as a TypeScript to C# bindings converter.
Compatibility Status
- typedoc: 0.20
- TypeScript: 3.9, 4.0, 4.1, 4.2
Languages support
- Enums
- Direct value
- Referenced value
- Interfaces
- Inherits
- Generics
- Generics Constaints
- Properties
- Methods
- Events
- Classes
- Constructors
- Inherits
- Generics
- Generics Constaints
- Properties
- Methods
- Events
- Indexer
- Types
- String literals
- Type literals
- Type alias*
- Union types
- Intersection types
- Split entities to different files
- Auto rename conflict parameter names
- WinRT/CLR async types support (
IAsyncAction
/IAsyncOperation<T>
orTask
/Task<T>
) - Newtonsoft.Json and System.Text.Json for JSON serialization
- Nullable Reference Types
- Type validation
*: Partial support
Installation
dotnet tool install -g TypedocConverter
Quick start
TypeScript code input.ts
:
declare namespace test {
/**
* The declaration of an enum
*/
export enum MyEnum {
A = 0,
B = 1,
C = 2,
D = C
}
/**
* The declaration of an interface
*/
export interface MyInterface1 {
/**
* A method
*/
testMethod(arg: string, callback: () => void): string;
/**
* An event
* @event
*/
onTest(listener: (e: MyInterface1) => void): void;
/**
* An property
*/
readonly testProp: string;
}
/**
* Another declaration of an interface
*/
export interface MyInterface2<T> {
/**
* A method
*/
testMethod(arg: T, callback: () => void): T;
/**
* An event
* @event
*/
onTest(listener: (e: MyInterface2<T>) => void): void;
/**
* An property
*/
readonly testProp: T;
}
/**
* The declaration of a class
*/
export class MyClass1<T> implements MyInterface1 {
/**
* A method
*/
testMethod(arg: string, callback: () => void): string;
/**
* An event
* @event
*/
onTest(listener: (e: MyInterface1) => void): void;
/**
* An property
*/
readonly testProp: string;
static staticMethod(value: string, isOption?: boolean): UnionStr;
}
/**
* Another declaration of a class
*/
export class MyClass2<T> implements MyInterface2<T> {
/**
* A method
*/
testMethod(arg: T, callback: () => void): T;
/**
* An event
* @event
*/
onTest(listener: (e: MyInterface2<T>) => void): void;
/**
* An property
*/
readonly testProp: T;
static staticMethod(value: string, isOption?: boolean): UnionStr;
}
/**
* The declaration of a type alias
*/
export type UnionStr = "A" | "B" | "C" | "other";
}
With below commands (need a tsconfig.json
):
typedoc input.ts --json output.json
TypedocConverter --inputfile output.json --outputfile output.cs
Voila! C# type bindings generated in output.cs:
namespace Test
{
/// <summary>
/// The declaration of an enum
/// </summary>
enum MyEnum
{
A = 0,
B = 1,
C = 2,
D = 2
}
}
namespace Test
{
/// <summary>
/// The declaration of a class
/// </summary>
class MyClass1<T> : MyInterface1
{
/// <summary>
/// An event
/// </summary>
public event System.Action<MyInterface1> OnTest;
/// <summary>
/// An property
/// </summary>
[Newtonsoft.Json.JsonProperty("testProp", NullValueHandling = Newtonsoft.Json.NullValueHandling.Ignore)]
public string TestProp { get => throw new System.NotImplementedException(); set => throw new System.NotImplementedException(); }
/// <summary>
/// A method
/// </summary>
public string TestMethod(string arg, System.Action callback) => throw new System.NotImplementedException();
static UnionStr StaticMethod(string value, bool isOption) => throw new System.NotImplementedException();
}
}
namespace Test
{
/// <summary>
/// Another declaration of a class
/// </summary>
class MyClass2<T> : MyInterface2<T>
{
/// <summary>
/// An event
/// </summary>
public event System.Action<MyInterface2<T>> OnTest;
/// <summary>
/// An property
/// </summary>
[Newtonsoft.Json.JsonProperty("testProp", NullValueHandling = Newtonsoft.Json.NullValueHandling.Ignore)]
public T TestProp { get => throw new System.NotImplementedException(); set => throw new System.NotImplementedException(); }
/// <summary>
/// A method
/// </summary>
public T TestMethod(T arg, System.Action callback) => throw new System.NotImplementedException();
static UnionStr StaticMethod(string value, bool isOption) => throw new System.NotImplementedException();
}
}
namespace Test
{
/// <summary>
/// The declaration of an interface
/// </summary>
interface MyInterface1
{
/// <summary>
/// An event
/// </summary>
event System.Action<MyInterface1> OnTest;
/// <summary>
/// An property
/// </summary>
[Newtonsoft.Json.JsonProperty("testProp", NullValueHandling = Newtonsoft.Json.NullValueHandling.Ignore)]
string TestProp { get; set; }
/// <summary>
/// A method
/// </summary>
string TestMethod(string arg, System.Action callback);
}
}
namespace Test
{
/// <summary>
/// Another declaration of an interface
/// </summary>
interface MyInterface2<T>
{
/// <summary>
/// An event
/// </summary>
event System.Action<MyInterface2<T>> OnTest;
/// <summary>
/// An property
/// </summary>
[Newtonsoft.Json.JsonProperty("testProp", NullValueHandling = Newtonsoft.Json.NullValueHandling.Ignore)]
T TestProp { get; set; }
/// <summary>
/// A method
/// </summary>
T TestMethod(T arg, System.Action callback);
}
}
namespace Test
{
/// <summary>
/// The declaration of a type alias
/// </summary>
[Newtonsoft.Json.JsonConverter(typeof(UnionStrConverter))]
enum UnionStr
{
///<summary>
/// A
///</summary>
A,
///<summary>
/// B
///</summary>
B,
///<summary>
/// C
///</summary>
C,
///<summary>
/// other
///</summary>
Other
}
class UnionStrConverter : Newtonsoft.Json.JsonConverter
{
public override bool CanConvert(System.Type t) => t == typeof(UnionStr) || t == typeof(UnionStr?);
public override object ReadJson(Newtonsoft.Json.JsonReader reader, System.Type t, object? existingValue, Newtonsoft.Json.JsonSerializer serializer)
=> reader.TokenType switch
{
Newtonsoft.Json.JsonToken.String =>
serializer.Deserialize<string>(reader) switch
{
"A" => UnionStr.A,
"B" => UnionStr.B,
"C" => UnionStr.C,
"other" => UnionStr.Other,
_ => throw new System.NotSupportedException("Cannot unmarshal type UnionStr")
},
_ => throw new System.NotSupportedException("Cannot unmarshal type UnionStr")
};
public override void WriteJson(Newtonsoft.Json.JsonWriter writer, object? untypedValue, Newtonsoft.Json.JsonSerializer serializer)
{
if (untypedValue is null) { serializer.Serialize(writer, null); return; }
var value = (UnionStr)untypedValue;
switch (value)
{
case UnionStr.A: serializer.Serialize(writer, "A"); return;
case UnionStr.B: serializer.Serialize(writer, "B"); return;
case UnionStr.C: serializer.Serialize(writer, "C"); return;
case UnionStr.Other: serializer.Serialize(writer, "other"); return;
default: break;
}
throw new System.NotSupportedException("Cannot marshal type UnionStr");
}
}
}
Build
cd TypedocConverter/TypedocConverter
dotnet publish -c Release -r win-x64 --no-self-contained /p:PublishSingleFile=true /p:PublishReadyToRun=true
You can replace win-x64
with other platform identifiers such as win-arm64
, linux-x64
, linux-arm64
, osx-x64
and etc.
Then built dists will be placed in bin/Release/net7.0/[platform identifier]/publish
Native Build
cd TypedocConverter/TypedocConverter
dotnet publish -c Release -r win-x64 /p:PublishAot=true
You can replace win-x64
with other platform identifiers such as win-arm64
, linux-x64
, linux-arm64
, osx-x64
and etc.
Then built dists will be placed in bin/Release/net7.0/[platform identifier]/publish
Run & Usage
TypedocConverter --help
Sample:
TypedocConverter --inputfile 1.json --splitfiles true --outputdir .
Arguments:
--inputfile [file]: input file
--namespace [namespace]: specify namespace for generated code
--splitfiles [true|false]: whether to split code to different files
--outputdir [path]: used for place code files when splitfiles is true
--outputfile [path]: used for place code file when splitfiles is false
--number-type [int/decimal/double...]: config for number type mapping
--promise-type [CLR/WinRT]: config for promise type mapping, CLR for Task and WinRT for IAsyncAction/IAsyncOperation
--any-type [object/dynamic...]: config for any type mapping
--array-type [Array/IEnumerable/List...]: config for array type mapping
--nrt-disabled [true|false]: whether to disable Nullable Reference Types
--json-mode [system|newtonsoft|both]: whether to use System.Text.Json or Newtonsoft.Json or both
Prebuilt binaries
We have prepared some prebuilt binaries for Windows, Linux and macOS.
You can download them directly from Releases
Prerequisites: .NET Runtime 7.0