Open
Description
Hello again!
In my project, I use a lot of enums, and it is often desirable to match on the variants.
As a result, it'd be nice if something like this:
#[tsync]
struct AppleData {
crunchy: bool
}
#[tsync]
struct BananaData {
size: i32
}
#[tsync]
struct CarrotData {
color: String
}
#[tsync]
enum Fruit {
Apple(AppleData),
Banana(BananaData),
Carrot(CarrotData),
}
Converted to something like this:
export interface AppleData {
crunchy: boolean
}
export interface BananaData {
size: number
}
export interface CarrotData {
color: string
}
const enum FruitKinds {
Apple,
Banana,
Carrot
}
export interface CaseFruitApple {
kind: FruitKinds.Apple;
data: AppleData;
}
export interface CaseFruitBanana {
kind: FruitKinds.Banana;
data: BananaData;
}
export interface CaseFruitCarrot {
kind: FruitKinds.Carrot;
data: CarrotData;
}
export type Fruit =
| CaseFruitApple
| CaseFruitBanana
| CaseFruitCarrot;
My reasoning:
It provides the frontend code with everything it needs. Many functions may only be interested in the case for the banana, and can take just that as a parameter. It makes it so that none of the frontend types are anonymous anymore. It also provides an enum of all the variants as well, since that is often useful. And it allows for a full conversion of the ADT pattern, such that you can narrow the types in the frontend code. For example:
function renderApple(apple: AppleData) {
// type-safe and narrowed to an apple
}
function renderBanana(apple: BananaData) {
// type-safe and narrowed to a banana
}
function renderCarrot(apple: CarrotData) {
// type-safe and narrowed to a carrot
}
switch (fruit.kind) {
case FruitKinds.Apple: return renderApple(fruit.data);
case FruitKinds.Banana: return renderBanana(fruit.data);
case FruitKinds.Carrot: return renderCarrot(fruit.data);
}
Thoughts?
Metadata
Metadata
Assignees
Labels
No labels