У меня есть модель, скажем, Attachments, которая использует attachment_fu для приема загрузки файла от пользователя. Я хочу "глубоко скопировать" (или в Ruby-ese, глубокое клонирование) вложение, создав тем самым совершенно новый двоичный объект в таблице "db_files".
Я обнаружил, что это еще не совсем решенная проблема. Это сообщение в блоге:
http://www.williambharding.com/blog/rails/rails-faster-clonecopy-of-attachment_fu-images/
Показывает метод, который предположительно работает для хранилища на основе файловой системы. Для хранилищ на основе БД «глубокое копирование» не выполняется. Создается новое «Attachment», но в нем используется уже существующий db_file_id, поэтому выполняется поверхностное копирование.
Внутри файла attachment_fu db_file_backend.rb я вижу метод сохранения:
# Saves the data to the DbFile model
def save_to_storage
if save_attachment?
(db_file || build_db_file).data = temp_data
db_file.save!
self.class.update_all ['db_file_id = ?', self.db_file_id = db_file.id], ['id = ?', id]
end
true
end
Итак, я пытаюсь расшифровать это, и я считаю, что "build_db_file" - это некое волшебное сокращение для метапрограммирования Ruby для DbFile.new, хотя я не могу подтвердить это (поиск источника не показывает упоминания об этом, и я не могу найти его в Google) .
Я не совсем уверен, что он делает, но моя теория заключается в том, что файл db_file копируется из исходного объекта как часть попытки «глубокого копирования» (в связанном коде), таким образом, он просто вызывает сохранение вместо создания.
Моя первоначальная теория заключалась в том, что родительский объект (вложение) будет установлен на "новый" при попытке глубокого копирования, поэтому я сделал что-то вроде:
def save_to_storage
if save_attachment?
if self.new_record?
db_file = DbFile.new :data => temp_data
self.class.update_all ['db_file_id = ?', self.db_file_id = db_file.id], ['id = ?', id]
end
end
true
end
Это на самом деле хорошо работает для клонированных объектов, но, к сожалению, все тесты для обычной, не клонированной загрузки файлов не выполняются. Объект Attachment создан, но в db_file данные не записываются. Теория заключается в том, что родительский объект сначала сохраняется, а потом пишется файл db_file, то есть new_record? возвращает false.
Итак, в качестве эксперимента я решил попробовать:
def save_to_storage
if save_attachment?
if self.new_record?
db_file = DbFile.new :data => temp_data
self.class.update_all ['db_file_id = ?', self.db_file_id = db_file.id], ['id = ?', id]
else
(db_file || build_db_file).data = temp_data
db_file.save!
self.class.update_all ['db_file_id = ?', self.db_file_id = db_file.id], ['id = ?', id]
#end
end
true
end
Это работает частично - файл db_file заполнен, но затем я получаю сообщение об ошибке на db_file.save! - сказать, что db_file - ноль.
Итак, я в некотором роде застрял. Я могу сделать еще несколько проб и ошибок, но в этот момент я достиг своего ограниченного понимания того, как работает этот плагин. Я действительно не ожидал и не хочу тратить на это столько времени, поэтому я не хочу больше пытаться исследовать attachment_fu, но я боюсь, что мне придется пройти по кроличьей норе, чтобы понять это. Есть идеи или мысли?
Спасибо !!