1
votes

I cant get carrierwave to work with Amazon S3. Get a can't convert nil into String error.

I am using couchrest_model, carrierwave 0.5.8, fog 1.9.0 and Rails 3.1.11

Cant upgrade to a later carrierwave because of a dependency to Rails 3.2.x

The S3 key and secret is 100% sure correct and working.

initializers/carrierwave.rb

# encoding: utf-8

require 'couchrest_model'
require 'carrierwave/validations/active_model'

module CarrierWave
  module CouchrestModel
    include CarrierWave::Mount

    ##
    # See +CarrierWave::Mount#mount_uploader+ for documentation
    #
    def mount_uploader(column, uploader, options={}, &block)
      options[:mount_on] ||= "#{column}_filename"
      property options[:mount_on]

      super

      alias_method :read_uploader, :read_attribute
      alias_method :write_uploader, :write_attribute

      include CarrierWave::Validations::ActiveModel

      validates_integrity_of  column if uploader_option(column.to_sym, :validate_integrity)
      validates_processing_of column if uploader_option(column.to_sym, :validate_processing)

      after_save "store_#{column}!".to_sym
      before_save "write_#{column}_identifier".to_sym
      after_destroy "remove_#{column}!".to_sym
    end    
  end
end

CouchRest::Model::Base.class_eval do
  extend ::CarrierWave::CouchrestModel
end

app/uploaders/avatar_uploader.rb

# encoding: utf-8
class AvatarUploader < CarrierWave::Uploader::Base
  include CarrierWave::MiniMagick

  storage :fog

  fog_credentials({
    :provider               => 'AWS',
    :aws_access_key_id      => 'xxx',
    :aws_secret_access_key  => 'yyy'
  })
  fog_directory  'cabify'
  fog_public     true
  fog_attributes 'Cache-Control' => 'max-age=315576000'

  def store_dir
    "#{Rails.env}/avatars/#{model.id}"
  end

  def default_url
    if model.email.present?
      model.gravatar_url
    else
      "/images/avatars/" + [version_name, "default.png"].compact.join('_')
    end
  end

  process :resize_to_fit => [250, 250]

  version :thumb do
    process :resize_to_fill => [80, 80]
  end

  def extension_white_list
    %w(jpg jpeg gif png)
  end
end

The line in the gem with the error:

https://github.com/carrierwaveuploader/carrierwave/blob/v0.5.8/lib/carrierwave/uploader/url.rb#L18

the problem is that root == nil

Backtrace

TypeError - can't convert nil into String:
  (gem) carrierwave-0.5.8/lib/carrierwave/uploader/url.rb:22:in `url'
  (gem) carrierwave-0.5.8/lib/carrierwave/uploader/versions.rb:164:in `url'
  (gem) carrierwave-0.5.8/lib/carrierwave/uploader/default_url.rb:8:in `url'
  app/models/user.rb:344:in `avatar_url'
  app/controllers/admin/users_controller.rb:56:in `update'
  (gem) actionpack-3.1.11/lib/action_controller/metal/implicit_render.rb:4:in `send_action'
  (gem) actionpack-3.1.11/lib/abstract_controller/base.rb:167:in `process_action'
  (gem) actionpack-3.1.11/lib/action_controller/metal/rendering.rb:10:in `process_action'
  (gem) actionpack-3.1.11/lib/abstract_controller/callbacks.rb:18:in `block in process_action'
  (gem) activesupport-3.1.11/lib/active_support/callbacks.rb:443:in `_run__2850817817751956370__process_action__3254483072592469464__callbacks'
  (gem) activesupport-3.1.11/lib/active_support/callbacks.rb:386:in `_run_process_action_callbacks'
  (gem) activesupport-3.1.11/lib/active_support/callbacks.rb:81:in `run_callbacks'
  (gem) actionpack-3.1.11/lib/abstract_controller/callbacks.rb:17:in `process_action'
  (gem) actionpack-3.1.11/lib/action_controller/metal/rescue.rb:17:in `process_action'

app/models/user.rb (line 344)

class User < CouchRest::Model::Base
  mount_uploader :avatar, AvatarUploader

  def avatar_url
    avatar.thumb.url
  end
end

the uploading form

= form_for [:admin, @user], :html => {:multipart => true} do |f|
  = f.file_field :avatar
2
avatar.thumb.url - what is avatar?? may be you wanted to say user.thumb.url? or if avatar is the uploaded file then you probably need to add self.avatar.thumb.url.rmagnum2002
Updated the question. avatar is the indeed the file. self.avatar.thumb.url gives the same error.Michael Koper

2 Answers

1
votes

In this branch solution given by stephenmurdoch was helpfull for me. Try to add


def root
  Rails.root.join 'public/'
end

in your uploader to force CarrierWave temporary upload directory location.

0
votes

In the end I fixed it by forking the gem and changing the dependencies to Rails 3.1. So you can upgrade to the carrierwave 0.8.0 with Rails 3.1

If somebody got the same issue, try out my fork: https://github.com/michaelkoper/carrierwave.git