Skip to main content

Concise sum types in Python.

Project description

type_enum: Concise sum types in Python

Sum types (aka tagged unions) in the style of Rust's enums, with pattern matching and (with the mypy plugin) exhaustiveness checking.

Basic usage

from type_enum import Field, TypeEnum

class BgColor(TypeEnum):
    transparent: Field[()]
    name: Field[str]
    rgb: Field[int, int, int]
    hsv: Field[int, int, int]

background_color: BgColor = BgColor.rgb(39, 127, 168)

assert isinstance(background_color, BgColor)
assert not isinstance(BgColor.rgb, BgColor)

match background_color:
    case BgColor.transparent():  # unfortunately needs the parentheses
        print("no color")
    case BgColor.name(color_name):
        print(f"color name: {color_name}")
    case BgColor.rgb(red, green, blue):
        print(f"RGB: {red}, {green}, {blue}")
    case BgColor.hsv(hue, saturation, value):
        print(f"HSV: {hue}, {saturation}, {value}")
# will print "RGB: 39, 127, 168"

Installation

Requires Python >= 3.11 (because features from PEP 646 are required)

pip install type-enum

And for the mypy plugin (requires mypy >= 1.8):

pip install type-enum-plugin

Then register the plugin with

[tool.mypy]
plugins = "type_enum_plugin"

Advanced usage

Exhaustiveness checking

To make exhaustiveness checking work, you first need the mypy plugin, and then you also need to use the special T attribute that is synthesized for each TypeEnum:

from type_enum import Field, TypeEnum

class Color(TypeEnum):
    transparent: Field[()]
    name: Field[str]

def f(color: Color.T) -> str:
    match color:
        case Color.transparent():
            return "no color"
        case Color.name(color_name):
            return color_name

assert f(Color.transparent()) == "no color"

The requirement to use .T is a limitation of the mypy plugin, and hopefully will be removed in the future.

Generics

The .T attribute can also be used to specify type arguments for generic TypeEnums:

from typing import Generic, Tuple, Type, TypeVar

from type_enum import Field, TypeEnum

U = TypeVar("U")

class Maybe(TypeEnum, Generic[U]):
    nothing: Field[()]
    some: Field[U]

a = Maybe.some[int](3)

def f(x: Maybe.T[int]) -> int:
    match x:
        case Maybe.some(y):
            return y
        case Maybe.nothing():
            return 0

assert f(a) == 3

Project details


Download files

Download the file for your platform. If you're not sure which to choose, learn more about installing packages.

Source Distribution

type_enum-0.5.0.tar.gz (7.8 kB view details)

Uploaded Source

Built Distribution

type_enum-0.5.0-py3-none-any.whl (5.1 kB view details)

Uploaded Python 3

File details

Details for the file type_enum-0.5.0.tar.gz.

File metadata

  • Download URL: type_enum-0.5.0.tar.gz
  • Upload date:
  • Size: 7.8 kB
  • Tags: Source
  • Uploaded using Trusted Publishing? No
  • Uploaded via: twine/4.0.2 CPython/3.12.1

File hashes

Hashes for type_enum-0.5.0.tar.gz
Algorithm Hash digest
SHA256 c9dcb0e4c302c7f44648ae656fce91a4a620b071b5cee3d58f64cbbf902a498a
MD5 ce41e01a8f897037a71051ccde522050
BLAKE2b-256 de3a55c2d7426962b9caefb6995884fcd5ee4cd7905cb698c12d0c12ebdbec69

See more details on using hashes here.

File details

Details for the file type_enum-0.5.0-py3-none-any.whl.

File metadata

  • Download URL: type_enum-0.5.0-py3-none-any.whl
  • Upload date:
  • Size: 5.1 kB
  • Tags: Python 3
  • Uploaded using Trusted Publishing? No
  • Uploaded via: twine/4.0.2 CPython/3.12.1

File hashes

Hashes for type_enum-0.5.0-py3-none-any.whl
Algorithm Hash digest
SHA256 f9482abae65eb80f2ec7fc4f52a1da6172775fd2b33daa60a8c1da5f1370fa95
MD5 2a88aec9ba95664b17a96be798dd880f
BLAKE2b-256 86e52c7b9ad4971be8c1a6af0dac887ce2e6789f6da2d7919171a2c68bcdb47e

See more details on using hashes here.

Supported by

AWS AWS Cloud computing and Security Sponsor Datadog Datadog Monitoring Fastly Fastly CDN Google Google Download Analytics Microsoft Microsoft PSF Sponsor Pingdom Pingdom Monitoring Sentry Sentry Error logging StatusPage StatusPage Status page