2012-06-16 65 views
0

我是一位經驗豐富的Web開發人員,但是對於rails而言是新手。我正在編寫基於複式會計數據庫的預算申請。數據庫包含日記帳分錄以表示交易,並且每個日記帳分錄具有多個過帳。每個發佈都有一個帳戶和一個金額。我已將借方金額表示爲負值,將信用額表示爲正值。對1個模型字段使用2個虛擬屬性

但是,我不希望用戶記住正面和負面的情況,所以我已經爲我的模型製作了信用額度和借記金額的虛擬屬性,以便用戶可以看到單獨的信用額度和借項金額字段。

張貼模型是如下:

class Posting < ActiveRecord::Base 
    belongs_to :account 
    belongs_to :journal_entry 

    attr_accessible :account_id, :credit_amount, :debit_amount 
    attr_accessor :credit_amount, :debit_amount 

    after_validation :set_amount 
    after_find :split_amount 

    validates :credit_amount, :format => { :with => /\A(?:\d+(?:\.\d{1,2})?|(?:.\d{1,2}))?\z/ } 
    validates :debit_amount, :format => { :with => /\A(?:\d+(?:\.\d{1,2})?|(?:.\d{1,2}))?\z/ } 

    validate :check_amounts 

    def check_amounts 
    unless @account_id.blank? 
     if not @debit_amount.blank? and not @credit_amount.blank? 
     errors.add(:base, "cannot specify both credit and debit amount.") 
     elsif @debit_amount.blank? and @credit_amount.blank? 
     errors.add(:base, "must specify one of credit or debit amount.") 
     end 
    end 
    end 

    protected 

    def set_amount 
    unless @debit_amount.blank? and @credit_amount.blank? 
     self.amount = @debit_amount.blank? ? BigDecimal.new(@credit_amount) : -BigDecimal.new(@debit_amount) 
    end 
    end 

    def split_amount 
    @credit_amount = (self.amount.nil? or self.amount >= 0) ? self.amount : nil 
    @debit_amount = (self.amount.nil? or self.amount >= 0) ? nil : -self.amount 
    end 
end 

這是使用2個虛擬屬性(credit_amount和debit_amount)爲1個模型字段(量)的正確方法?我嘗試爲credit_amount/debit_amount編寫getter和setter,直接使用基礎數量字段,但這意味着我無法準確地向用戶報告驗證錯誤。

+1

我同意Anil的做法是好的。可能還有其他方法可以做到,但這足夠直觀。儘管有關代碼的一些評論(拿走或離開)。 1)我將你的驗證正則表達式提取爲一個常量,因爲它在兩個地方使用。常數名稱將更好地記錄意圖是什麼。 2)Ruby開發人員傾向於喜歡&&,|| 3)從方法返回以避免額外縮進(在check_amounts中,返回如果@ account_id.blank?)4)使用reader方法而不是實例變量(account_id vs @account_id) –

+0

感謝您的反饋和指導風格的鏈接 - 我錯過了我的搜索。我熱衷於學習ruby的風格習慣以及rails方式。 – Nathan

+0

雄辯Ruby是學習Ruby風格和最佳實踐的好書。 –

回答

2

我喜歡你寫它的方式。使用正則表達式的信用額度和借記金額驗證比僅僅驗證這些字段是數字更緊密。分割數量方法可以使用上面的註釋來解釋你在那裏做什麼,這樣下一個在凌晨3:00調試的人就不必弄清楚了(實際上,正則表達式也可以使用明確的描述註釋)。

我希望這會有所幫助。

祝你好運!

+0

感謝您的回答 - 將添加您建議的評論 – Nathan