views:

354

answers:

3

I am trying to assign a message to flash[:notice] in a model observer.

This question has already been asked: Ruby on Rails: Observers and flash[:notice] messages?

However, I get the following error message when I try to access it in my model:

undefined local variable or method `flash' for #<ModelObserver:0x2c1742c>

Here is my code:

class ModelObserver < ActiveRecord::Observer
  observe A, B, C

  def after_save(model)
    puts "Model saved"
    flash[:notice] = "Model saved"
  end
end

I know the method is being called because "Model saved" is printed to the terminal.

Is it possible to access the flash inside an observer, and if so, how?

A: 

No, you set it in the controller where the saving is occurring. flash is a method defined on ActionController::Base.

Ryan Bigg
Ryan's right though. You should be setting the flash in the controller ... it's a function of the view presentation layer. The "answer" above is a lot of dangerous heavy lifting to get this working.
Toby Hede
As I said in my post, setting the flash in the controller impractical (if it is even possible) in my application. I need add a message to the flash every time a model is updated; I am unaware of another method of doing so--at least without throwing a plate of spaghetti code at the wall.
titaniumdecoy
A: 

I found an answer to my question.

titaniumdecoy
I fear for your codebase.
Ryan Bigg
I appreciate your concern.
titaniumdecoy
+1  A: 

I needed to set flash[:notice] in the model to override the generic "@model was successfuly updated".

This what I did

  1. Created a virtual attribute in the respective model called flash_notice
  2. Then I set the virtual attribute in the respective model when needed
  3. Used an after_filter when this virtual attribute was not blank to override the default flash

You can see my controller and model how I accomplished this below:

class Reservation < ActiveRecord::Base

  belongs_to :retailer
  belongs_to :sharedorder
  accepts_nested_attributes_for :sharedorder
  accepts_nested_attributes_for :retailer

  attr_accessor :validation_code, :flash_notice

  validate :first_reservation, :if => :new_record_and_unvalidated

  def new_record_and_unvalidated
      if !self.new_record? && !self.retailer.validated?
         true
      else
          false
      end
  end

  def first_reservation
      if self.validation_code != "test" || self.validation_code.blank?
         errors.add_to_base("Validation code was incorrect") 
      else
          self.retailer.update_attribute(:validated, true)
          self.flash_notice = "Your validation as successful and you will not need to do that again"
      end
  end

end


class ReservationsController < ApplicationController

   before_filter :authenticate_retailer!
   after_filter :flash_notice, :except => :index

   def flash_notice
       if [email protected]_notice.blank?
          flash[:notice] = @reservation.flash_notice
       end
   end 
Sam