質問

So in my ClientsController.rb I have a before filter that does the following:

Checks the current year, and month. If the month is after June, then set the variable vote_year to next year. If it isn't, then set the vote_year to this year.

Then I am setting the date attribute based on that year, along with the hard month & day of July 1.

Basically, this particular date is on July 1st every year. I want this before filter to set the next date based on whether or not the time that this filter has been run is before or after July 1st.

The code I have is as follows:

before_filter :set_next_vote_date, :only => [:create, :new, :edit, :update]

private

def set_next_vote_date
    client = current_user.clients.find(params[:id])
    today = DateTime.parse(Time.now.to_s)
    year = today.year

    if today.month == 7 && today.day == 1
        vote_year = today.year
    elsif today.month > 6
        vote_year = year + 1
    else
        vote_year = year
    end

    client.next_vote = "#{vote_year}-07-01"         
end

The issue is that there is no error thrown, whenever I do any of those actions on those controllers. But, the next_vote attribute on the client record is not being updated.

What am I missing?

Edit 1:

After I have used update_attribute (without the !), I don't get an error, but I am not seeing this particular attribute being updated in the log.

Started PUT "/clients/1" for 127.0.0.1 at 2012-09-08 20:09:17 -0500
Processing by ClientsController#update as HTML
  Parameters: {"utf8"=>"✓", "authenticity_token"=>"J172LuZQc5N=", "client"=>{"name"=>"John F Kennedy", "email"=>"jfk@email.com", "phone"=>"8234698765", "firm_id"=>"1", "topic_ids"=>"2"}, "commit"=>"Update Client", "id"=>"1"}
  User Load (0.3ms)  SELECT "users".* FROM "users" WHERE "users"."id" = 1 LIMIT 1
  Client Load (0.1ms)  SELECT "clients".* FROM "clients" WHERE "clients"."user_id" = 1 AND "clients"."id" = ? LIMIT 1  [["id", "1"]]
   (0.1ms)  begin transaction
   (0.0ms)  commit transaction
  CACHE (0.0ms)  SELECT "clients".* FROM "clients" WHERE "clients"."user_id" = 1 AND "clients"."id" = ? LIMIT 1  [["id", "1"]]
   (0.1ms)  begin transaction
  Topic Load (0.6ms)  SELECT "topics".* FROM "topics" WHERE "topics"."id" = ? LIMIT 1  [["id", 2]]
  Topic Load (0.2ms)  SELECT "topics".* FROM "topics" INNER JOIN "clients_topics" ON "topics"."id" = "clients_topics"."topic_id" WHERE "clients_topics"."client_id" = 1
   (0.4ms)  UPDATE "clients" SET "phone" = 823498765, "updated_at" = '2012-09-09 01:09:17.631839' WHERE "clients"."id" = 1
   (1.4ms)  commit transaction
Redirected to http://localhost:3000/clients/1

Note that the next_vote attribute isn't updated. Granted, I didn't include that attribute in the edit form partial, but I assumed that this before_filter - if it is being executed, would update the record. But I am not even sure if it is being executed at all.

Edit 2:

Never mind, it seems to be working now. The above log paste was AFTER the edit action, and the before_filter executes before the edit action - DUH! Silly me :)

役に立ちましたか?

解決

It seems you're not saving the client after changing the attribute.

Some further suggestions on how to clean up that code a bit:

before_filter :set_next_vote_date, :only => [:create, :new, :edit, :update]

private

def set_next_vote_date
  client    = current_user.clients.find(params[:id])
  today     = Date.today
  vote_year = today.month > 6 ? today.year + 1 : today.year

  client.update_attribute(:next_vote, Date.new(vote_year, 7, 1))
end

他のヒント

try:

def set_next_vote_date
  client = Client.find(params[:id])
  today = Time.now
  year = today.year

  if today.month == 7 && today.day == 1
    vote_year = year
  elsif today.month > 6
    vote_year = year + 1
  else
    vote_year = year
  end

  client.update_attribute!(:next_vote, "#{vote_year}-07-01")
end

the update_attribute! (note the bang) will cause an exception to be raised if something goes wrong.. atleast allowing you to rescue with pry-rescue and see what's going on. a call to save shouldn't be necessary, as it will be persisted later in the activerecord callback cycle.

ライセンス: CC-BY-SA帰属
所属していません StackOverflow
scroll top