Node
nodejs
readline
getchar

Node.jsでC言語のgetchar()マクロ(getc()関数)に相当するような、標準入力から1文字文字を読みとる処理を書くやりかた。NPMを使わずに手軽に直接できる方法を見つけられなかったため作成。仕様は以下のとおり。

  • Promiseベース。以下で「〜を返す」は、「〜をPromiseのresolve値とするPromiseを返す」と読みかえてほしい。
  • 呼ぶごとに標準入力から1文字ずつ取得したUnicodeのコードポイント値を返す。readlineから得たstringからcharCodeAtしているのでサロゲートペアは別に対処が必要。
  • バッファにデータがなければブロッキングして入力を待つ(stdinがTTYの場合)。
  • 行単位のバッファリングは行う。改行キーを押さない限りブロックは解除されない。
  • バッファにデータが存在する限り、バッファから1文字を取り出し文字コードを返す。
  • EOFでnullを返す。
const readline = require('readline');
const rl  = readline.createInterface(process.stdin);
let buf = "";

function getchar() {
  if (buf.length == 0) {
    if (process.stdin.AtEndOfStream) {
      return Promise.resolve(null); // EOF
    }
    return new Promise((resolve, reject) => {
      rl.once('line', (line) => {
        buf = buf + line + "\n";
        resolve(getchar());
      });
    });
  } else {
    const result = buf.charCodeAt(0);
    buf = buf.substring(1);
    return Promise.resolve(result);
  }
}

async function test() {
  let ch
  while ((ch = await getchar()) !== null) {
    console.log(ch);
  }
}

test();