我有articles
,每篇文章has_many categories
。在一筆交易中指定或創建關聯模型
當用戶創建或更新文章時,他或她可以填寫類別名稱,如果此類別不存在,則需要創建一個新類別。
模式
class Article < ActiveRecord::Base
attr_accessible :category_id, :content, :title, :category_name
belongs_to :category
def category_name
category.try(:name)
end
def category_name=(name)
self.category = Category.find_or_create_by_name(name) if name.present?
end
end
class Category < ActiveRecord::Base
attr_accessible :name
has_many :articles
end
控制器
class ArticlesController < ApplicationController
load_and_authorize_resource
respond_to :json
def create
@article = Article.create(params[:article])
respond_with(@article)
end
def update
@article.update_attributes(params[:article])
@article.save
respond_with(@article)
end
...
end
問題
在create
或update
行動,如果類別不存在,那麼NE w將在單獨的交易中創建。因此,如果在article
中出現錯誤,則無論如何都可以創建新類別。
創建/更新操作的日誌(修剪爲了簡潔):
(0.0ms) begin transaction
SQL (0.3ms) INSERT INTO "categories" ....
(35.1ms) commit transaction
(0.0ms) begin transaction
SQL (0.5ms) INSERT INTO "articles" ...
(32.2ms) commit transaction
我希望得到一些建議/解決方案如何以優雅的方式解決這個問題。
我大概可以寫在我的控制器
ActiveRecord::Base.transaction do
@article = Article.create(params[:article])
respond_with(@article)
end
但它意味着我不得不寫相同的代碼在這兩種方法:create
和update
。既然它違反了DRY原則,我寧願找到另一種方式。
看看[Token]上的Railscast(http://railscasts.com/episodes/258-token-fields?view=asciicast)。它需要一些額外的步驟,但瑞安很好地解釋它。 – Firyn