Image

Category:

initialize и кэш

Привет.

Вот такая у меня проблема: есть конструктор класса, который вытаскивает инстанс из кэша и проверяет его валидность. Если кэшированый инстанс устарел, то понятно, конструктор конструирует объект по-новой и всё нормально...
А вот если кэшированый инстанс валидный, то как-то надо его (UPD или его копию) вернуть в качестве объекта, полученого через new.
А вот как - я что-то не могу понять. self = cached выдаёт ошибку - нельзя self значение присваивать. return cached из initialize тоже не работает. ошибок не выдаёт, но new возвращает неинициализированый объект.
Пока приходится по полям копировать данные из cached, но как-то уж больно уродливо это смотрится...

Вот примерный код, ну чтоб понятнее:

class SomeClass
  attr_reader :data, :updated
  def initialize
    cached = cache.read('cached')                       # читаем из кэша
    if cached.nil? or ((Time.now - cached.updated) > 5) # если в кэше пусто или инстанс старше 5 секунд
      @data = ...                                       # как-то обновляем данные
      @updated = Time.now                               # фиксируем время обновления данных
      cache.write('cached', self)                       # обновляем/записываем данные в кэше
    else
      # а вот тут непонятно что делать. то что ниже - это какой-то ужас.
      # потому что при любом изменении списка полей надо ж не забыть это всё тут поправить...
      # короче, явно что-то тут не так.
      @data = cached.data
      @updated = cached.updated
    end
  end
end


Заранее благодарен за советы и прочий rtfm :)
UPD: кажется придумал кое-какое решение
class SomeClass
  attr_reader :data, :updated
  def initialize
    cached = cache.read('cached')                       # читаем из кэша
    if cached.nil? or ((Time.now - cached.updated) > 5) # если в кэше пусто или инстанс старше 5 секунд
      @data = ...                                       # как-то обновляем данные
      @updated = Time.now                               # фиксируем время обновления данных
      cache.write('cached', self)                       # обновляем/записываем данные в кэше
    else
      # в принципе примерно то же самое, но список переменных берется через отражение
      cached.instance_variables.each { |varname|
        self.instance_variable_set(varname,
                                    cached.instance_variable_get(varname))
      }
    end
  end
end