Docsの目次

最初の小さなCLIアプリ

Docsの目次 · 前:準備と最初の実行 · 次:コードを書きながら学ぶ

入力した金額が1,000円以内かを判定するCLIアプリを作ります。Nagiの公開compilerをインストールし、Rust/CargoとCのビルド環境を用意してください。準備がまだならセットアップを先に進めます。

この例は1行の入力だけを扱い、結果を画面に表示します。ファイルやDBには保存しません。データ保存を追加するときはSQLiteの現在のAPIと制約を確認してください。

このページの目次

1. 作業フォルダーとファイルを作る

ターミナルで作業場所を選び、次のコマンドを実行します。nagi-budgetという新しいフォルダーを作り、その中を作業場所にします。

mkdir nagi-budget
cd nagi-budget

このフォルダーにfirst_app.nagiを作り、次のコードを保存してください。同じコードはリポジトリの実行例にあります。

def within_budget(amount_text: view[str], limit: i64) -> Result[bool, Error]:
    amount = try parse_i64(amount_text)
    if amount < 0:
        return error("amount must be non-negative")
    return ok(amount <= limit)

def main() -> Result[unit, Error]:
    print("Enter a whole-number amount:")
    text = try read_line()
    fits = try within_budget(view(text), 1000)
    if fits:
        print("within budget")
    else:
        print("over budget")
    return ok(print("done"))

mkdirとcdは成功すると何も表示しません。エディターで保存したファイルがnagi-budget/first_app.nagiにあることを確認してください。フォルダーが既にある場合は、mkdirを繰り返さずそのフォルダーへ移動します。

within_budgetは入力文字列を整数に変換します。view[str]は文字列を読むための借用で、parse_i64の失敗はResult[i64, Error]として返ります。tryは失敗をこの関数の呼び出し元へ伝えます。負の金額を拒否した後、okで判定結果を返します。mainでもtryを使うため、mainの戻り値はResultです。

初出の用語は、viewとownershipとResult・try・matchで詳しく確認できます。unitは値を返さない処理の型で、ここではprintの結果をok(...)に入れています。

2. 検査して動かす

同じ作業フォルダーで、compilerの版とソースを確認します。

nagic --version
nagic check first_app.nagi

対象compilerがNagi 0.1.11なら、版表示はnagic 0.1.11です。checkが成功すると終了コードは0で、Nagiの構文・型・所有権について診断がありません。checkはRust/Cargoのビルドを行いません。

成功時はcheckedに続いて確認したファイルのpathが表示されます。失敗した場合はsourceの行を確認し、nagic --versionで0.1.11以降を使っていること、first_app.nagiを作業フォルダーに保存したことを確かめてください。

LinuxとmacOSでは、標準入力から金額を渡して実行できます。

printf '700\n' | nagic run first_app.nagi

PowerShellでは同じ確認を次のように実行できます。

"700" | nagic run .\first_app.nagi

アプリの標準出力は次のとおりです。compilerの進捗やエラーは別の診断として表示されることがあります。

Enter a whole-number amount:
within budget
done

runはRust/Cargoによるアプリのbuildと実行を行います。そのためcheckが通っても、C compilerやlinkerがない、依存を取得できない、といった理由で実行前に失敗することがあります。準備はセットアップ、build診断は検査とビルドを確認してください。

3. 境界値を試して間違いを直す

実際に間違いを観測するため、within_budgetのreturn ok(amount <= limit)を一時的にreturn ok(amount < limit)へ変更して保存します。作業フォルダーからcheckし、上限と等しい1000を入力してください。

nagic check first_app.nagi
printf '1000\n' | nagic run first_app.nagi
nagic check .\first_app.nagi
"1000" | nagic run .\first_app.nagi

この状態では1000の判定行がover budgetになります。上限と等しい額も受け入れるため、比較をamount <= limitへ戻して保存します。nagic check first_app.nagiをもう一度実行し、次の3入力で修正を確認してください。

入力 期待する出力 確かめること
700 within budget 上限より小さい値
1000 within budget 上限と等しい値
1001 over budget 上限より大きい値

1000でover budgetになったら、比較をamount <= limitへ直します。nagic check first_app.nagiを再実行し、3入力の結果をもう一度確かめてください。

LinuxとmacOSでは次の3コマンドを実行します。PowerShellでは右の3行を使います。

printf '%s\n' '700' | nagic run first_app.nagi
printf '%s\n' '1000' | nagic run first_app.nagi
printf '%s\n' '1001' | nagic run first_app.nagi
"700" | nagic run .\first_app.nagi
"1000" | nagic run .\first_app.nagi
"1001" | nagic run .\first_app.nagi

各コマンドはプロンプトの後に表の判定、doneの順で表示します。abcは数値変換の失敗、-1はアプリが作った失敗として終了コード1になります。次の表は、compiler診断ではなく、起動したアプリが実行時に表示するエラーです。Nagi 0.1.11での表示は次のとおりです。

入力 実行時エラー出力 exit code
abc Invalid: invalid digit found in string 1
-1 Invalid: amount must be non-negative 1

Linux/macOSではprintf '%s\n' 'abc'またはprintf '%s\n' '-1'を、PowerShellでは"abc"または"-1"を同じようにpipeして確認できます。実行時エラーが表示されたらResultの伝播と回復を確認してください。アプリが起動する前にcompilerやCargoの診断が出た場合は、前節のbuild準備と検査とビルドを確認します。

負数はアプリが作ったError、abcはparse_i64が返すErrorになります。どちらもtryを通ってmainへ伝わります。失敗をその場で別の値に置き換える方法はResultとエラー処理を参照してください。

開発中のNagiには組み込みの単体テストフレームワークはありません。ここでは小さな入力表を手動で実行し、期待結果と比較します。compiler本体を変更するときの自動回帰テストは貢献ガイドとcompiler test guideを参照してください。

4. 次に広げる

関数、List、class、ループ、enum、nullable、Result、matchの使い分けは言語ガイドと言語機能索引へ。入力を複数ファイルに分けるときはimportとmodule、別の値を安全に受け渡すときはownershipとborrow、Rustライブラリを呼ぶときはRust連携を読みます。

Nagi 0.2.0 · Docsこのページのソース