Decorator In Ruby on Rails
Bài đăng này đã không được cập nhật trong 3 năm
Decorator In Ruby on Rails
With this article I want to show you guy about one technech of ruby on rails that is called Decorator. It is an object-oriented layer of presentation logic to your Rails Application. We can image it that without decorator, the functionality might have been tangle up. with this article too, you heard about why the reason we need to use decorator in ruby on rails appplication with practice code and you can apply it into your application ruby on rails. So in this article I will show you introduce you guy about one gem in ruby on rails that's call draper.
What is a decorator?
The decorator pattern is a design pattern that allows behavior to be added to an individual object without affecting the behavior of other objects from the same class. We can check it with the simple example.
@movie = Movie.find(1)
We can add additional behaveior to an instantiated model like @movie, before we pass it from controler to view. However, in other context, the Movie model, doesn't have the added behavior that's the result tof the decoration. example
movie.create_at
// Mon, 16 Oct 2017 04:17:21 UTC +00:00
But we want to show result of movie.created_at
is 2017-11-16
. So decorator can help to do that.
To understand more about this, we need to one simple project about draper gem that allow us to use decorator in ruby on rails.
Project demo
- create new rails application that is called draper-app-demo
rails new draper-app-demo
bundle install
- For my design database on this project, I will create simple as below, we have 2 model:
Book
andAuthor
with simple design as image below: - let's create two models follow design
rails db:create
rails g model author name:string
rails g model book published_at:datetime author:references
rails db:migrate
Now we can add gem draper
into your file Gem file with gem 'draper', '~> 3.0.1'
and you need to run bundle
. After that we need to create ApplicationDecorator
that all generated decorators inherit from, run...
rails generate draper:install
After that we need to have draper installed and generate for each our resource
rails generate decorator Book
rails generate decorator Author
Usage
When writing decorator methods you'll usually need to access the wrapped model. While you may choose to use delegation (covered below) for convenience, you can always use the object (or its alias model). On file app/decorators/book_decorator.rb
class BookDecorator < ApplicationDecorator
delegate_all
def published_at
object.published_at.strftime("%m/%d/%Y")
end
end
class AuthorDecorator < ApplicationDecorator
delegate_all
def name
"#{object.name} this is name"
end
end
after we config as before we test it, book.decorate.published_at
, author.decorate.name
will be display other format. we need to work it with view and controller, by generate:
rails g controller books
To use Draper in our Book page we first need to make a change to the show action in the BooksController. This action currently fetches a Book in the usual way.
class BooksController < ApplicationController
def show
@book = Book.find(params[:id])
end
end
We need to wrap this user in our decorator which we do by replacing Book.find with BookDecorator.find. on /app/controllers/books_controller.rb
def show
@book = BookDecorator.find(params[:id])
end
This code will now return a BookDecorator instance that wraps the Book record and delegates all methods to it by default (more on this later). The action will still work as it did before even though we’re working with a BookDecorator instead of a Book. Now we can start to clean up our views and we’ll begin with the code that renders the book’s published_at.
app/decorators/book_decorator.rb
------
decorates_finders
def published_at
if object.published_at.present?
object.published_at.strftime("%m/%d/%Y")
else
"Not yet to add published"
end
end
Next we’ll tidy up the code that renders the book’s name. We’ll replace this code in the view:
app/views/users/show.html.erb
<h1><%= @book.published_at %></h1>
- when published_at is not present
- when published_at is present
Conclusion
Decorators to a Rails application’s views much like a presenter pattern. If you find that you have a lot of complex view logic in your templates and helper methods Draper can help to clean up this code by taking a more object-orientated approach.
All rights reserved