ProductPromotion
Logo

Elixir

made by https://0x3d.site

GitHub - asiniy/ecto_state_machine: State machine pattern for Ecto
State machine pattern for Ecto. Contribute to asiniy/ecto_state_machine development by creating an account on GitHub.
Visit Site

GitHub - asiniy/ecto_state_machine: State machine pattern for Ecto

GitHub - asiniy/ecto_state_machine: State machine pattern for Ecto

Ecto state machine

travis ci badge badge

This package allows to use finite state machine pattern in Ecto. Specify:

and go:

defmodule User do
  use Web, :model

  use EctoStateMachine,
    states: [:unconfirmed, :confirmed, :blocked, :admin],
    events: [
      [
        name:     :confirm,
        from:     [:unconfirmed],
        to:       :confirmed,
        callback: fn(model) -> Ecto.Changeset.change(model, confirmed_at: Ecto.DateTime.utc) end # yeah you can bring your own code to these functions.
      ], [
        name:     :block,
        from:     [:confirmed, :admin],
        to:       :blocked
      ], [
        name:     :make_admin,
        from:     [:confirmed],
        to:       :admin
      ]
    ]

  schema "users" do
    field :state, :string, default: "unconfirmed"
  end
end

now you can do:

user = Repo.get_by(User, id: 1)

# Create changeset transition user state to "confirmed". We can make him admin!
confirmed_user = User.confirm(user)     # =>

# We can validate ability to change user's state
User.can_confirm?(confirmed_user)       # => false
User.can_make_admin?(confirmed_user)    # => true

# Create changeset transition user state to "admin"
admin = User.make_admin(confirmed_user)

# Store changeset to the database
Repo.update(admin)                      


# List all possible states
# If column isn't `:state`, function name will be prefixed. IE,
# for column `:rules` function name will be `rules_states`
User.states # => [:unconfirmed, :confirmed, :blocked, :admin]

# List all possible events
# If column isn't `:state`, function name will be prefixed. IE,
# for column `:rules` function name will be `rules_events`
User.events # => [:confirm, :block, :make_admin]

You can check out whole test/dummy directory to inspect how to organize sample app.

Installation

If available in Hex, the package can be installed as:

  1. Add ecto_state_machine to your list of dependencies in mix.exs:

    def deps do [{:ecto_state_machine, "~> 0.1.0"}] end

Custom column name

ecto_state_machine uses state database column by default. You can specify column option to change it. Like this:

defmodule Dummy.User do
  use Dummy.Web, :model

  use EctoStateMachine,
    column: :rules,
    # bla-bla-bla
end

Now your state will be stored into rules column.

Contributions

  1. Install dependencies mix deps.get
  2. Setup your config/test.exs & config/dev.exs
  3. Run migrations mix ecto.migrate & MIX_ENV=test mix ecto.migrate
  4. Develop new feature
  5. Write new tests
  6. Test it: mix test
  7. Open new PR!

Roadmap to 1.0

  • Cover by tests
  • Custom db column name
  • Validation method for changeset indicates its value in the correct range
  • Initial value
  • CI
  • Add status? methods
  • Introduce it at elixir-radar and my blog
  • Custom error messages for changeset (with translations by gettext ability)
  • Rely on last versions of ecto & elixir
  • Write dedicated module instead of requiring everything into the model
  • Write bang! methods which are raising exception instead of returning invalid changeset
  • Rewrite spaghetti description in README

Articles
to learn more about the elixir concepts.

Resources
which are currently available to browse on.

mail [email protected] to add your project or resources here 🔥.

FAQ's
to know more about the topic.

mail [email protected] to add your project or resources here 🔥.

Queries
or most google FAQ's about Elixir.

mail [email protected] to add more queries here 🔍.

More Sites
to check out once you're finished browsing here.

0x3d
https://www.0x3d.site/
0x3d is designed for aggregating information.
NodeJS
https://nodejs.0x3d.site/
NodeJS Online Directory
Cross Platform
https://cross-platform.0x3d.site/
Cross Platform Online Directory
Open Source
https://open-source.0x3d.site/
Open Source Online Directory
Analytics
https://analytics.0x3d.site/
Analytics Online Directory
JavaScript
https://javascript.0x3d.site/
JavaScript Online Directory
GoLang
https://golang.0x3d.site/
GoLang Online Directory
Python
https://python.0x3d.site/
Python Online Directory
Swift
https://swift.0x3d.site/
Swift Online Directory
Rust
https://rust.0x3d.site/
Rust Online Directory
Scala
https://scala.0x3d.site/
Scala Online Directory
Ruby
https://ruby.0x3d.site/
Ruby Online Directory
Clojure
https://clojure.0x3d.site/
Clojure Online Directory
Elixir
https://elixir.0x3d.site/
Elixir Online Directory
Elm
https://elm.0x3d.site/
Elm Online Directory
Lua
https://lua.0x3d.site/
Lua Online Directory
C Programming
https://c-programming.0x3d.site/
C Programming Online Directory
C++ Programming
https://cpp-programming.0x3d.site/
C++ Programming Online Directory
R Programming
https://r-programming.0x3d.site/
R Programming Online Directory
Perl
https://perl.0x3d.site/
Perl Online Directory
Java
https://java.0x3d.site/
Java Online Directory
Kotlin
https://kotlin.0x3d.site/
Kotlin Online Directory
PHP
https://php.0x3d.site/
PHP Online Directory
React JS
https://react.0x3d.site/
React JS Online Directory
Angular
https://angular.0x3d.site/
Angular JS Online Directory