Ash Framework 튜토리얼 따라하기 (1)

https://hexdocs.pm/ash/get-started.html 을 따라해 보며 Ash 프레임워크의 기본 기능을 배워 본다.

시나리오

간소화된 HelpDesk 시스템을 가정해 보자.

시스템에는 두 개의 리소스가 있다.

  • Helpdesk.Support.Ticket (티켓)
  • Helpdesk.Support.Representative (담당자)

리소스에는 다음과 같은 액션을 할 수 있다.

  • 티켓을 열 수 있다
  • 티켓을 닫을 수 있다
  • 담당자에게 티켓을 배정할 수 있다

Ash 를 사용하여 구현

새 프로젝트 생성

mix 프로젝트가 없다면 새로 만들 수 있다. Ash 만 사용하는 프로젝트도 만들 수 있으나 향후 JSON API 까지 고려해 Phoenix도 같이 설치 한다.

# install the archive
mix archive.install hex phx_new
mix archive.install hex igniter_new

# use the `--with` flag to generate the project with phx.new and add Ash
mix igniter.new helpdesk --install ash,ash_phoenix --with phx.new && cd helpdesk

igniter 는 Elixir 로 만들어진 코드 생성기 이다. 지금 처럼 프레임워크 초반 세팅이나 버전 업그레이드를 할 때 사용할 수 있다.

첫 번째 도메인

먼저 도메인 폴더와 파일을 만든다.

mkdir -p lib/helpdesk/support && touch $_/ticket.ex && touch lib/helpdesk/support.ex

다음과 같은 폴더 구조일 것이다. lib/helpdesk 내부에 support 도메인이 만들어졌다.

lib/helpdesk/support.ex 파일에 다음 코드를 작성한다.

# lib/helpdesk/support.ex

defmodule Helpdesk.Support do
  use Ash.Domain

  resources do
    resource Helpdesk.Support.Ticket
  end
end

Helpdesk.Support 는 Ash.Domain 이고 Helpdesk.Support.Ticket 이라는 Resource 를 가지는 것으로 선언한다.

defmodule Helpdesk.Support.Ticket do
  # 이것은 이 모듈을 리소스로 만듭니다
  use Ash.Resource, domain: Helpdesk.Support

  actions do
    # :read 액션의 기본 구현을 사용합니다
    defaults [:read]
    # 그리고 나중에 커스터마이징할 create 액션
    create :create
  end

  # 속성들은 리소스에 존재하는 간단한 데이터 조각들입니다
  attributes do
    # `:id`라는 자동 생성되는 UUID 기본 키를 추가합니다
    uuid_primary_key :id
    # `:subject`라는 문자열 타입 속성을 추가합니다
    attribute :subject, :string
  end
end

Helpdesk.Support.Ticket 은 Ash.Resource 이고 Helpdesk.Support 도메인에 속한다. 이 리소스를 다루는 몇가지 action 들을 선언할 수 있고 속성 데이터도 정의할 수 있다.

실행

% iex -S mix

iex(1)> Helpdesk.Support.Ticket|> Ash.Changeset.for_create(:create)|> Ash.create!()

Helpdesk.Support.Ticket 리소스를 한 개 만들어 내기 위해 먼저 Changeset 을 만들고 Changeset 을 가지고 Ash.create! 함수를 통해 레코드를 만든다. Ecto.Changeset의 역할을 Ash 에선 Ash.Changeset이 담당하는 것 같다.

warning: Domain Helpdesk.Support is not present in

    config :helpdesk, ash_domains: [].


To resolve this warning, do one of the following.

1. Add the domain to your configured domain modules. The following snippet can be used.

    config :helpdesk, ash_domains: [Helpdesk.Support]

2. Add the option `validate_config_inclusion?: false` to `use Ash.Domain`

3. Configure all domains not to warn, with `config :ash, :validate_domain_config_inclusion?, false`

warning 발생해도 결과는 얻어지지만 warning 을 없애기 위해 다음 코드를 config.exs 에 추가한다.

# in config/config.exs
import Config

config :helpdesk, :ash_domains, [Helpdesk.Support] # 추가
% iex -S mix

iex(1)> Helpdesk.Support.Ticket|> Ash.Changeset.for_create(:create)|> Ash.create!()

%Helpdesk.Support.Ticket{
  id: "7d3d0639-5201-4eb3-9532-a7c837c98eaa",
  subject: nil,
  __meta__: #Ecto.Schema.Metadata<:built, "">
}

도메인과 리소스를 정의하고 몇가지 선언만 추가해도 기본 뼈대가 되는 기능을 얻을 수 있다.

다음 글에서 계속…

댓글 남기기