I have a user model that is generated using Devise. I am extending this model using paperclip to enable file upload and also the processing of a file using a custom paperclip processor.
My paperclip field is declared in the user model as follows. PaperClipStorage is a hash that I create with the paperclip variables. Also, the being stored on AWS S3.
has_attached_file :rb_resume, PaperclipStorageHash.merge(:style => { :contents => 'resume_contents'}, :processors => [:resume_builder])
validates_attachment_content_type :rb_resume, :if => lambda { |x| x.rb_resume? }, :content_type => ['application/pdf', 'application/x-pdf', 'application/msword', 'application/x-doc']
The validates_attachment_content_type check is being done to make sure that it only processes pdf and MS word files.
My processor looks as follows
module Paperclip
class ResumeBuilder < Processor
def initialize(file,options = {}, attachment = nil)
#file = file
#attachment = attachment
puts "Attachment is not null " if !attachment.nil?
end
def make
rb = MyModule::MyClass.new(#file.path) ### Do something with the file
section_layout = rb.parse_html
#attachment.instance_write(:whiny, section_layout)
#file
end
end
end
In my user model I also have an after_save callback that is supposed to take the section_layout generated in the processors make method. Code is as follows
after_save :save_sections
def save_sections
section_layout = rb_resume.instance_read(:whiny)
# Do something with section_layout...
end
Now my problem is that the processor code is never being called, and I can't figure out why.
Because of that the section_layout variable is always nil.
Another point to note is that the same model also has two other has_attached_file attributes. None of the other two use a custom processor.
I've been struggling with this for last 3 hours. Any help would be greatly appreciate.
Thanks
Paul
Error in my has_attached_file declaration
has_attached_file :rb_resume, PaperclipStorageHash.merge(:style => { :contents => 'resume_contents'}, :processors => [:resume_builder])
should actually be
has_attached_file :rb_resume, PaperclipStorageHash.merge(:styles => { :contents => 'resume_contents'}, :processors => [:resume_builder])
Notice the plural styles as opposed to singular style
Related
My User model:
class User < ActiveRecord::Base
has_attached_file :avatar, :styles => { :profile => "200x200>", :collab => "300x200>", :msg => "50x50>" }, :default_url => "missing.png"
validates_attachment_content_type :avatar, :content_type => /\Aimage\/.*\Z/
...
I have just added the :msg and :profile styles and I'm trying to refresh them so they show up properly in my views.
I've tried running:
rake paperclip:refresh CLASS=User
and I get this error:
rake aborted!
ArgumentError: wrong number of arguments (0 for 1)
/home/jrile/rails/cs480/app/models/user.rb:44:in `hash'
/home/jrile/.rvm/gems/ruby-2.1.0/gems/paperclip-4.1.1/lib/paperclip/attachment_registry.rb:42:in `names_for'
/home/jrile/.rvm/gems/ruby-2.1.0/gems/paperclip-4.1.1/lib/paperclip/attachment_registry.rb:16:in `names_for'
/home/jrile/rails/cs480/lib/tasks/paperclip.rake:15:in `obtain_attachments'
Here's line 44 of user.rb (not sure why this has anything to do with paperclip)
def User.hash(token)
Digest::SHA1.hexdigest(token.to_s)
end
I was trying to add an avatar following railstutorial.org.
EDIT: Also, in all my views where I'm trying to display the avatar, it's displaying ":msg" even if I'm trying to display one of the other two. I.E.,
<%= image_tag user.avatar.url(:profile) %>
is showing the 50x50 avatar.
For the first issue, from this SO question
You shouldn't override ruby core methods like object#hash they are made for specific reasons and changing their behavior could cause unexpected results , apparently later on the tutorial this will change to:
def User.digest(token)
Digest::SHA1.hexdigest(token.to_s)
end
I have the following ToyPhoto model:
require "open-uri"
class ToyPhoto < ActiveRecord::Base
belongs_to :toy
has_attached_file :image, :styles => {
:thumb => ["210x210>", :jpg]
}
def image_url=(value)
self.image = open(value)
end
end
When I upload a photo, I don't see the corresponding thumb folder being created. This is how I create the ToyPhoto objects:
params[:photos].each do |photo|
#toy_photo = ToyPhoto.new
#toy_photo.image_url = photo[:url]
#toy_photo.save
#toy.photos << #toy_photo
end
I do see photo being successfully uploaded to original folder, but no thumb folder created. Did I miss some configuration problem? I am suspecting that strong_parameter didn't defined when uploading from url, however I am not sure how to set strong_parameter in this case.
Thanks!
I believe that the problem in your code is how you specify the format of the thumb style. Reading the Paperclip API showed that the proper way to do this is like so:
has_attached_file :image, :styles => { :thumb => ["210x210#", :jpg] }
Using Rails 2, I try to separate different, dynamic image sizes trough another Model from the Paperclip-Model. My current approach, using a Proc, looks the following:
class File < ActiveRecord::Base
has_many :sizes, :class_name => "FileSize"
has_attached_file(
:attachment,
:styles => Proc.new { |instance| instance.attachment_sizes }
)
def attachment_sizes
sizes = { :thumb => ["100x100"] }
self.sizes.each do |size|
sizes[:"#{size.id}"] = ["#{size.width}x#{size.height}"]
end
sizes
end
end
class FileSize < ActiveRecord::Base
belongs_to :file
after_create :reprocess
after_destroy :reprocess
private
def reprocess
self.file.attachment.reprocess!
end
end
Everything seems to work out fine but apparently no styles are processed and no image is being created.
Did anyone manage doing stuff like this?
-- Update --
Obviously the method attachment_sizes on instance sometimes is not defined for # - but shouldn't instance actually be #?
For me this looks like altering instance..
The solution is simple. instance in my first example Proc is an instance of Paperclip::Attachment. As I want to call a File method, one has to get the calling instance inside the Proc:
Proc.new { |clip| clip.instance.attachment_sizes }
instance represents File-instance in the given example.
I'm assuming you have everything working with paperclip, such that you have uploaded an image and now the proc is just not working.
It should work. Try not putting the size in an array.
You are doing this
sizes = { :thumb => ["100x100"] }
But I have it where I'm not putting the size in an arry
sizes = { :thumb => "100x100" }
Give that a try :)
Is there anyway to have the validates_attachment_size except a dynamic file size limit? Here's an example:
class Document < ActiveRecord::Base
belongs_to :folder
has_attached_file :document
validates_attachment_size :document, :less_than => get_current_file_size_limit
private
def get_current_file_size_limit
10.megabytes # This will dynamically change
end
end
I've tried this but I keep getting an error saying "unknown method". Lambdas and Procs don't work either. Has anyone ever tried this? Thanks
Paperclip doesn't allow to pass function as size limit parameter. So you probably need to write custom validation:
validate :validate_image_size
def validate_image_size
if document.file? && document.size > get_current_file_size_limit
errors.add_to_base(" ... Your error message")
end
end
Long shot...
validates_attachment_size :document, :less_than => :get_current_file_size_limit
Usually when passing a function you have to pass the symbol and not the actual function.
There is a built-in Paperclip validation now:
validates_attachment_size :mp3, :less_than => 10.megabytes
Change mp3 to whatever your paperclipped file's name is.
See this post for more helpful Paperclip tips: http://thewebfellas.com/blog/2008/11/2/goodbye-attachment_fu-hello-paperclip
I'm creating a program which will be examining images which are uploaded by the users logged in. I have the RMagick code written up to do the examination (basically finding out if a pixel black is in an image), but I don't know how to write the unit tests for this model.
Currently I'm using paperclip to attach the uploaded file to the model, which I understand uses a number of fields in the database for tracking the files. How should I set up my fixtures so that I can do unit testing on the same data every time?
My model is currently:
class Map < ActiveRecord::Base
has_attached_file :image, :styles => { :small => "150x150>" }
validates_attachment_presence :image
validates_uniqueness_of :name, :message => "must be unique"
def pixel_is_black(x, y)
<code to return true if position (x,y) in image is black>
end
end
Best to read up on the usage of fixture_file_upload in your functional tests
For unit tests, i normally have a teardown method that deletes the files once done they have been modified (though it can be used to copy over originals, whatever you want - see the fileutils library for that)
def setup
FileUtils.cp 'original.jpg', '/path/to/where/file/exists/in/fixture.jpg'
end
def teardown
Fileutils.rm '/path/to/where/file/exists/in/fixture.jpg', :force => true
end
http://api.rubyonrails.org/classes/ActionController/TestProcess.html#M000406
http://www.ruby-doc.org/stdlib/libdoc/fileutils/rdoc/index.html