JavaScript 非同期同期 例外処理
実行環境
Node - v 14.16.0
例外の基本
try{}で囲ってる箇所に例外が起こりえるような処理を書いて、 もし例外が発生したらcatch{}の中に書いた処理を実行する。
finallyは実行してほしいような処理がある場合使う。
try { // 例外が発生するかもしれない処理 } catch (error) { // 例外発生時の処理 } finally { // 必ず実行される処理 }
例外の基本の書き方ですが、ファイルを読込処理をしていた時に 例外が拾えずはまったのでもう一度復習。
コールバックについて
非同期
ファイルを読み込むためにfsモジュールを使います。
const fs = require('fs'); fs.readFile('./saplme.txt');
このままだとエラーとなります。
TypeError [ERR_INVALID_CALLBACK]: Callback must be a function. Received undefined
仕様が変更されてfsモジュール使用時にコールバック関数がMustになっているため追加します。
const fs = require('fs'); fs.readFile('./sample.txt', (error, txt) => { if (error) { console.log(error); } else { console.log(txt.toString()); } });
第一引数はerrorが起こった場合、エラーオブジェクトが入ります。
第二引数は読み込めた場合、読み込んだ内容が入ります。
無事にtxtファイルの中身sampleが表示されました。
sample!
次にtrycatchで囲んだ後に例外を発生させてみましょう。
先ほどのsample.txtを削除して読み込めなくします。
その後にthrowでcatchさせるようにします。
テキストファイルが読み込めなかった場合。
const fs = require('fs'); try { fs.readFile('./sample.txt', (error, txt) => { if (error) { console.log('callback'); throw error.message; } else { console.log(txt.toString()); } }); } catch (err) { console.log('catch'); console.log(err.message); }
callback ENOENT: no such file or directory, open 'C:\repos\javasc\sample.txt' (Use `node --trace-uncaught ...` to show where the exception was thrown)
結果からわかるようにコールバック関数を用いたエラーハンドリングでは、trycatchを外側に書くと拾うことはできないようです。
次はコールバック関数の中でtrycatchで拾うようにしてみます。
const fs = require('fs'); try { fs.readFile('./sample.txt', (error, txt) => { try{ if (error) { console.log('callback'); throw error; } else { console.log(txt.toString()); } }catch(innnerError){ console.log("innnerCatch") console.log(innnerError.message); } }); } catch (err) { console.log('catch'); console.log(err.message); }
無事拾うことができました。
可読性がひどいのでtrycatchではなくコールバック関数でエラーハンドリングすべきですね!
callback innnerCatch ENOENT: no such file or directory, open 'C:\repos\javasc\sample.txt'
同期
const fs = require('fs'); try { var txt = fs.readFileSync('./sample.txt'); console.log(txt.toString()); } catch (err) { console.log(err.message); }
trycatchは同期的に動くため、同期処理の場合はcatchできるようです。
catch ENOENT: no such file or directory, open './sample.txt'
結論
- 非同期の場合はコールバック関数でのエラーハンドリング
- 同期の場合はtrycatchでのエラーハンドリング