Какова цель обратного вызова around_create в Rails Model? - PullRequest
14 голосов
/ 29 марта 2011

когда выполняется код обратного вызова around_create, в каких ситуациях мы должны его использовать?

Ответы [ 6 ]

33 голосов
/ 15 марта 2012

Имел и этот вопрос, и теперь нашел ответ: around_create позволяет вам в основном использовать before_create и after_create в одном методе.Вы должны использовать yield для выполнения сохранения между ними.

class MyModel < ActiveRecord::Base
  around_create :my_callback_method

  private
    def my_call_back_method
      # do some "before_create" stuff here

      yield  # this makes the save happen

      # do some "after_create" stuff here
    end
end
3 голосов
/ 18 марта 2019

Более простое и аккуратное объяснение об обратном вызове, которое я нашел, дано ниже

Обратный вызов around_ * вызывается вокруг действия и внутри действий before_ * и after_ *. Например:

class User
  def before_save
    puts 'before save'
  end

  def after_save
    puts 'after_save'
  end

  def around_save
    puts 'in around save'
    yield # User saved
    puts 'out around save'
  end
end

User.save
  before save
  in around save
  out around save
  after_save
=> true

Первоначально опубликовано здесь

3 голосов
/ 28 мая 2013

Только что нашел один вариант использования для меня:

Представьте себе ситуацию с полиморфным наблюдателем, и наблюдателю в некоторых случаях необходимо выполнить действие перед сохранением, а в других - после него.

ПриблизительноФильтр, вы можете захватить действие сохранения в блоке и запускать его, когда вам нужно.

class SomeClass < ActiveRecord::Base

end

class SomeClassObserver < ActiveRecord::Observer
  def around_create(instance, &block)
    Watcher.perform_action(instance, &block)
  end
end

# polymorphic watcher
class Watcher
  def perform_action(some_class, &block)
    if condition?
      Watcher::First.perform_action(some_class, &block)
    else
      Watcher::Second.perform_action(some_class, &block)
    end
  end
end

class Watcher::First
  def perform_action(some_class, &block)
    # update attributes
    some_class.field = "new value"

    # save
    block.call
  end
end

class Watcher::Second
  def perform_action(some_class, &block)
    # save
    block.call

    # Do some stuff with id
    Mailer.delay.email( some_class.id )
  end
end
1 голос
/ 25 сентября 2013

Помимо Ответ Тома Харрисона-младшего о регистрации и мониторинге, я обнаружил, что ключевым отличием является получение контроля над тем, выполняется ли операция вообще . В противном случае вы можете реализовать свои собственные обратные вызовы before_* и after_*, чтобы сделать то же самое.

Взять, к примеру, around_update. Допустим, у вас есть случай, когда вы не хотите запускать обновление. Например, я создаю драгоценный камень, который сохраняет черновики в другой таблице drafts, но не сохраняет определенные обновления в главной таблице.

around_update :save_update_for_draft

private

def save_update_for_draft
  yield if update_base_record?
end

Детали метода update_base_record?, на которые здесь ссылаются, на самом деле не имеют значения. Вы можете видеть, что операция обновления просто не будет выполняться, если этот метод не оценивается как true.

1 голос
/ 15 марта 2012

Классический вариант использования «круглых» фильтров - это измерение производительности, регистрация или регистрация или изменение состояния.

0 голосов
/ 29 марта 2011

around_create вызывается при сохранении модели с флагом new?.Он может быть использован для добавления данных для добавления / изменения значений модели, вызова других методов и т. Д. Я не могу определить конкретный вариант использования для этого обратного вызова, но он завершает набор «до, после, вокруг»обратные вызовы для действия создания.Для событий поиска, обновления, сохранения и удаления существует аналогичный режим «до, после, вокруг».

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...