2011-02-06 1 views
19

Sto avendo difficoltà a capire come impedire a Paperclip di eliminare la versione precedente di un allegato (immagine).Impedire Paperclip dall'eliminazione/sovrascrittura degli allegati sull'aggiornamento

Ho un modello, Sito, che ha un allegato, logo. Mi piacerebbe conservare i vecchi loghi poiché terrò conto delle modifiche al modello e vorrei vedere la cronologia dei loghi.

Sto tenendo traccia delle modifiche in un altro modello, che ha un riferimento ai percorsi dei file. Il mio problema è che quando si aggiorna un sito con un nuovo logo, Paperclip svuota per primo il vecchio logo.

Mi sorprende che non ci sia un'opzione che è possibile passare per impedire a Paperclip di svuotare il vecchio allegato prima di crearne uno nuovo.

Qualche idea?

risposta

32

C'è una nuova opzione che dice graffetta per preservare vecchi allegati:

https://github.com/thoughtbot/paperclip/commit/65e8d4f6de50732d8e1b https://github.com/thoughtbot/paperclip/issues/60

Semplice da utilizzare:

has_attached_file => :attachment, 
        :styles => { :thumb => 100x100! }, 
        :preserve_files => true 

Non è ancora documentato e ha preso un po 'scavare per trovare così ho voluto condividere qui.

+0

Grazie. +1 da qui, anche se non hai risolto il mio problema in quel momento. – simonwh

+5

Ad oggi, 'preserve_files' sembra deprecato, per l'ultima API di paperclip: http://rubydoc.info/gems/paperclip/Paperclip/ClassMethods:has_attached_file Vedere' keep_old_files': conserva i file allegati esistenti (originale + ridimensionato) dall'eliminazione automatica quando un allegato viene cancellato o aggiornato. Il valore predefinito è falso. –

+1

@AdrienSchuler Ho letto quei due come separati. 'preserve_files' manterrà i file anche se il record genitore viene cancellato, dove come' keep_old_files' non dà questa sicurezza. –

1

Perché gli allegati sono definiti a livello di classe, Paperclip interpola i simboli nelle stringhe utilizzando il proprio libreria di interpolazione. È possibile creare le proprie interpolazioni utilizzando questa libreria.

Vorrei aggiungere un campo al modello chiamato attachment_version o qualcosa di simile e quindi incrementare questo numero di versione ogni volta che il file viene modificato. Quindi, creare un'interpolazione per esso in un file di inizializzazione:

Paperclip.interpolates :version do |attachment, style| 
    attachment.instance.attachment_version 
end 

Ora è possibile utilizzare :version nelle stringhe:

class Model < ActiveRecord::Base 
    has_attached_file :something, :path => " :rails_root/public/somethings/etc/:version.:extension" 
end 

Vedi the wiki documentation per ulteriori informazioni.

[Update]

Dopo un po 'scavare intorno (si vedano i commenti a questa risposta), sono giunto alla conclusione che la graffetta sarà ancora cancellare il vecchio attaccamento a causa di codice che si chiama in Paperclip::Atachment#attach . Probabilmente il modo migliore per gestire questo è creare un nuovo motore di archiviazione basato su Paperclip::Storage::Filesystem e sovrascrivere #flush_deletes. Si noti che non esiste alcun modo in questo metodo per stabilire se un file viene accodato per l'eliminazione a causa del modello a cui appartiene per essere eliminato o un nuovo file viene caricato al suo posto.

+0

Mi sembra che Paperclip possa ancora eliminare il vecchio file, solo per impostazione predefinita, anche se i nomi non corrispondono ... –

+1

Questo sembra essere il caso. 'Paperclip :: Attachment # assign' chiama' # clear', che chiama 'queue_existing_for_delete', che a sua volta fa esattamente quello che sembra. Potresti * creare un nuovo motore di archiviazione basato su https://github.com/thoughtbot/paperclip/blob/master/lib/paperclip/storage/filesystem.rb e modificare '# flush_deletes' se necessario. –

+0

Grazie a BinaryMuse, sembra essere il modo migliore per farlo al momento. Dovresti creare una risposta ;-) – simonwh

0

lib/paperclip_monkey_patch.RB:

module Paperclip 
    class Attachment 
    def clear 
    # nop 
    #raise "hell" 
    # op 
    instance_write(:file_name, nil) 
    instance_write(:content_type, nil) 
    instance_write(:file_size, nil) 
    instance_write(:updated_at, nil) 
    end 
end 
end 

Quindi aggiungere questa riga nella parte superiore di qualsiasi file cancellato allegati:

require 'paperclip_monkey_patch'

Grazie alla Ruby Forum