Get mosaic-like screenshot using IMGKit - ruby-on-rails

Here I want to take a screenshot of an external url, and I use IMGkit with CarrierWave.
#Class Micropost
after_create :take_snapshot
def take_snapshot
file = Tempfile.new(["template_#{self.id.to_s}", 'jpg'], 'tmp', :encoding => 'ascii-8bit')
file.write(IMGKit.new(self.external_url).to_jpg)
file.flush
self.snapshot = file
self.save
file.unlink
end
and the screenshot get generated is.....
So whats wrong with it?

Related

How to set all attributes to UploadedFile in Rails 4

I've an API and I send a image from Angular Client in Base64, I've the next code for my method create:
if params[:profile][:picture]
picture_params = params[:profile][:picture]
#Create new Temporal File
temp_file = Tempfile.new("file_to_upload")
temp_file.binmode
temp_file.write(Base64.decode64(picture_params["body"]))
#Create a new uploaded file
uploaded_file = ActionDispatch::Http::UploadedFile.new(
:tempfile => temp_file,
:original_filename => picture_params[:name])
#After replace picture with the new uploaded file
params[:profile][:picture] = uploaded_file
Rails.logger.info "#{params[:profile]}"
end
#profile = #current_user.build_profile(profile_params)
if #profile.save
render "api/v1/profiles/show"
else
errors_array!(#profile.errors.full_messages, :unprocessable_entity)
end
After when I print my params the information is nil
"picture"=>#<ActionDispatch::Http::UploadedFile:0x007f872daac5b0 #tempfile=#<Tempfile:/var/folders/nx/30024wp17ggfgw542lyzs4zw0000gn/T/file_to_upload20160225-14952-by947r>, #original_filename=nil, #content_type=nil, #headers=nil>}
And after when try to create the profile I've the next error, I think that is for the previous problem
NoMethodError (undefined method `gsub' for nil:NilClass):
app/controllers/api/v1/profiles_controller.rb:39:in `create'
I use the paperclip gem for upload files in Rails 4.2.5.1
Thanks for watching, but Have a solution, I changed my method:
def set_selfies(selfie_params)
picture_params = selfie_params
encoded_picture = picture_params[:body]
content_type = picture_params[:content_type]
image = Paperclip.io_adapters.for("#{encoded_picture}")
image.original_filename = picture_params[:name]
image
end
I Read this Blog:
And That's all, works for me, Thanks :D

Invalid encoding with rqrcode

I'm having an invalid encoding error that doesn't let me save the image to a carrierwave uploader.
require 'rqrcode_png'
img = RQRCode::QRCode.new( 'test', :size => 4, :level => :h ).to_img.to_s
img.valid_encoding?
=> false
I'm not sure if this is what you're looking for, in my case I needed to associate the generated QR code with a Rails model using carrierwave, what I ended up doing was saving the image to a temp file, associating that file with the model and afterwards deleting the temp file, here's my code:
def generate_qr_code!
tmp_path = Rails.root.join('tmp', "some-filename.png")
tmp_file = RQRCode::QRCode.new(self.hash_value).to_img.resize(200,200).save(tmp_path)
# Stream is handed closed, we need to reopen it
File.open(tmp_file.path) do |file|
self.qr_code = file
end
File.delete(tmp_file.path)
self.save!
end

Rails + Prawn_rails: How do I add an image to my PDF?

I'm using this gem to use Prawn to create a PDF: https://github.com/Whoops/prawn-rails
However, I can't seem to figure out how to add an image. I've tried pdf.image "path/to/img.jpg but it would say the file is not a recognized format.
I've also looked into this on page 101: http://prawn.majesticseacreature.com/manual.pdf , but it doesn't work.
This is happening in the views:
prawn_document() do |pdf|
pdf.image "#{Rails.root}/public/logo.gif"
end
This throws:
Prawn::Errors::UnsupportedImageType at /admin/purchases/6188.pdf
image file is an unrecognised format
Same happens for a .jpg image
I would do something like this.
gem 'prawn'
bundle install
In your controller.
def controller_method
pdf = Prawn::Document.new
begin
pdf_file_path = "#{Rails.root}/public/output"
full_doc = "#{Rails.root}/public/something.png"
pdf.image full_doc
pdf.start_new_page
pdf.render_file pdf_file_path
rescue Prawn::Errors::UnsupportedImageType
flash[:notice] = "Image unsupported"
redirect_to '/handle'
end
end
Adding an image is easy enough.
def download
#document = Document.find(params[:id])
tmp_file = Tempfile.new(Digest::MD5.hexdigest(rand(12).to_s))
pdf = Prawn::Document.generate(tmp_file.path, :margin => 0, :page_size => "A4", :skip_page_creation => true) do |posting|
posting.start_new_page
posting.image #document.user.logo.path
send_data posting.render, :filename => "whatever.pdf", :type => "application/pdf"
end
end
Obviously #document.user.logo.path could be a literal path, that's just a Paperclip attachment in this case.
UPDATE
If it's a literal path you might need to do something like this:
require "open-uri"
def download
...
posting.image File.open("/path/to/image.jpg")
...
end
It seems the latest prawn (version 1.0.0) has changed. You'll get
undefined method `image=' for #<Prawn::Document
if you try and apply something to pdf.image.
This worked for me:
img = "#{Rails.root}/public/my_lovely_image.png"
Prawn::Document.new(background: img)

Rails 3 - Tempfile Path?

I have the following:
attachments.each do |a|
Rails.logger.info a.filename
tempfile = Tempfile.new("#{a.filename}", "#{Rails.root.to_s}/tmp/")
Rails.logger.info tempfile.path
end
Where attachments is from paperclip.
Here's the output:
billgates.jpg
/Users/bhellman/Sites/cline/tmp/billgates.jpg20101204-17402-of0u9o-0
Why is the file name getting 20101204-17402-of0u9o-0 appended to at the end? That's breaking everything with paperclip etc. Anyone seen this before? For the life of I have no idea what's doing it?
Thanks
UPDATE
Paperclip: Paperclip on github
a is the attachment file
tempfile = Tempfile.new("#{a.filename}", "#{Rails.root.to_s}/tmp/")
tempfile << a.body
tempfile.puts
attachments.build(
:attachment => File.open(tempfile.path)
)
best make sure your tempfile has the correct extension, saving you to trying and change it after:
file = Tempfile.new(['hello', '.jpg'])
file.path # => something like: "/tmp/hello2843-8392-92849382--0.jpg"
more here: http://apidock.com/ruby/v1_9_3_125/Tempfile/new/class
The first argument for Tempfile.new is just a basename. To make sure each Tempfile is unique the characters are appended to the end of the file.
You should use Paperclip's API for this:
tempfiles = []
attachments.each do |a|
# use Attachment#to_file to get a :filesystem => file, :s3 => tempfile
tempfiles << a.to_file
end
tempfiles.each do |tf|
Rails.logger.debug tf.filename
end
attachment = attachments.build(
:attachment => File.open(tempfile.path)
)
# change the displayed file name stored in the db record here
attachment.attachment_file_name = a.filename # or whatever else you like
attachment.save!
The best way I found to deal with this was to specify the file extension in the Paperclip attribute. For example:
has_attached_file :picture,
:url => "/system/:hash.jpg",
:hash_secret => "long_secret_string",
:storage => :s3,
:s3_credentials => "#{Rails.root}/config/s3.yml"
Note that the :url is declared as '.jpg' rather than the traditional .:extension.
Good luck!

Difficulty with send_data in Ruby on Rails in conjunction with Spreadsheet plug-in

I have a function in a controller that takes in some specifications and generates a report on them. This function user_report is called in a view:
< %= submit_to_remote 'submit-button', "Export Report to Excel", :url => { :controller => :reports, :action => :user_report, :print_state => 'print'} % >
In reports_controller I use the Spreadsheet plugin to generate an Excel file within the user_report function. I want to use send_data to stream the file to the user without creating it on the server first. The research I've done shows that using StringIO is the way to go, as shown below. Frustratingly, nothing happens when I call send_data. The plugin seems to work well creating a file and saving it on the server, but does nothing when I use send_file, suggesting that the problem doesn't lie in the plugin. But then what am I doing wrong with send_file/send_data?
The function itself looks like this:
def user_report
if request.post?
unless params[:reports][:userid].blank?
#userid=params[:reports][:userid]
end
if params[:print_state]=='print'
report = Spreadsheet::Workbook.new
info = report.create_worksheet :name => 'User Information'
info.row(1).push 'User ID', #userid
#outfile = "Report_for_#{#userid}.xls"
require 'stringio'
data = StringIO.new ''
report.write data
send_data data.string, :type=>"application/excel", :disposition=>'attachment', :filename => #outfile
end
respond_to do |format|
format.js { }
end
end
end
The log file reads
2010-10-18 14:13:59 INFO -- Sending data Report_for_jjohnson.xls
but no download begins in-browser. I've succeed in using send_data on this app before, which is confusing.
I'm using Rails v2.3, Ruby v1.8.7, and Spreadsheet v6.4.1 at spreadsheet.rubyforge.org.
Just change the line:
send_data data.string, :type=>"application/excel", :disposition=>'attachment', :filename => #outfile
to:
send_data data.string.bytes.to_a.pack("C*"), :type=>"application/excel", :disposition=>'attachment', :filename => #outfile
Even though I dont like to write and delete , but with spreadsheet seems like the only solution.
# write the file
book.write "Employee_History_#{ params[:id]}.xls"
# send the file
send_file "Employee_History_#{ params[:id]}.xls", :type => "application/vnd.ms-excel", :filename => "data.xls", :stream => false
# and then delete the file
File.delete("Employee_History_#{ params[:id]}.xls")
For someone looking at this in (or after) 2022, a possible solution to this would be to use Axlsx Gem. The interface provides a method for converting it to a StringIO object. (From Axlsx Documentation)
#serialize to a file
p = Axlsx::Package.new
# ......add cool stuff to your workbook......
# Serialize to a stream
s = p.to_stream()
send_data(
s.read,
:type => 'application/vnd.openxmlformats-officedocument.spreadsheetml.sheet',
:disposition => 'attachment',
:filename => #filename
)

Resources