web-dev-qa-db-fra.com

Rails comment supprimer un fichier sans échouer en cas d'erreur

J'utilise JPEGCAM pour permettre aux utilisateurs de prendre une photo de profil avec leur webcam. Cela télécharge un fichier temporaire comme suit:

def ajax_photo_upload    
  File.open(upload_path, 'w:ASCII-8BIT') do |f|
    f.write request.raw_post
  end
  # @user.photo = File.open(upload_path)
  @user.assign_attributes(
    :photo => File.open(upload_path),
    :orig_filename => "#{current_user.full_name}.jpg"
  )
  if @user.save
  respond_to do |format|
  .....
private

  def upload_path # is used in upload and create
    file_name = session[:session_id].to_s + '.jpg'
    File.join(::Rails.root.to_s, 'public', 'temp', file_name)
  end

Quelle est la meilleure façon de supprimer ce fichier temporaire en toute sécurité? Merci

56
AnApprentice

Lorsque vous savez que vous avez terminé avec le fichier:

File.delete(path_to_file) if File.exist?(path_to_file)

Une autre chose: assurez-vous de toujours fermer les fichiers que vous avez ouverts, un système d'exploitation ne peut gérer qu'un certain nombre de fichiers ouverts/descripteurs de fichiers et vous risquez de rencontrer des bogues étranges lorsque vous dépassez cette limite ... Donc quand vous voulez ouvrir des fichiers en Ruby utilisez toujours la forme de bloc:

File.open(path) do |f|
  # ...
end

et Ruby fermera automatiquement le fichier pour vous. Si le formulaire de blocage n'est pas utilisable, vous devez fermer les fichiers par vous-même:

f = File.open(path)
# ...
f.close

Assurez-vous donc de fermer le fichier que vous passez à @user.assign_attributes(...)...

113
severin

Si vous êtes sûr d'en avoir fini, pourquoi ne pas simplement utiliser FileUtils.rm Ou FileUtils.rm_f?

FileUtils.rm_f(upload_path)

http://www.Ruby-doc.org/stdlib-1.9.3/libdoc/fileutils/rdoc/FileUtils.html#method-c-rm_f

Vous pouvez également ignorer cela dans Rails et avoir un cron qui se réveille et supprime les fichiers plus anciens qu'un jour du répertoire temporaire qui correspondent à ces fichiers temporaires. Cela présente l'avantage d'une marge d'erreur si un fichier n'est pas retraité - vous ne le rmez pas immédiatement - et l'opération de fichier n'est pas effectuée sur la boucle de demande/réponse pour Rails, qui répondra alors un peu plus rapidement.

29
Andrew Kuklewicz