2 つのモデル: AnOwner
と a Dog
:
owner.rb
class Owner < ActiveRecord::Base
has_one :dog
end
dog.rb
class Dog < ActiveRecord::Base
belongs_to :owner
end
そして、ここにスキーマがあります:
schema.rb
ActiveRecord::Schema.define(version: 123) do
create_table "dogs", force: true do |t|
t.string "name"
t.integer "energy"
t.integer "owner_id"
t.datetime "created_at"
t.datetime "updated_at"
end
add_index "dogs", ["owner_id"], name: "index_dogs_on_owner_id"
create_table "owners", force: true do |t|
t.string "name"
t.string "energy"
t.datetime "created_at"
t.datetime "updated_at"
end
end
かなりシンプルなセットアップ。
彼を散歩owner
に連れて行きたい。dog
散歩が終わると、飼い主の気力が5減り、犬の気力が20減る。
明らかに、このwalk_the_dog
アクション/メソッドは、owner
オブジェクトとオブジェクトの 2 つのオブジェクトに影響を与えdog
ます (もちろん、この犬のオブジェクトはたまたまこの所有者に関連付けられています)。
このコードをどこに置くべきかわかりません。内で単純にアクションを作成できることはわかっていますがowners_controller.rb
、それは悪い考えのように思えます。次のようになります。
owners_controller.rb
class OwnersController < ApplicationController
def walk_the_dog
@owner = Owner.find(params[:id])
@owner.energy -= 5
@owner.dog.energy -= 20 # this line in particular seems like bad OO design
@owner.save
@owner.dog.save
end
...
end
私が理解しているように、オブジェクトは自分自身の状態のみを変更する必要があり、他のオブジェクトの状態を変更するべきではありません。owner
オーナー コントローラ内でオブジェクトだけでなく、関連付けられたオブジェクトの状態も変更しているため、これは悪い考えのように見えdog
ます。
サービスについて読みました。walk_the_dog
私が理解しているように、サービスはオブジェクト間の相互作用と複数のオブジェクトの状態変更を可能にするため、サービスの優れたケースのようです。私はそれを行う/実装する方法がわかりません。
と呼ばれるサービスオブジェクトが必要walk_the_dog
ですか? 一連のサービスメソッドを含むサービスディレクトリ内のファイルである必要があります-そのうちの1つが呼び出されwalk_the_dog
、owners_controller.rb
コントローラーでこのメソッドを使用するだけですか? 次のステップが何かわかりません。
注: 「これが OO 設計を壊すかどうかなんて誰が気にするんだろう。ただそれを実行して、うまくいくならうまくいく」と言っている人を見ることができます。残念ながら、これはオプションではありません。私が今取り組んでいるアプリケーションは、その考え方に従いました。アプリケーションが非常に大きくなり、現在は維持が非常に困難になっています。アプリの大幅なリニューアルでこの状況を打破したい。