More than 1 year has passed since last update.

phoenixプロジェクトでstate_mcの使い方について説明したいと思います。

state_mcとはelixirのEcto用のstatemachineライブラリです。


Ectoのstate_mcライブラリ


インストール

まず、phoenixプロジェクトのmix.exsに追加します。

  def deps do

[{:state_mc, "~> 0.1.0"}]
end

そして、mix deps.getコマンドを実行し、パッケージをインストールします。


使い方

以下のサンプルを一緒に見ましょう。

defmodule Example.User do

use Example.Web, :model

# StateMc.EctoSMをインポートする
import StateMc.EctoSm

schema "users" do
# stateカラム
field :state, :string, default: "waiting"
end

# statemcとはmacroです。第一引数はステータスを格納するカラム名です。
statemc :state do

# defstateマクロで、ステータス配列を定義します。
defstate [:waiting, :approved, :rejected]

# defeventマクロで、イベントを定義します。
# ステータスを:waitingあるいは:rejectedから:approvedに変更するイベント
defevent :approve, %{from: [:waiting, :rejected], to: :approved}, fn(changeset) ->
# ここはコールバックです。changeset引数を使用して、DBにステータスを格納するなど、自由に処理できます。
changeset
|> Example.Repo.update()
end

# ステータスを:waitingから:rejectedに変更するイベント
defevent :reject, %{from: [:waiting], to: :rejected}, fn(changeset) ->
changeset
|> Example.Repo.update()
end
end
end

上記のコードは:waiting, :approved, :rejectedという三つのステータスとapproveとrejectという二つのイベントを定義しました。approveイベントで、ステータスを:waitingあるいは:rejectedから:approvedに変更します。そして、rejectイベントで、ステータスを:waitingから:rejectedに変更します。

最後にステータスを変更してみましょう。

user = Example.Repo.get(Example.User, 1)

Example.User.current_state(user) # => 現在のステータスを取得
Example.User.can_approve?(user) # => :approvedステータスに変更できるかどうかチェック
Example.User.can_reject?(user) # => :rejectedステータスに変更できるかどうかチェック
Example.User.approve(user) # => :approvedステータスに変更する
Example.User.reject(user) # => :rejectedステータスに変更する


参考リンク

https://github.com/leogi/state_mc