2012-03-14 54 views
2

我正在實現幾個類,它本身沒有數據,只是邏輯。這些類實現了迄今爲止的訪問控制策略,這取決於從其他模型的數據中取得的幾個參數。我如何模塊化Rails模型?

我最初試圖找到答案「在哪裏存儲這樣的類?」在這裏,答案是apps/models目錄。沒關係,但我喜歡將這些類從層次結構中的ActiveRecord繼承類清楚地分離出來,無論是作爲文件還是類。

因此,我在Logic模塊內創建了類,如Logic::EvaluationLogicLogic::PhaseLogic。我也想要在這些邏輯之間傳遞的常量。我更喜歡將這些常量放入Logic模塊中。因此,我實現這樣的:

# in logic/phase_logic.rb 
module Logic 
    PHASE_INITIAL = 0 
    PHASE_MIDDLE = 1000 

    class PhaseLogic 
    def self.some_phase_control_code 
    end 
    end 
end 

# in logic/evaluation_logic.rb 
module Logic 
    class EvaluationLogic 
    def self.some_other_code 
     Logic::PhaseLogic.self.some_phase_control_code(Logic::PHASE_INITIAL) 
    end 
    end 
end 

現在,它工作的很好rspec(它通過測試,我沒有問題寫的),但不能與開發服務器,因爲它不能找到Logic::PHASE_INITIAL不變。

我懷疑它與Rails的自動加載方案和我想要做的不匹配有關。我試圖調整軌道,但沒有運氣,最終取消了module Logic包裹。

現在我想問的問題是:我如何使用Rails來組織這些類? 此刻我正在使用3.2.1。

發佈的後續問題「How I can organize namespace of classes in app/modules with rails?

+0

也許在'lib/logic /'中,並在相關模型中包含/擴展? – Brian 2012-03-14 12:45:02

回答

1

我不知道我是否真的瞭解你的類,但不能創建Logic模塊或(我寧願做這個:)PhaseLogic and EvaluationLogic objects in /lib directory

並不是說「模型」始終是ActiveRecord的後代。如果對象屬於「業務邏輯」,那麼它就是一個模型。你可以有任何不接觸數據庫的模型。因此,如果您的類是「業務對象」,請將它們放在「應用/模型」中,並像其他任何模型一樣使用。

另一個問題是,是否應該使用繼承或模塊 - 但我寧願去想包括模塊中PhaseLogic,而不是關於一個模塊中定義PhaseLogic。當然,這一切都很大程度上取決於您的對象的預期角色。

因爲在Ruby中對象的類不重要,所以不需要使用繼承。如果您想將邏輯對象「插入」其他對象,請注意所有'* Logic'類都具有所需的方法。我知道我所說的都很模糊,但我想我不能更多地瞭解這些對象的作用,所以不能給你更具體的建議。

啊,還有一件事!

如果您發現自己在Rails類自動加載中發生衝突,只需在所有使用Logic::PHASE_INITIAL常量的類中使用舊的require "lib/logic.rb"即可。

在這種情況下,我想你的問題是由不同的加載順序造成的。 logic/evaluation_logic.rb已在logic/phase_logic.rb之前加載。如果您在某處創建logic.rb,類自動加載可以找到它,並在該文件中定義這些常量,則問題可能會消失。

+1

你也可以在'config/application.rb'中使用'config.autoload_paths + =「#{config.root}/wherever_you_want_to_put_your_logic_classes''來不必使用'require'。 – Frost 2012-03-14 13:01:07

+0

我意識到我把兩個問題混合在一起。 我最初的想法是把這樣的類放入'lib'就像你建議的那樣。但是我覺得把這樣的東西放到'lib'中有些尷尬。我試圖在Stackoverflow中找到建議,並發現大多數人建議放置到「模型」中。 如何設計類是不同的問題,我沒有描述爲什麼我採取了課程。我的意圖是我想實現兩種交互的邏輯類型,所以把它們放到單個命名空間中似乎是合理的,所以上面的結構。 (con't) – shigeya 2012-03-14 23:32:40

+0

模塊的使用方式,我更喜歡我的方案,因爲我想將邏輯封裝到類中,並且不想污染引用模塊的類(通過包含它)。這部分是因爲我仍然不習慣ruby的混音方式(我使用的C++太長:20多年) 另外請注意,正如Frost推薦的,在'app'之外使用autoload_paths似乎很自然。我可以用這個方案解決,但我會發表另一個問題來看。 - 無論如何回覆/評論 – shigeya 2012-03-14 23:34:28

0

不要命名您的類或模塊Logic使用特定的名稱。首先將邏輯提取到不同的類中,然後嘗試將它們分解爲更小的類。使用命名空間在lib文件夾中區分它們,在完成這一步之後,您將能夠提取一些邏輯部分來分離寶石,並減少應用程序的代碼庫和複雜性。也看看presenter模式。

+0

我正在使用'module'來命名空間分離。你如何區分'module'以外的命名空間? – shigeya 2012-03-14 23:41:13