MultiType.NET.Generators 1.0.1

dotnet add package MultiType.NET.Generators --version 1.0.1
                    
NuGet\Install-Package MultiType.NET.Generators -Version 1.0.1
                    
This command is intended to be used within the Package Manager Console in Visual Studio, as it uses the NuGet module's version of Install-Package.
<PackageReference Include="MultiType.NET.Generators" Version="1.0.1" />
                    
For projects that support PackageReference, copy this XML node into the project file to reference the package.
<PackageVersion Include="MultiType.NET.Generators" Version="1.0.1" />
                    
Directory.Packages.props
<PackageReference Include="MultiType.NET.Generators" />
                    
Project file
For projects that support Central Package Management (CPM), copy this XML node into the solution Directory.Packages.props file to version the package.
paket add MultiType.NET.Generators --version 1.0.1
                    
#r "nuget: MultiType.NET.Generators, 1.0.1"
                    
#r directive can be used in F# Interactive and Polyglot Notebooks. Copy this into the interactive tool or source code of the script to reference the package.
#:package MultiType.NET.Generators@1.0.1
                    
#:package directive can be used in C# file-based apps starting in .NET 10 preview 4. Copy this into a .cs file before any lines of code to reference the package.
#addin nuget:?package=MultiType.NET.Generators&version=1.0.1
                    
Install as a Cake Addin
#tool nuget:?package=MultiType.NET.Generators&version=1.0.1
                    
Install as a Cake Tool

๐Ÿšฆ MultiType.NET

Type-safe, zero-allocation discriminated unions for modern .NET
Bring TypeScript-style union types to C# โ€” safer than object, cleaner than if, and built for real-world APIs and models.

Any<int, string> result = "hello";

NuGet Downloads


๐Ÿง  What Is a Union Type?

A union type lets a value be one of multiple specified types โ€” like this in TypeScript:

let result = number | string | null

// C# with MultiType.NET
Any<int, string> result = "hello";

MultiType.NET brings that idea to C# with full support for:

  • โœ… Type-safe access (Is<T>(), As<T>(), Match)
  • โœ… JSON (de)serialization
  • โœ… Zero boxing
  • โœ… ASP.NET API compatibility
  • โœ… Source generation for no-boilerplate code

โœจ Features Overview

Category Features
โœ… Matching Match, TryMatch, Switch, SwitchAsync, SwitchOrDefault
๐Ÿ” Mapping Map, MapAsync, MapSafe, MapValue, MapAny, MapWithContext, MapOrDefault, MapWhere
๐Ÿ” Selection Select, TrySelect, SelectAsync, SelectAsyncOrDefault, SelectWithContext, SelectWhere
๐Ÿ“ฆ Extraction GetTn, TryGetTn, GetTn(out remainder), Deconstruct(...)
๐Ÿง  Introspection ActualType, AllowedTypes, IsNull, ToString()
โš™๏ธ Construction From, TryFrom, FromTn, implicit/explicit operators
๐Ÿ“ค Serialization Native System.Text.Json support (global or attribute-based)
๐Ÿง‘โ€๐Ÿ’ป API-Ready Works with Controllers & Minimal APIs
๐Ÿงฉ Generator Auto-generates union types via [GenerateAny] or Any<T1..Tn>
๐Ÿงฉ Model Binding All types are Controller / Minimal-API Binding Ready

๐Ÿš€ Get Started

๐Ÿ“ฆ Install Core Library

dotnet add package MultiType.NET.Core

This gives you:

  • Any<T1..T16> prebuilt types
  • Core features like Match, Map, Switch, TryMatch, ...etc
  • JSON support via converter factory

๐Ÿ”ง Add Optional Source Generators

Package Description
MultiType.NET.Generator Adds [GenerateAny(typeof(...))] support
MultiType.NET.SourceGenerator Enables Any<T1..Tn> (over 16 types), JSON support, API integration
dotnet add package MultiType.NET.Generator

This allow you to generate a custom types with [GenerateAny], for more details MultiType.NET.Generator attribute.

[GenerateAny(typeof(string), typeof(MyType))]
public partial struct MyCustomType{}

This will generate MyCustomType with all MultiType APIs.

Need to generate Any<T17, ..., Tn>?

Install the official CLI generator:

dotnet tool install --global MultiType.NET.SourceGenerator

Then run:

multitypegen --maxArity 50 --project PATH_TO_TARGET_PROJECT.csproj

for more details and documentation MultiType.NET.SourceGenerator CLI


๐Ÿ’ก Learn by Example

Any<int, string, DateTime> result = "hello";

string output = result.Match(
    i => $"Int: {i}",
    s => $"String: {s}",
    d => $"Date: {d:yyyy-MM-dd}"
);
// Using generic Any<T1, T2, T3> directly from body
[HttpPost("process-multi-type")]
public async Task<IActionResult> ProcessMultiTypeData(
    [FromBody] Any<int, string, DateTime> requestData)
{
    // Example usage: requestData.Match(...)
    return Ok();
}

// Using generic Any<T1, T2, T3> from query string (less typical, but possible)
[HttpGet("query-multi-type")]
public async Task<IActionResult> QueryMultiTypeData(
    [FromQuery] Any<int, string, DateTime> queryData)
{
    return Ok();
}
if (result.TryGetT1(out var i, out var remainder))
    Console.WriteLine($"Was int: {i}");
else
    Console.WriteLine($"Not an int: {remainder}");
var summary = result.Select(
    i => $"# {i}",
    s => s.ToUpperInvariant(),
    d => d.ToShortTimeString()
);

๐Ÿงฑ Creating Any Values

MultiType.NET offers multiple ways to construct union values.

โœ… From(...) โ€” dynamic dispatch

object raw = 123;
var value = Any<int, string, DateTime>.From(raw);

๐Ÿ’ก Throws if the value is not one of the allowed types.

โœ… TryFrom(...) โ€” safe version

if (Any<int, string>.TryFrom(someValue, out var result))
{
    // Use result
}

โœ… FromTn(...) โ€” type-specific creation

var a = Any<int, string, bool>.FromT1(42);
var b = Any<int, string, bool>.FromT2("hello");

๐Ÿ’ก These are especially useful for code generation, dynamic input handling, or overload clarity.

โœ… Implicit Operators

Any<int, string> v1 = 5;
Any<int, string> v2 = "done";

๐Ÿ“ฆ JSON Serialization

MultiType.NET works seamlessly with System.Text.Json without any manual changes.

โœ… Per-type registration

public readonly partial struct MyUnionType;

๐Ÿงช Example

var options = new JsonSerializerOptions { WriteIndented = true };
string json = JsonSerializer.Serialize(Any<int, string>.From(123), options);

๐Ÿ’ก JSON output includes both the value and the represented type.


๐Ÿงฉ Custom Types with [GenerateAny]

โš ๏ธ Requires MultiType.NET.Generator installed.

[GenerateAny(typeof(int), typeof(string), typeof(Guid))]
public partial struct Payload;
// POST endpoint accepting Payload from body
[HttpPost("submit-payload")]
public async Task<IActionResult> SubmitPayload(
    [FromBody] Payload payload)
{
    // payload.Match(...)
    return Ok();
}

// GET endpoint accepting Payload from query
[HttpGet("search")]
public async Task<IActionResult> SearchPayload(
    [FromQuery] Payload query)
{
    return Ok();
}

Payload payload = Guid.NewGuid();

payload.Match(
    i => Console.WriteLine($"Int: {i}"),
    s => Console.WriteLine($"Str: {s}"),
    g => Console.WriteLine($"Guid: {g}")
);

** More advanced Type**

[GenerateAny(typeof(Success), typeof(Warning), typeof(Error), typeof(Info))]
public partial struct StatusType
{
    public static StatusType From(string value) => value.ToLowerInvariant() switch
    {
        "success" => new Success(),
        "warning" => new Warning(),
        "error" => new Error(),
        "info" => new Info(),
        _ => throw new ArgumentException("Invalid status", nameof(value))
    };

    public bool IsSuccess => this.Is<Success>();
    public bool IsWarning => this.Is<Warning>();
    public bool IsError => this.Is<Error>();
    public bool IsInfo => this.Is<Info>();

    public readonly struct Success { }
    public readonly struct Warning { }
    public readonly struct Error { }
    public readonly struct Info { }
}

โš™๏ธ How It Works (Behind the Scenes)

  • Any<T1, ..., Tn> is a readonly struct with internal value/ref handling.
  • Tracks active type via TypeIndex
  • Source generators:
    • Generate custom union types with all logic
    • Auto-wire JSON support
    • Add full method surface (Match, Map, Select, etc.)

๐Ÿงช Real-World Use Cases

Use Case Example
โœ… API Results Any<SuccessDto, ErrorDto>
๐Ÿง‘โ€โš–๏ธ Workflow Results Any<Approved, Rejected, Escalated>
๐Ÿง  State Modeling Any<Draft, Submitted, Published>
๐Ÿงพ Flexible Inputs Any<string, int, bool>
๐Ÿ”„ Retry Backoff Any<RetryLater, Fail, Success>

๐Ÿ“ Project Structure

Project Description
MultiType.NET.Core Runtime types and logic
MultiType.NET.Generator [GenerateAny] source generation
MultiType.NET.SourceGenerator JSON + Any<T1..Tn> generation

๐Ÿ“˜ Documentation

Resource Link
๐Ÿ” Advanced Features docs/AdvancedFeatures.md
๐Ÿง  Generator Guide docs/SourceGenerators.md
๐Ÿ’ก Integration Tips docs/Integration.md

๐Ÿ™Œ Contributing

Contributions, issues, and PRs are welcome!
See CONTRIBUTING.md to get started.


๐Ÿ“„ License

MIT โ€” LICENSE


Because type safety shouldn't be optional.

Product Compatible and additional computed target framework versions.
.NET net5.0 was computed.  net5.0-windows was computed.  net6.0 was computed.  net6.0-android was computed.  net6.0-ios was computed.  net6.0-maccatalyst was computed.  net6.0-macos was computed.  net6.0-tvos was computed.  net6.0-windows was computed.  net7.0 was computed.  net7.0-android was computed.  net7.0-ios was computed.  net7.0-maccatalyst was computed.  net7.0-macos was computed.  net7.0-tvos was computed.  net7.0-windows was computed.  net8.0 was computed.  net8.0-android was computed.  net8.0-browser was computed.  net8.0-ios was computed.  net8.0-maccatalyst was computed.  net8.0-macos was computed.  net8.0-tvos was computed.  net8.0-windows was computed.  net9.0 was computed.  net9.0-android was computed.  net9.0-browser was computed.  net9.0-ios was computed.  net9.0-maccatalyst was computed.  net9.0-macos was computed.  net9.0-tvos was computed.  net9.0-windows was computed.  net10.0 was computed.  net10.0-android was computed.  net10.0-browser was computed.  net10.0-ios was computed.  net10.0-maccatalyst was computed.  net10.0-macos was computed.  net10.0-tvos was computed.  net10.0-windows was computed. 
.NET Core netcoreapp2.0 was computed.  netcoreapp2.1 was computed.  netcoreapp2.2 was computed.  netcoreapp3.0 was computed.  netcoreapp3.1 was computed. 
.NET Standard netstandard2.0 is compatible.  netstandard2.1 was computed. 
.NET Framework net461 was computed.  net462 was computed.  net463 was computed.  net47 was computed.  net471 was computed.  net472 was computed.  net48 was computed.  net481 was computed. 
MonoAndroid monoandroid was computed. 
MonoMac monomac was computed. 
MonoTouch monotouch was computed. 
Tizen tizen40 was computed.  tizen60 was computed. 
Xamarin.iOS xamarinios was computed. 
Xamarin.Mac xamarinmac was computed. 
Xamarin.TVOS xamarintvos was computed. 
Xamarin.WatchOS xamarinwatchos was computed. 
Compatible target framework(s)
Included target framework(s) (in package)
Learn more about Target Frameworks and .NET Standard.
  • .NETStandard 2.0

    • No dependencies.

NuGet packages

This package is not used by any NuGet packages.

GitHub repositories

This package is not used by any popular GitHub repositories.

Version Downloads Last Updated
1.0.1 138 7/2/2025