Supposons que vous ayez un Question
et un Answer
et que les nouvelles réponses proviennent de la page questions#show
(comme StackoverFlow).Modèle pour éviter le couplage entre les actions de contrôleur des contrôleurs parent et enfant
À moins que le questions#show
et les actions answers#create
charger des données identiques, le answers#create
jetteront une exception (généralement pas de méthode de la classe nulle) s'il y a une erreur de validation d'une nouvelle réponse. Ce n'est pas un problème majeur, mais lorsque vous ajoutez des filtres et d'autres types de données, le code commence à sentir, et vous obtenez un couplage étroit entre les deux actions. Changer une exige de changer l'autre - quelque chose facile à oublier.
Je me demande ce que les développeurs expérimentés de Rails font, le cas échéant, pour éviter ce couplage?
# Assume Discussion = Question, and Response = Answer
# Discussions#show
def show
@discussion = Discussion.find(params[:id]) # The question
@responses = @discussion.responses.includes(:author) # Existing answers
@response = @discussion.responses.build # New answer object for the form
order = 'users.role'
if params[:filter].present?
order = case params[:filter]
when 'new'
then 'responses.created_at DESC'
end
end
@responses = @responses.order(order)
end
Maintenant, regardons l'action responses#create
, qui doit charger les mêmes données pour render
au travail (si la validation échoue):
# Responses#create
def create
# @discussion is loaded using a before filter
@response = @discussion.responses.build(params[:response])
@response.author = current_user
@responses = @discussion.responses.includes(:author)
order = 'users.role'
if params[:filter].present?
order = case params[:filter]
when 'new'
then 'responses.created_at DESC'
end
end
@responses = @responses.order(order)
respond_to do |format|
if @response.save
format.html { redirect_to @discussion }
format.js
else
format.html { render 'discussions/show' } # fails if discussions#show and responses#new do not load the same data.
end
end
end