Skip to content

Instantly share code, notes, and snippets.

@thejefflarson
Last active May 23, 2018 21:36
Show Gist options
  • Star 0 You must be signed in to star a gist
  • Fork 0 You must be signed in to fork a gist
  • Save thejefflarson/039426f675e4a01231807842bcacc14a to your computer and use it in GitHub Desktop.
Save thejefflarson/039426f675e4a01231807842bcacc14a to your computer and use it in GitHub Desktop.
class Thing {
val = null;
constructor(val) {
this.val = val;
}
unwrap() {
throw "unimplemented!";
}
is_ok() {
throw "unimplemented!";
}
is_err() {
throw "unimplemented!";
}
}
export class Ok extends Thing {
unwrap = () => this.val;
is_ok = () => true;
is_err = () => false;
}
export class Err extends Thing {
unwrap = () => throw this.val;
is_ok = () => false;
is_err = () => true;
}
export class Result {
val = null;
constructor(val) {
this.val = val
}
and(val) {
if(this.val.is_ok() && val.is_ok()) {
return new Result(val);
} else {
if(this.val.is_err()) {
return new Result(this.val);
} else if(val.is_err()) {
return new Result(val);
}
}
}
and_then(cb) {
if(this.val.is_ok()) {
return cb(this.val);
} else {
return new Result(this.val)
}
}
or(val) {
if(this.val.is_ok()) {
return new Result(this.val);
} else {
return new Result(val);
}
}
unwrap() {
return this.val.unwrap();
}
static async try(promise) {
try {
return new Result(new Ok(await promise));
} catch(e) {
return new Result(new Err(e));
}
}
}
export const R = Result.try;
// examples
const throws = new Promise((_, reject) => reject("blowup"));
const one = new Promise((r) => 1);
const two = new Promise((r) => 2);
const unsafeThing = (await Result.try(throws)).unwrap();
const safe = (await Result.try(one)).and(await Result.try(two)).unwrap(); // 2
const unsafeToSafe = (await Result.try(throws)).or(new Ok(2)).unwrap(); // 2
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment