Don’t use try catch in JavaScript
-
Upload
tetsuharu-ohzeki -
Category
Engineering
-
view
2.923 -
download
0
Transcript of Don’t use try catch in JavaScript
DON’T USE TRY-CATCH
Tetsuharu OHZEKI aka @saneyuki_s
April 5, 2016. 東京node学園 #20
ABOUT ME
• Tetsuharu OHZEKI
• twitter: saneyuki_s
• Open Source Contributor
• Mozilla Committer
• Firefox, Servo (as reviewer)
• ReactiveX/RxJS
• And some others…
• whatwg html, etc
• Working at VOYAGE GROUP, inc.
• My main work is to develop an advertising management system with using
TypeScript, babel compiler, React, and RxJS.
DO YOU USE TRY-CATCH?
DO YOU THROW AN ERROR?
TWO TYPES OF “ERROR”
•Just a Bug• NullPointerException, TypeError, calling undefined methods, not found a
required file, etc...
•Recoverable Errors• Network timeout, JSON parse errors, etc…
CAN YOU RECOVER A BUGIN A RUNNING APPLICATION?
No• A bug is just a programming mistake.
• Don’t recover them.
• So “let it crash”, “abandonment”, “fail-fast” immediately.
• Even if you success recovering from their fatal,there’re some serious conformity problem in your heap.
Promise/Observable .catch() are any type in TypeScript definitions. This is a hole for type
restriction.
interface Promise<T> {
catch(onrejected?: (reason: any) => T | PromiseLike<T>):
Promise<T>;
catch(onrejected?: (reason: any) => void): Promise<T>;
}
interface Observable<T> {
catch<R>(selector: (err: any, caught: Observable<T>) =>
Observable<R>): Observable<R>;
}
CAN WE USE TRY-CATCH FOR RECOVERABLE?
• I don’t think so excluding some exceptions…
• (of course, we have to handle errors from builtin
object, dom, libraries, ete with try-catch)
• “error throw-ablity” should be restricted by a
function signature.
• should force an error handling for a caller!
function parseJSON(obj) {
try {
const value = JSON.parse(obj);
return value;
}
catch (e) {
return null;
}
}
HOW DO WE REPRESENT“ERROR THROWABLE” TYPE?
RETURN A “RESULT TYPE” THAT IS LIKE A ITERATOR’S RESULT.
interface ErrorContainableResult<T, E> {
ok: boolean;
value: T;
error: E;
}
const { ok, value, error } = doSome();
if (ok) {
// handle value
}
else {
// handle error
}
doSomePromise().then((result) => {
const { ok, value, error } = result;
if (ok) {
// handle value
}
else {
// handle error
}
}, (unrecover) => crash(unrecover)).;
doSomeRxObservable().subscribe((result) => {
const { ok, value, error, } = result;
// blah, blah, blah
}, (unrecover) => crash(unrecover));
process.on(‘uncaughtException’, (reason) => {
// dump error report
process.exit();
});
throw new Error(‘Hello! This is fatal bug’);
INTRODUCE RESULT<T, E>
RESULT<T, E>
• Result<T, E> == Either<A, B>
• You can use it from npm:option-t• APIs are inspired by Rustlang’s std::result
• There are some instance methods
• This provides “utility” object & methods.
• You can same things with destructuring assignment.
const result = getSomeResult();
if ( result.isOk() ) {
// success
}
else {
// error
}
const result = getSomeResult();
const value: string = result
.map((v: number) => String(v)).unwrap();
const first = getSomeResult();
const second = first.andThen(first => {
return getSecondResult(first);
});
type Result<T, E> = Ok<T, E> | Err<T, E>;
class Ok<T, E> implements ResultMethods<T, E>;
class Err<T, E> implements ResultMethods<T, E>;
interface ResultMethods<T, E> {
ok(): Option<T>;
err(): Option<E>;
isOk(): boolean;
isErr(): boolean;
map<U>(op: MapFn<T, U>): Result<U, E>;
mapErr<F>(op: MapFn<E, F>): Result<T, F>;
andThen<U>(op: FlatmapOkFn<T, U, E>): Result<U, E>;
orElse<F>(op: FlatmapErrFn<T, E, F>): Result<T, F>;
unwrap(): T;
unwrapErr(): E;
}
SEEHTTPS://DOC.RUST-LANG.ORG/BOOK/ERROR-
HANDLING.HTML
DRAWBACKS IN JAVASCRIPT
• Need a extra object allocation cost
• In the future, JavaScript runtime may make the cost more cheap.
• Don’t use them if you require computation performance
extremely.
• Result<T, E> type needs static type analytics for more
convenient/secure programming (but plain JavaScript is not so).
• Let’s use with TypeScript or Flowtype
•DO NOT TRY TO RECOVER A BUG
• Don’t suppress a bug. FIX it.
•Don’t use try-catch
• Excluding: Runtime provided functions (include JSON.parse, DOM),ssand 3rd
party libraries.
•Tell “Error-Throwable” via function signature.