Getting started - Hanami

In order to get a Hanami app rolling with jsonapi-rb, you will usually want to follow those 3 steps:

  1. Add jsonapi-hanami to your Gemfile:
# Gemfile

gem 'jsonapi-hanami'
  1. Declare the :jsonapi MIME type (for serialization):
# apps/foo/application.rb

module Foo
  class Application < Hanami::Application
    configure do
      # ...
      controller.format jsonapi: 'application/vnd.api+json'
      # ...
    end
  end
end
  1. Enable the JSON body parser (for deserialization):
# apps/foo/application.rb

module Foo
  class Application < Hanami::Application
    configure do
      # ...
      body_parsers :json
      # ...
    end
  end
end
  1. Optional: Add apps/foo/resources/ to the load_path:
# apps/foo/application.rb

module Foo
  class Application < Hanami::Application
    configure do
      # ...
      load_paths << [
        # ...
        'resources'
      ]
      # ...
    end
  end
end
  1. Extend your actions to use jsonapi-rb:

When using jsonapi-rb with Hanami (via the jsonapi-hanami gem), enabling of jsonapi-rb features is opt-in, and is done by including JSONAPI::Hanami::Action in your actions. Rendering is done by setting options directly on the controller action instance. The primary data is set via the self.data setter.

Example:

module API::Controllers::Posts
  class Create
    include API::Action
    include JSONAPI::Hanami::Action

    expose :url_helpers

    def call(params)
      # ...
      @url_helpers = routes  # Will be available inside serializable resources.

      self.data = posts
      self.include = [:author, comments: [:author]]
      self.fields  = { users: [:name, :email],
                       posts: [:title, :content] }
    end
  end
end

Examples

# Gemfile
gem 'jsonapi-hanami'

# apps/api/controllers/posts/create.rb
module API::Controllers::Posts
  class Create
    include API::Action
    include JSONAPI::Hanami::Action

    deserializable_resource :post

    params do
      required(:post).schema do
        required(:title)
        required(:content)
        required(:tag_ids)
      end
    end

    def call(params)
      repo = PostRepository.new
      post = repo.create(params[:post])

      self.data = post
      self.include = [:author, comments: [:author]]
      self.fields = { users: [:name, :email] }
      self.status = 201
    end
  end
end