Warning: file_get_contents(/data/phpspider/zhask/data//catemap/2/ruby-on-rails/52.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
Ruby on rails 如何在rails中正确地使用ActiveStorage进行模型测试?_Ruby On Rails_Rspec_Rails Activestorage - Fatal编程技术网

Ruby on rails 如何在rails中正确地使用ActiveStorage进行模型测试?

Ruby on rails 如何在rails中正确地使用ActiveStorage进行模型测试?,ruby-on-rails,rspec,rails-activestorage,Ruby On Rails,Rspec,Rails Activestorage,我刚刚开始在rails 5.1.4上使用ActiveStorage,我是TDD的新手,正在努力弄清楚如何测试一个附加了头像的模型 require 'rails_helper' RSpec.describe User, :type => :model do let (:valid_user) { FactoryBot.build(:user) } describe "Upload avatar" do context "with a valid image" do

我刚刚开始在rails 5.1.4上使用ActiveStorage,我是TDD的新手,正在努力弄清楚如何测试一个附加了头像的模型

require 'rails_helper'

RSpec.describe User, :type => :model do

  let (:valid_user) { FactoryBot.build(:user) }
  describe "Upload avatar" do
    context "with a valid image" do      
      it "saves the image" do
        valid_user.save!        
        saved_file = valid_user.avatar.attach(io: File.open("/home/ubuntu/workspace/spec/fixtures/files/avatar.jpg"), filename: "face.jpg", content_type: "image/jpg")
        expect(saved_file).to be_an_instance_of(ActiveStorage::Attachment::One)
      end
    end
  end 

end
但我得到了以下错误:

Failures:

  1) User Upload avatar with a valid image saves the image
     Failure/Error:
       saved_file = valid_user.avatar.attach(io: File.open("/home/ubuntu/workspace/spec/fixtures/files/avatar.jpg"), filename: "face.jpg", 
                                             content_type: "image/jpg")


 NoMethodError:
   undefined method `upload' for nil:NilClass
   Did you mean?  load
 # /usr/local/rvm/gems/ruby-2.3.4/gems/activestorage-0.1/lib/active_storage/blob.rb:48:in `upload'
 # /usr/local/rvm/gems/ruby-2.3.4/gems/activestorage-0.1/lib/active_storage/blob.rb:21:in `block in build_after_upload'
 # /usr/local/rvm/gems/ruby-2.3.4/gems/activestorage-0.1/lib/active_storage/blob.rb:16:in `tap'
 # /usr/local/rvm/gems/ruby-2.3.4/gems/activestorage-0.1/lib/active_storage/blob.rb:16:in `build_after_upload'
 # /usr/local/rvm/gems/ruby-2.3.4/gems/activestorage-0.1/lib/active_storage/blob.rb:26:in `create_after_upload!'
 # /usr/local/rvm/gems/ruby-2.3.4/gems/activestorage-0.1/lib/active_storage/attached.rb:25:in `create_blob_from'
 # /usr/local/rvm/gems/ruby-2.3.4/gems/activestorage-0.1/lib/active_storage/attached/one.rb:9:in `attach'
 # ./spec/models/user_spec.rb:47:in `block (4 levels) in <top (required)>'
故障:
1) 用户上传带有有效图像的化身保存图像
失败/错误:
saved_file=valid_user.avatar.attach(io:file.open(“/home/ubuntu/workspace/spec/fixtures/files/avatar.jpg”),文件名:“face.jpg”,
内容类型:“图像/jpg”)
命名错误:
nil:NilClass的未定义方法“upload”
你是说?负载
#/usr/local/rvm/gems/ruby-2.3.4/gems/activestorage-0.1/lib/active_storage/blob.rb:48:在“上传”中
#/usr/local/rvm/gems/ruby-2.3.4/gems/activestorage-0.1/lib/active\u storage/blob.rb:21:在“上传后在构建中块”中
#/usr/local/rvm/gems/ruby-2.3.4/gems/activestorage-0.1/lib/active_storage/blob.rb:16:in'tap'
#/usr/local/rvm/gems/ruby-2.3.4/gems/activestorage-0.1/lib/active\u storage/blob.rb:16:在“上传后构建”中
#/usr/local/rvm/gems/ruby-2.3.4/gems/activestorage-0.1/lib/active\u storage/blob.rb:26:in“上传后创建”
#/usr/local/rvm/gems/ruby-2.3.4/gems/activestorage-0.1/lib/active\u storage/attached.rb:25:in'create\u blob\u from'
#/usr/local/rvm/gems/ruby-2.3.4/gems/activestorage-0.1/lib/active\u storage/attached/one.rb:9:in'attached'
#./spec/models/user_spec.rb:47:in'block(4层)in'

有什么提示吗?

问题已解决。在跟踪到ActiveStorage::Blob::upload方法的错误后,它说:
将io上载到此Blob的密钥上的服务。
我意识到我没有为测试环境设置active_storage.service。简单地说,只需添加:

config.active_storage.service = :test
要配置/environments/test.rb文件,我使用

FactoryBot.define do
  factory :culture do
    name 'Soy'
    after(:build) do |culture|
      culture.image.attach(io: File.open(Rails.root.join('spec', 'factories', 'images', 'soy.jpeg')), filename: 'soy.jpeg', content_type: 'image/jpeg')
    end
  end
end
之后


在config/environments/test.rb中

config.active\u storage.service=:测试

按你的要求


it{expect(valid\u user.avatar)。待连接}

以下是我如何解决它的

# model
class Report < ApplicationRecord
  has_one_attached :file
end

我希望它能帮助您

我遇到了一个类似的nil错误(Module::DelegationError:to_模型委托给附件,但附件是nil),但它仅在多个测试使用同一工厂时发生

问题似乎是,上一次测试拆卸的清理是在下一次工厂调用附加文件后删除该文件。密钥是将ActiveJob队列适配器更新为内联,以便立即删除该文件

将这两个设置添加到config/environments/test.rb:

# Use inline job processing to make things happen immediately
config.active_job.queue_adapter = :inline

# Store uploaded files on the local file system in a temporary directory.
config.active_storage.service = :test
为什么不:


RSpec.describe User, type: :model do
  describe 'relations' do
    it { is_expected.to have_one(:avatar_attachment) }
  end
end

提示:
expect(valid\u user.image.attached?).to true
,因为您不需要测试ActiveStorage的内部结构。
expect(valid\u user.image)。to\u attached
是一样的,但有点习惯性。另一个答案没有乐趣-这对我来说很有效,感谢如果某些型号有回形针,而其他型号有Activestorage,有什么方法可以设置此设置?这可能会给您带来误报,因为图像将始终是Activestorage::Attached::One的实例,即使它为零。在控制台中尝试以下操作:
User.new.avatar
。请注意,它是ActiveStorage::Attached::One的一个实例。这对我来说是一个更好的测试,您可以实际检查该项是否已附加。谢谢
# spec
require 'rails_helper'
RSpec.describe Report, type: :model do
  context "with a valid file" do
    before(:each) do
      @report = create(:report)
    end

    it "is attached" do
      @report.file.attach(
        io: File.open(Rails.root.join('spec', 'fixtures', 'file_name.xlsx')),
        filename: 'filename.xlsx',
        content_type: 'application/xlsx'
      )
      expect(@report.file).to be_attached
    end
  end
end
# Use inline job processing to make things happen immediately
config.active_job.queue_adapter = :inline

# Store uploaded files on the local file system in a temporary directory.
config.active_storage.service = :test

RSpec.describe User, type: :model do
  describe 'relations' do
    it { is_expected.to have_one(:avatar_attachment) }
  end
end