Как открыть файл, хранящийся в CarrierWave в GridFs, из модели рельсов? (Проблема File.open)

Я использую CarrierWave для хранения файлов в gridfs, но у меня проблемы с их открытием из моей модели. Вот мои конфиги:

/config/initialize/carrierwave.rb

 CarrierWave.configure do |config|
  config.grid_fs_database = Mongoid.database.name
  config.grid_fs_host = Mongoid.config.master.connection.host
  config.storage = :grid_fs
  config.grid_fs_access_url = "/files"
end

/приложение/контроллеры/gridfs_controller.rb

 /require 'mongo' 
        class GridfsController < ActionController::Metal
          def serve
            gridfs_path = env["PATH_INFO"].gsub("/files/", "")
            begin
              gridfs_file = Mongo::GridFileSystem.new(Mongoid.database).open(gridfs_path, 'r')
              self.response_body = gridfs_file.read
              self.content_type = gridfs_file.content_type
            rescue
              self.status = :file_not_found
              self.content_type = 'text/plain'
              self.response_body = ''
            end
          end
        end

/app/uploaders/list_uploader.rb

class ListUploader < CarrierWave::Uploader::Base
  storage :grid_fs
  def store_dir
    "uploads/#{model.class.to_s.underscore}/#{mounted_as}/#{model.id}"
  end

и в маршрутах

match "/files/uploads/*path" => "gridfs#serve"

Итак, у меня есть модель, в которой есть текстовый файл

class Campaign
  include Mongoid::Document
  mount_uploader :list, ListUploader

Когда я вызываю что-то вроде <%=link_to "List", @campaign.list.url %> из своего представления, оно открывается нормально. Но когда я пытаюсь что-то вроде File.open("#{campaign.list.url}", "r") из модели кампании, это не удается. Это дает мне false, даже когда я вызываю File.exists?("/files/uploads/campaign/list/4eb02c4d6b1c0f02b200000b/list.txt"), что является правильным URL-адресом для этого файла. Итак, вопрос в том, как мне это назвать, чтобы открыть файл из модели? И по некоторым причинам важно открыть его из модели. Любые предложения помогут, спасибо.


person Maay    schedule 01.11.2011    source источник


Ответы (1)


URL-адрес несущей волны с mongodb gridfs не является физическим путем. Это просто логический путь для загрузки файла из gridfs. Вот почему вы не можете получить к нему доступ из ruby ​​File.open. Посмотрите приведенный ниже фрагмент из консоли rails, пытаясь открыть файл из gridfs.

File.open(User.first.image.pic.url,'r')
Errno::ENOENT: No such file or directory - /images/uploads/e5a1007d34.jpg

видите, он выбрасывает Нет такого файла или каталога. Поэтому вам нужно загрузить файл, а не открыть его

>> require 'open-uri'
>> open('image.jpg', 'wb') do |file|
?> file << open('http://0.0.0.0:3000' + (User.first.image.pic.url)).read
>> p file
>> end
#<File:image.jpg>
=> #<File:image.png (closed)>
person RameshVel    schedule 02.11.2011
comment
да, получилось просто отлично, спасибо! А также этот опция - person Maay; 02.11.2011