Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Clean up “Pure Error Handling” #371

Open
datenreisender opened this issue Jan 26, 2018 · 1 comment
Open

Clean up “Pure Error Handling” #371

datenreisender opened this issue Jan 26, 2018 · 1 comment
Labels

Comments

@datenreisender
Copy link
Contributor

The section Pure Error Handling got more confusing during the recent update to ES6:

E.g. it says „ I've skipped the ceremony of creating the Either superclass“ while actually in the code that superclass is created.

And before Right and Left were more similar, e.g. both had a function of. Now a Left is created through the little standalone function left, while a Right is created through Either.of. It would be better, to make RIght and Left more similar again, by again giving both a static method of.

@KtorZ KtorZ added the FAQ label Jan 28, 2018
@KtorZ
Copy link
Member

KtorZ commented Jan 28, 2018

Well, yes and no ^.^

We definitely need to rephrase a bit the paragraph below the definition of Either and Right. About the of function, this is an issue that was discussed before (and I am sorry, I couldn't my hand back on this issue...).

of is actually an interface defined on different data structure. Usually, it goes under the Applicative flag, though in this book, @DrBoolean has chosen to present separately (Pointed) to ease the introduction of concepts. This interface gives a common way to put values into a minimal default context, i.e. to place a raw value inside a 'container'.

Yet, everything here is more or less linked to an underlying type-system and each type that implement the Pointed interface provides an of method. If you put this in perspective, it also means that there's one of method per type because the meaning of of has to be clear. Left and Right aren't types; they're rather constructors of the same type (Either a b). Thus, there's one of method actually bound to Either a b. Why the value is placed as a Right b and not a Left a stands more, in my opinion, as a convention and the common usage of those data structure: the value is put on the truthy side of the structure (look at Task.of and Maybe.of).

One thing to also have in mind is that JavaScript isn't statically typed and for that reason, we have to keep this of interface linked to a type and declared as part of the type representing that class. This is rather different in languages like Haskell or PureScript where the type-system itself can help figuring out to which type of would refer. For instance, imagine the following function and implementation.

// liftA2 :: (a → b → c) → Either String a → Either String b → Either String c
liftA2 = (fn, a1, a2) => of(fn).ap(a1).ap(a2) 

The signature is a bit restrictive here as nothing in the implementation really leverages the fact that a1 and a2 are Eithers. Therefore, we could simply go for:

// liftA2 :: (Pointed f, Applicative f) ⇒ (a → b → c)→f a → f b → f c
liftA2 = (fn, a1, a2) => of(fn).ap(a1).ap(a2)

Usually, the context will tell a compiler of interpreter what concrete type if f, or if the compiler isn't able to infer it all alone, one may provide an extra type annotation. However, the type is known statically, at compile-time. The value is only known at runtime. In the case of Either, it means that, you can indeed know that a given expression manipulates of returns an Either and what of gives you is a mean to at some point, transform any value of type b into a value of type Either a b. It doesn't tell much about whether it's a Left or a Right because those belongs to the world of values. It wouldn't be much practical to have 2 of functions, both returning an Either a b but of a very different shape one on the Left side and one on the Right side. In the case of liftA2, which one would you (a.k.a the compiler, yes, you're a compiler now!) choose? Both function would have same signature and would fit fine the equation.

As a matter of fact, it is simply wrong to define Left.of because it doesn't much fit the definition of the Pointed interface and breaks equational reasoning. There should be only one way to put a value in a default minimal context for a given type, and for Either, it was decided that it will be on the Right side.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
Projects
None yet
Development

No branches or pull requests

2 participants