Currently Option has type
interface None {
readonly _tag: 'None'
}
interface Some<A> {
readonly _tag: 'Some'
readonly value: A
}
type Option<A> = None | Some<A>
type None = null | undefined
type Option<A> = None | A
OptionOption to backend won't look confusing and won't require additional effortsNone, it's possible to just use them without transformingI can prepare the PR myself if it will be considered a good idea
You can't encode Option<Option<A>> or Option<A | null> with this.
@xuanduc987 good point, but could you please elaborate? It should be actually possible:
type Option<T> = T | null | undefined
const never: Option<never> = undefined
const some = <A>(a: A): Option<A> => a
let opt1: Option<Option<number>> = some(some(1))
opt1 = some(never)
opt1 = never
let opt2: Option<number | null> = some(1)
opt2 = some(null)
@denistakeda
Is null a never, or a some(never), or some(some(never))? It is important for things typeclassesCompactableand functions likecompact` in order to work properly.
a) Your data type does not represent the _possibility_ of having data or not having it (two cases) as you may believe. It represents the reality of _always_ having data, and not two but three different cases to handle ( A | null | undefined). If anything this would lead to more boilerplate when dealing with Option, not less.
b) As others already pointed out, your data type definition makes several instances not implementable. Imagine a series of nullable computations I may want to know which one failed, your data type cannot represent it, because it cannot represent a nested Option in the first place. Moreover, why would I have to be limited by not being able to represent Some<null> or Some<Some<null>>, There's difference between receiving a null from an external api or an undefined, or a key that is defined, but it's value is undefined. Leaking language specifications into a data type is pretty dangerous and makes code, imho, more bug-prone, harder to read and reason about.
c) About the serialization/deserialization issue: the proposed implementation seems unsafe. If anything an Option forces me to handle whether I want an undefined or a null value. undefined is not a valid JSON value, null is.
Your proposed implementation still forces me to handle 3 cases, not just 2. If all you want out of the fold is to have A | undefined it's literally a line of code. Leaking undefined and nulls in application code, rather than at its borders (when communicating with a third party api, either software or some server) is generally dangerous and what type safety tries to avoid. The proposal seem to go into the opposite direction.
d) About the memory issue: could you show any realistic scenario where you had memory bloating by appending a _tag to a data structure? This kind of micro-optimizations are fine as long as they are corroborated by evidence of tangible benefits.
Jm2c but I think you're simply looking for a Nullable type in your code (for which your definition is enough) and you're not interested in all the instances the Option data type offers.
Most helpful comment
You can't encode
Option<Option<A>>orOption<A | null>with this.