part3 - コマンドの実装
前回はユーザーの作成機能について考えた。今回は、コマンドについて考える。
CREATEやREADのようなコマンドを実装する必要がある。まずは、前回作成したcreate関数をcreateモジュールに移動しよう。
Create.fsの作成
module create
open System.IO
let counterDirectory = Path.Combine(".", "counter")let counterFile = Path.Combine(counterDirectory, "counter.txt")
let readCounter = if File.Exists(counterFile) then let counter = File.ReadAllText(counterFile) counter |> int else Directory.CreateDirectory(counterDirectory) |> ignore File.WriteAllText(counterFile, "1") |> ignore 1
let incrementCounter = let counter = readCounter + 1 File.WriteAllText(counterFile, counter.ToString()) |> ignore counter
let create = // まずはコンソールを全消去する。 System.Console.Clear()
Directory.CreateDirectory("./users") |> ignore
printfn "名前を入力してください(1文字以上、150字以内)。" let name = stdin.ReadLine()
printfn "年齢を入力してください(0以上、150以下)。" let age = stdin.ReadLine()
printfn "メールアドレスを入力してください(任意)。" let email = stdin.ReadLine()
let id = incrementCounter
let csvData = sprintf "%d,%s,%s,%s" id name age email
let path = Path.Combine("./users", id.ToString() + ".csv") File.WriteAllText(path, csvData) |> ignorefsprojの修正
fsprojファイルにCreate.fsを追加しよう。
// crud.fsproj<Project Sdk="Microsoft.NET.Sdk">
<PropertyGroup> <OutputType>Exe</OutputType> <TargetFramework>net9.0</TargetFramework> </PropertyGroup>
<ItemGroup> <Compile Include="Create.fs" /> <Compile Include="Program.fs" /> </ItemGroup>
</Project>オフサイドルールのため、createモジュールをProgram.fsで使うためには、必ず先にCreate.fsをコンパイルする必要がある。
コマンドの実装
次に、Program.fsでCommandの型を定義してみよう。
type Command = | Create | Read | Help | Unknown of string本当は他にもいろいろあるのだが、今回はこの3つだけで十分だろう。
入力されたコマンドをparseする関数も作成する。
let parseCommand args = match args with | [| "create" |] -> Create | [| "read" |] -> Read | [| "--help" |] -> Help | [| "-h" |] -> Help | [||] -> Help // コマンドがないときもヘルプを表示 | _ -> Unknown args.[0]helpをprintするコマンドもついでに作成しておく。
let showHelp = printfn "Usage: dotnet run [command]" printfn "Commands:" printfn " create Create a new user" printfn " read <ID> Read a user by ID" printfn " update Update a user by ID" printfn " delete <ID> Delete a user by ID" printfn " list List all users" printfn " --help, -h Show this help"まだupdateやdelteなどは実装していないが良いことにしよう。
あとは、EntryPointでコマンドをparseして、それに応じた処理を行うようにする。
[<EntryPoint>]let main argv = let command = parseCommand argv
match command with | Create -> create | Read -> printfn "read" | Help -> showHelp | Unknown s -> printfn "Unknown command: %s" s
0EntryPointとはプログラムの実行を開始する関数のことで、main関数がそれにあたる。argvとはコマンドライン引数のことで、dotnet run createのように実行すると、argvには[| "create" |]が入る。もし、パースできないaaaのようなコマンドが入力された場合は、Unknownとして扱う。
いままでの実装をまとめると、以下のようになる。
open create
type Command = | Create | Read | Help | Unknown of string
let parseCommand args = match args with | [| "create" |] -> Create | [| "read" |] -> Read | [| "--help" |] -> Help | [| "-h" |] -> Help | [||] -> Help // コマンドがないときもヘルプを表示 | _ -> Unknown args.[0]
let showHelp = printfn "Usage: dotnet run [command]" printfn "Commands:" printfn " create Create a new user" printfn " read <ID> Read a user by ID" printfn " update Update a user by ID" printfn " delete Delete a user by ID" printfn " list List all users" printfn " --help, -h Show this help"
[<EntryPoint>]let main argv = let command = parseCommand argv
match command with | Create -> create | Read -> printfn "read" | Help -> showHelp | Unknown s -> printfn "Unknown command: %s" s
0これで、dotnet run createと実行すると、ユーザーの作成が行われるようになる。
dotnet runだけで実行すると、ヘルプが表示されるようになる。
まとめ
さて、これでコマンドの実装ができた。次回は、ユーザーの読み込み機能を実装していこう。