ora の使い方 — ターミナルにエレガントなスピナーを表示するnpmパッケージ
一言でいうと
ora は、CLIツールやNode.jsスクリプトのターミナル出力にアニメーション付きスピナー(ローディングインジケーター)を簡単に表示できるパッケージです。処理の進行中であることをユーザーに視覚的に伝え、成功・失敗・警告などの結果表示まで一貫して扱えます。
どんな時に使う?
- CLIツールの開発時 — API呼び出しやファイル処理など、時間のかかる処理中にユーザーへフィードバックを返したいとき
- デプロイスクリプトやビルドツール — 複数ステップの処理を順番に実行し、各ステップの進行状況と結果(✔ / ✖)を表示したいとき
- データベースマイグレーションやバッチ処理 — 長時間実行されるスクリプトで、処理がフリーズしていないことをユーザーに示したいとき
インストール
# npm
npm install ora
# yarn
yarn add ora
# pnpm
pnpm add ora
注意: ora v9 は ESM (ES Modules) 専用です。
"type": "module"がpackage.jsonに設定されているか、.mjs拡張子を使用する必要があります。CommonJS (require) では利用できません。
基本的な使い方
import ora from 'ora';
const spinner = ora('データを取得中...').start();
try {
const data = await fetch('https://api.example.com/data');
const json = await data.json();
spinner.succeed('データの取得が完了しました');
} catch (error) {
spinner.fail('データの取得に失敗しました');
process.exit(1);
}
ターミナルには以下のように表示されます:
⠋ データを取得中...
↓(処理完了後)
✔ データの取得が完了しました
よく使うAPI
1. ora(options) — スピナーの作成
文字列を渡すとテキスト付きスピナーを生成します。オブジェクトを渡すと詳細なオプションを指定できます。
import ora from 'ora';
// シンプルな使い方
const spinner1 = ora('Loading...').start();
// オプション指定
const spinner2 = ora({
text: 'ファイルを処理中...',
color: 'yellow',
spinner: 'dots', // スピナーの種類(dots, line, arc など多数)
prefixText: '[STEP 1]', // スピナーの前に表示するテキスト
indent: 2, // インデント(スペース数)
}).start();
2. .succeed() / .fail() / .warn() / .info() — 結果の表示
スピナーを停止し、結果に応じたシンボルとテキストを表示します。
import ora from 'ora';
const spinner = ora('処理中...').start();
// 成功: ✔(緑)
spinner.succeed('処理が完了しました');
// 失敗: ✖(赤)
// spinner.fail('処理に失敗しました');
// 警告: ⚠(黄)
// spinner.warn('一部のファイルがスキップされました');
// 情報: ℹ(青)
// spinner.info('3件のファイルが見つかりました');
3. .text / .color / .spinner — 動的なプロパティ変更
スピナーの回転中にテキストや色を動的に変更できます。
import ora from 'ora';
const spinner = ora('ステップ 1/3: 設定を読み込み中...').start();
// 1秒後にテキストと色を変更
setTimeout(() => {
spinner.text = 'ステップ 2/3: データを変換中...';
spinner.color = 'yellow';
}, 1000);
// 2秒後にさらに変更
setTimeout(() => {
spinner.text = 'ステップ 3/3: 結果を書き込み中...';
spinner.color = 'green';
}, 2000);
// 3秒後に完了
setTimeout(() => {
spinner.succeed('すべてのステップが完了しました');
}, 3000);
4. oraPromise() — Promiseと連携したスピナー
Promiseの解決/拒否に応じて自動的にスピナーを制御します。ボイラープレートを大幅に削減できます。
import { oraPromise } from 'ora';
async function fetchUsers(): Promise<{ name: string }[]> {
const res = await fetch('https://api.example.com/users');
return res.json();
}
// Promiseが解決すれば succeed、拒否されれば fail が自動で呼ばれる
const users = await oraPromise(fetchUsers(), {
text: 'ユーザー一覧を取得中...',
successText: (result) => `${result.length}件のユーザーを取得しました`,
failText: (error) => `取得失敗: ${error.message}`,
});
console.log(users);
5. .stopAndPersist() — カスタムシンボルで停止
succeed / fail 以外の独自シンボルでスピナーを停止・表示を残したい場合に使います。
import ora from 'ora';
const spinner = ora('チェック中...').start();
spinner.stopAndPersist({
symbol: '🚀',
text: 'デプロイ準備完了',
suffixText: '(v2.1.0)',
});
// 出力: 🚀 デプロイ準備完了 (v2.1.0)
類似パッケージとの比較
| パッケージ | サイズ | ESM/CJS | 特徴 |
|---|---|---|---|
| ora | ~30KB | ESM のみ | 豊富なAPI、Promise連携、多数のスピナー種類 |
| yocto-spinner | ~3KB | ESM のみ | ora作者による軽量版。最小限のAPIで十分な場合に最適 |
| nanospinner | ~3KB | ESM + CJS | 軽量でCJS対応。シンプルなユースケース向け |
| cli-spinners | ~5KB | ESM + CJS | スピナーのアニメーション定義のみ(表示ロジックなし) |
| log-symbols | ~2KB | ESM のみ | ✔ ✖ ⚠ ℹ のシンボルのみ提供。スピナー機能なし |
選定の目安:
- フル機能が必要 → ora
- バンドルサイズを最小化したい → yocto-spinner または nanospinner
- CommonJS が必須 → nanospinner
注意点・Tips
ESM 専用パッケージである
ora v9 は ESM のみ対応です。CommonJS プロジェクトで使いたい場合は、import() による動的インポートか、プロジェクト自体の ESM 移行を検討してください。
// CommonJS プロジェクトでの動的インポート(非推奨だが回避策)
const { default: ora } = await import('ora');
同期処理でスピナーがフリーズする
JavaScriptはシングルスレッドのため、CPU集約的な同期処理を行うとスピナーのアニメーションが止まります。重い処理は非同期API、Worker Thread、または子プロセスで実行してください。
// ❌ スピナーがフリーズする
const spinner = ora('処理中...').start();
heavySyncOperation(); // ブロッキング処理
spinner.succeed();
// ✅ 非同期で実行する
const spinner = ora('処理中...').start();
await heavyAsyncOperation(); // ノンブロッキング
spinner.succeed();
discardStdin オプションに注意
デフォルトで discardStdin: true が設定されており、スピナー回転中のキー入力が破棄されます。スピナー実行中にユーザー入力を受け付けたい場合は false に設定してください。また、discardStdin が有効な状態で同期処理がイベントループをブロックすると、Ctrl+C の応答が遅れる点にも注意が必要です。
テキストの色を変えたい場合は chalk / yoctocolors を併用
color オプションはスピナーのシンボル部分の色のみを変更します。テキスト部分の色を変えるには chalk などを組み合わせます。
import ora from 'ora';
import chalk from 'chalk';
const spinner = ora(`${chalk.bold('重要:')} データベースをマイグレーション中...`).start();
spinner.succeed(`${chalk.bold('重要:')} マイグレーション完了 ${chalk.gray('(2.3s)')}`);
CI環境やパイプ時の挙動
TTYでない環境(CI、パイプ出力など)ではスピナーのアニメーションとANSIエスケープコードが自動的に無効化されます。テキスト自体は出力されるため、ログとしては機能します。強制的に有効/無効にしたい場合は isEnabled オプションを使用してください。
まとめ
ora は、CLIツール開発における「処理中」の表示を、わずか数行のコードでエレガントに実現できるパッケージです。succeed / fail による結果表示、oraPromise によるPromise連携、動的なテキスト・色の変更など、実用的なAPIが揃っています。軽量さを重視する場合は同作者の yocto-spinner も検討しつつ、機能の充実度で選ぶなら ora が第一選択肢となるでしょう。