Skip to content

Instantly share code, notes, and snippets.

@nnabeyang
Last active December 19, 2015 01:28
Show Gist options
  • Save nnabeyang/5875717 to your computer and use it in GitHub Desktop.
Save nnabeyang/5875717 to your computer and use it in GitHub Desktop.
ruby on railsでコンポジットパターン
# test/fixtures/bodies.yml
one:
id: 1
file_entry_id: 1
description: desc1
two:
id: 2
file_entry_id: 3
description: description2
three:
id: 3
file_entry_id: 5
description: hello, world
# app/models/body.rb
class Body < ActiveRecord::Base
attr_accessible :description
belongs_to :file_entry
def size
description.bytesize
end
end
# app/models/chid_item.rb
class ChildItem < ActiveRecord::Base
attr_accessible :directory_entry_id, :entry_id
belongs_to :entry
belongs_to :directory_entry
end
# test/fixtures/child_items.yml
one:
id: 1
entry_id: 1
directory_entry_id: 2
two:
id: 2
entry_id: 3
directory_entry_id: 2
three:
id: 3
entry_id: 5
directory_entry_id: 4
four:
id: 4
entry_id: 2
directory_entry_id: 4
# app/models/directory_entry.
class DirectoryEntry < Entry
has_many :child_items
has_many :entries, through: :child_items
def size
entries.inject(0) {|size, entry| size += entry.size; size}
end
end
# test/fixtures/entries.yml
one:
id: 1
name: file_name
type: FileEntry
two:
id: 2
name: directory_name
type: DirectoryEntry
three:
id: 3
name: file_name2
type: FileEntry
four:
id: 4
name: directory_name2
type: DirectoryEntry
five:
id: 5
name: file_name3
type: FileEntry
# app/models/entry.rb
class Entry < ActiveRecord::Base
attr_accessible :name, :type
end
# test/unit/entry_test.rb
require 'test_helper'
class EntryTest < ActiveSupport::TestCase
test "file_entry has body" do
body = entries(:one).body
assert_equal "desc1", body.description
end
test "directory_entry has entries" do
entries = entries(:two).entries
assert_equal 2, entries.count
assert_equal "file_name", entries[0].name
assert_equal "file_name2", entries[1].name
end
test "entry size returns byte size of description" do
assert_equal 5, entries(:one).size
assert_equal 17, entries(:two).size
assert_equal 29, entries(:four).size
end
end
# app/models/file_entry.rb
class FileEntry < Entry
has_one :body
def size
body.size
end
end
# db/schema.rb
ActiveRecord::Schema.define(:version => 20130627094453) do
create_table "bodies", :force => true do |t|
t.text "description"
t.integer "file_entry_id"
t.datetime "created_at", :null => false
t.datetime "updated_at", :null => false
end
create_table "child_items", :force => true do |t|
t.integer "entry_id"
t.integer "directory_entry_id"
t.datetime "created_at", :null => false
t.datetime "updated_at", :null => false
end
create_table "entries", :force => true do |t|
t.string "name"
t.string "type"
t.datetime "created_at", :null => false
t.datetime "updated_at", :null => false
end
end
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment