More ergonomic runtime representation of variants #512
Replies: 9 comments
-
Yes, for nullary constructors, it's better to use plain string. For non-nullary constructors, we can also use kind, e.g.
|
Beta Was this translation helpful? Give feedback.
-
Yes that also works.
Indeed, this would support TypeScript's discriminated unions and checks for exhaustive pattern matching. From a quick scan of the candid spec, it seems that because of sub typing:
Mentioning this as in the mixed case, then one would not be able to pattern match all cases in TS with a simple |
Beta Was this translation helpful? Give feedback.
-
Depends on the Candid/Motoko type.
I don't see why that's the case. For mixed types, we will use kind for nullary constructors to keep the representation consistent. We only use strings when all constructors are nullary. In general, I think it should be the developers' choice to decide how to represent candid types in the host language. We probably need a config language to guide the compiler for how to generate bindings. This problem becomes more prominent for Rust bindings, considering one candid type can map to multiple types in Rust with different lifetime, mutability, reference, etc. |
Beta Was this translation helpful? Give feedback.
-
Oh that's right. |
Beta Was this translation helpful? Give feedback.
-
Another type that is currently not ergonomic is the option type. |
Beta Was this translation helpful? Give feedback.
-
Right. The promise of subtyping is that when one party upgrades the interface, the other party with the old interface can still decode the message. When the server side adds a non-nullary constructor, the JS side with the old interface will ignore the new field, and considers the type to be nullary constructors only. So the representation in JS side is unchanged. But when the JS side upgrades its interface, it's more work to change all the existing patterns. That's a cons for specializing on nullary constructors.
Agreed. That's a good suggestion. We didn't explicitly define |
Beta Was this translation helpful? Give feedback.
-
Also, type variables would have to be considered nullable. So |
Beta Was this translation helpful? Give feedback.
-
We don't have type variables in Candid. All types are monomorphized when translating to Candid. Things may change with dfinity/candid#245, but most likely generic data will be a syntactic sugar or an opaque blob. |
Beta Was this translation helpful? Give feedback.
-
I still think we can do something more satisfactory here. Standardizing around a "kind" attribute that will definitely be present would be a step forward for JS ergonomics, in my opinion |
Beta Was this translation helpful? Give feedback.
-
Is your feature request related to a problem? Please describe.
The following variant declaration
has this runtime representation:
Here are patterns one could try to use for a function to check whether a value represents
#a
:There's no help that the TypeScript type checker can give to figure out the correct pattern.
Describe the solution you'd like
One possible idiomatic representation, at the cost of some reduced uniformity (variants with no arguments represented differently from variants with arguments):
Beta Was this translation helpful? Give feedback.
All reactions