Configuring Paths in Development and Production - ruby-on-rails

I have an app that lets users download itineraries if they like the preview of the first page. In order to make the preview, I use PDF Reader to parse the original document and create a PDF version of the first page.
In development, the original itinerary is stored in the public folder.
#itin_preview = itinerary
reader = PDF::Reader.new("public/#{#itin_preview/document_file_name}")
formatted_page = reader.page(1)
formatted_text = formatted_page.text.gsub! /\s+/, ''
page_text = formatted_text.gsub!(/$/, "\n")
This return public/itinerary.pdf. However, in production, the itinerary is stored on Amazon AWS, so i tried to configure an initializer with different paths in a YAML file for development and production, taken from here.
config.rb
APP_CONFIG = YAML.load_file("#{Rails.root}/config/initializers/config.yml")
config.yml
development:
itinerary_path: /public/#{#itin_preview.document_file_name}
production:
itinerary_path: <%= asset_path "#{#itin_preview.document_file_name}" %>
When I input the constant into my PDF Reader like so,
reader = PDF::Reader.new(APP_CONFIG[Rails.env]['itinerary_path'])
I get the following error:
Completed 500 Internal Server Error in 19ms (ActiveRecord: 1.3ms)
ArgumentError (input must be an IO-like object or a filename):
I have double checked that APP_CONFIG[Rails.env]['itinerary_path'] spits out public/itinerary.pdf in development. So why does it work as a string but not as a Constant?
How can i get it to work?

Related

Process an uploaded file to remove unwanted leading string before renaming

A file is being uploaded by rails and is logged as follows:
Parameters: {"authenticity_token"=>"[FILTERED]", "account"=>{"main_file"=>#<ActionDispatch::Http::UploadedFile:0x000000010922f7b8 #tempfile=#<Tempfile:/var/folders/jf/13j7d83s4_79kb5c4lkgdy0r0000gn/T/RackMultipart20221116-18676-44klzi.js>, #original_filename="smaller_sample_array.js"
The following does not work as the file is not a string per se
params[:account][:main_file] = params[:account][:main_file].reverse.chomp("revision.main.categories.part.0 = ".reverse).reverse
> NoMethodError (undefined method `reverse' for #<ActionDispatch::Http::UploadedFile:
while there is a method for renaming:
self.active_storage_object.blob.update(filename: "#{account_id}_#{self.active_storage_object.filename}.json")
what is a recommended method - or flow of methods - to alter (reverse chomp) the file contents?
Bote: if a file is first saved, then calling in this case account.file (Account has_one_attached :file), the view shows:
ActiveStorage::Attached::One:0x0000000106775338>
The file saved under the storage directory can be found, but have no idea how to access it from the rails controller.

Ruby on Rails copy S3 file with special characters (%C5) in path

I have a problem with my attachment system on web page. I store them on amazon S3 using paperclip. I have an option to copy attachment to new file. Everything works fine until there are polish special characters in title, like: ŁĄKA.jpg. Then I get an error:
Saving error: Appendix Paperclip::Errors::NotIdentifiedByImageMagickError
/Users/michal/.rbenv/versions/2.1.5/lib/ruby/gems/2.1.0/gems/activerecord-4.2.5/lib/active_record/validations.rb:79:in `raise_record_invalid'
/Users/michal/.rbenv/versions/2.1.5/lib/ruby/gems/2.1.0/gems/activerecord-4.2.5/lib/active_record/validations.rb:43:in `save!'
My code:
instance.appendixes.select {|a| a.temporary? && !a.appendix.exists?}.each do |a|
a.appendix = S3File.new(a.s3path)
a.process = false
a.appendix_url = nil
puts "CREATING NEW FILE from (temporary?) appendix: #{a.id}, path: #{a.s3path}, is_public: #{a.is_public}, determine_is_public: #{a.determine_is_public}"
a.is_public = a.determine_is_public
logger.debug("CREATING NEW FILE from (temporary?) appendix: #{a.id}, path: #{a.s3path}, is_public: #{a.is_public}, determine_is_public: #{a.determine_is_public}")
a.save! # bo delayed_job
end
I'm getting error on a.save! when path is like: appendixes/appendixes/242/original/%25C5%2581A%25CC%25A8KA.jpg, but works like charm when it is: appendixes/appendixes/243/original/laka.jpg or another file name without polish letters. Anybody had this kind of problem or have suggestions how to fix it?
Ok, I found what was wrong. I had to replace in a.s3path, the last part with original name (łąka.jpg) and everything works fine. So when I have:
S3File.new(appendixes/appendixes/243/original/łąka.jpg) it works good and finds the correct file on s3 server.

Attach a pdf in asset pipeline using ActionMailer Rails 4

I'm trying to attach a file to an email. The file is in assets/downloads/product.pdf
In the mailer, I have:
attachments["product.pdf"] = File.read(ActionController::Base.helpers.asset_path("product.pdf"))
I've tried:
attachments["product.pdf"] = File.read(ActionController::Base.helpers.asset_url("product.pdf"))
...and even:
attachments["product.pdf"] = File.read(ActionController::Base.helpers.compute_asset_host("product.pdf") + ActionController::Base.helpers.compute_asset_path("product.pdf"))
I always get the same error:
EmailJob crashed!
Errno::ENOENT: No such file or directory - //localhost:3000/assets/product.pdf
...or a variation on the theme. But even when I try using asset_url in the view or just put the url in the browser it works:
http://localhost:3000/assets/product.pdf
I've also tried using straight up:
File.read("app/assets/downloads/product.pdf")
File.read("downloads/product.pdf")
...which works in dev environment but not on staging server (heroku). Error is still:
Errno::ENOENT: No such file or directory - downloads/product-market-fit-storyboard.pdf
Also tried:
File.read("/downloads/product.pdf")
File.read("http://lvh.me:3000/assets/product.pdf")
...don't work at all.
Ideas?
you should use syntex like this.it is work for me may be will work for you also.
File.open(Dir.glob("#{Rails.root}/app/assets/downloads/product.pdf"), "r")
When using mailer, you shouldn't use assets pipline. Asset pipeline would be useful if you wanted to have link to a file inside your email. When rendering an email, action mailer has access to files in app directory.
Please read about attachments in action mailer guide. As you can see, you just need to pass path to a file, not url:
attachments['filename.jpg'] = File.read('/path/to/filename.jpg')

Displaying the image saved to the database as blob correctly

I have a web application on Rails and now I am about to seed some data. I am stuck on displaying the image that is saved as a blob type in database.
In my seeds.rb
user = User.find(1)
file = File.open("db/seeds/images/stewart.jpg").read
user.user_image = file
user.save!
The image (stewart.jpg):
http://postimg.org/image/qyjagb2xf/1418c08f/
In my left.html.erb file where the image is displayed:
<%= ("<img id = 'profile-image' width = '80' height = '80' alt = 'image' class = 'list_image' src='data:image/jpg;base64,%s'>" % Base64.encode64(#user.user_image)).html_safe %>
After the seeding, I checked the database using SQLite browser and I confirmed that the image has been
read. But when I rendered left.html.erb, here is what the image looked like:
The image rendered:
http://postimg.org/image/mnr9bo5yl/5aea8b27/
Additionally, the data type in migration file is binary in which the equivalent type in sqlite is blob, and I don't want to use extra gems like paperclip and the like.
Thanks in advance.
This solved the problem:
file = File.open("db/seeds/images/stewart.jpg", "rb").read
The line above reads the file in binary mode.
Thanks to Mr. Bryan Bibat of Ruby Users Group - Philippines (https://www.facebook.com/groups/phrug/)

Set System Directory Rails Production Environment

I have an app that works fine in on my development machine, but on my production server it uses a broken link to serve an image served using the Paperclip Gem.
Production environment is Linux(Debian), Apache, Passenger and I am deploying with Capistrano.
The app is stored in (a symlink that points to the public folder of the current version of the app deployed using capistrano):
/var/www/apps/root/appname
However, when I try and access it on the production server, the Apache error log displays this as the path it is looking in:
/var/www/apps/root/system
The correct path, however, is:
/var/www/apps/appname/shared/system
One option available to me is to create a symlink in root that directs system to the correct path, but I don't want to do this in case I want to deploy another app in the same root dir.
The url for this request is generated by rails, but Apache is what fetches the static resource (image files), so I have tried placing the following in my config/environments/production.rb:
ENV["RAILS_RELATIVE_URL_ROOT"] = '/appname/'
Which has resolved all other pathing issues I've been experiencing, but when rails generates the url (via the Paperclip gem), it doesn't seem to use it.
How can I set it so Paperclip uses the right path and only uses it production?
I've a workaround, add this as one of initializers:
config/initializer/paperclip.rb
Paperclip::Attachment.class_eval do
def url(style_name = default_style, options = {})
if options == true || options == false # Backwards compatibility.
res = #url_generator.for(style_name, default_options.merge(:timestamp => options))
else
res = #url_generator.for(style_name, default_options.merge(options))
end
# replace adding uri before res, minus final /
Rails.application.config.site_relative_url[0..-2]+res
end
end
At the moment Paperclip doesn’t work with ENV['RAILS_RELATIVE_URL_ROOT'] and the. You can follow the issue here:
https://github.com/thoughtbot/paperclip/issues/889

Resources