Http links from Paperclip with s3 - ruby-on-rails

I'm using Paperclip with s3_permissions = :private
I have some assets of the same model that are public and I want to generate a HTTP link for them (not HTTPS)
for generating the url I'm currently using my_model.my_asset.expiring_url(1000)
how can I do that?
Thank you

You should be able to configure the s3_protocol to be HTTP (it defaults to HTTPS when s3_permissions are not public_read):
# config/application.rb
config.paperclip_defaults = {
storage: :s3,
s3_protocol: 'http',
s3_permissions: :private,
s3_credentials: { ... }
}
That said, if you set the protocol to HTTP, you will be potentially exposing the assets anyway. HTTPS would be preferable if you care about privacy of the assets.
You can read more about the available options here.

Related

Rails application resources not getting rendered over https

I am using ruby 2.4.0p0 and Rails 5.2.3
In the production.rb file I have done the following setting:
# Force all access to the app over SSL, use Strict-Transport-Security, and use secure cookies.
config.force_ssl = true
if Rails.application.config.force_ssl
Rails.application.routes.default_url_options[:protocol] = 'https'
end
But still the resource are getting rendered on http rather then https do I need to do any thing extra, please provide the desired thing to be done to get all assets getting loaded from s3 loads over https.
The website is live here at: https://tukaweb.com/asset/garments
The s3 resources are at http
ex: http://tukaweb.s3.amazonaws.com/uploads/three_d_garment/thumbnail/7/Womens_Dress_35-41_Thumbnail.png?X-Amz-Expires=600&X-Amz-Date=20200918T060705Z&X-Amz-Algorithm=AWS4-HMAC-SHA256&X-Amz-Credential=AKIAIRDA3IQIVTEPMN6Q%2F20200918%2Fus-west-2%2Fs3%2Faws4_request&X-Amz-SignedHeaders=host&X-Amz-Signature=1792bd4cc2437abd950b7d16d360d09e64423bdef89f41c24a5386d35e982dfa
need them over https.
The required change should be done inside the carrierwave.rb inside the webapp/config/initializers directory modified the settings as:
CarrierWave.configure do |config|
config.fog_provider = 'fog/aws'
config.fog_credentials = {
provider: 'AWS',
aws_access_key_id: 'XXXXXXXXXX',
aws_secret_access_key: 'xxxxxxxxxx',
use_iam_profile: false,
region: 'us-west-2', # optional, defaults to 'us-east-1'
# host: 'ec2-xx-xxx-xx-xx.us-west-2.compute.amazonaws.com', # optional, defaults to nil
:endpoint => 'https://s3.amazonaws.com',
}
config.fog_directory = 'tukaweb' # required
config.fog_public = false # optional, defaults to true
# config.fog_attributes = { cache_control: "public, max-age=#{365.days.to_i}" } # optional, defaults to {}
end
The line which is responsible for changing s3 resource to be downloaded from https instead of http
:endpoint => 'https://s3.amazonaws.com' ## earlier it was 'http://s3.amazonaws.com'
Force SSL only works for the incoming requests to the rail's routes. If you have an image link set to http://image-domain.com/image it's going to use the http, and you'll get a mixed content warning. You need to ensure anything external to the app's routes is going to be using SSL or a secure connection as well.
First thing I do when I see a mixed content warning is to do a global search of the codebase for http:// to find everywhere that isn't using https://. I may or may not do a global find + replace depending on what I see, there are cases where it needs to be http:// or it won't work right (if the site doesn't have an https:// version).
Next thing is to work out what is causing the insecure url, here it is S3, so I would be looking at what uses S3, and working out how I can tell it to use SSL or a secure connection.
Note: The other answer does well explaining what your actual issue is, but this may be more useful to others for general troubleshooting of mixed content issues, and would lead to the same result.

Rails Sitemap_generator using aws_fog configuration

I am using sitemap_generator gem with rails 6 on heroku. I am told the easiest way is to use an s3 on amazon and bridge with aws_fog.
The implementation is well documented on the gem side... but I am struggling to make sure the amazon config is correct.
I search a lot and couldn't find anything so I was hoping someone could help
I configure an s3 instance lets name it example and I add it to region US East(Ohio). This is all pretty simple.
The Properties tab... what should and shouldn't be selected? i select nothing.
The Permissions tab. I make public, although this feels wrong... the bucket is for a sitemap, so it should be public right?
I set up my region as per the doumentation
SitemapGenerator::Sitemap.default_host = "https://www.example.com"
SitemapGenerator::Sitemap.public_path = 'tmp/'
SitemapGenerator::Sitemap.sitemaps_host = "https://example.s3.amazonaws.com/"
SitemapGenerator::Sitemap.sitemaps_path = 'sitemaps/'
SitemapGenerator::Sitemap.adapter = SitemapGenerator::S3Adapter.new(fog_provider: 'AWS',
aws_access_key_id: Rails.application.credentials.aws[:access_key_id],
aws_secret_access_key: Rails.application.credentials.aws[:secret_access_key],
fog_region: 'us-east-2')
when i hit rake sitemap:refresh:no_ping on my local host I get :status_line => "HTTP/1.1 301 Moved Permanently\r\n"
I think maybe i need to add the sitemaps folder to the s3 instance, so i do but i still get the :status_line => "HTTP/1.1 301 Moved Permanently\r\n".
Any tips would be great...
I am also using sitemap-generator gem on my rails application (heroku hosted and rails 6). I have the following code inside config/sitemap.rb, before SitemapGenerator::Sitemap.create. I have configured it with aws-sdk-s3 gem and it goes like this:
require 'aws-sdk-s3'
SitemapGenerator::Sitemap.default_host = "https://www.example.com"
SitemapGenerator::Sitemap.sitemaps_host = 'https://example.s3.eu-west-2.amazonaws.com/'
SitemapGenerator::Sitemap.adapter = SitemapGenerator::AwsSdkAdapter.new(Rails.application.credentials.dig(:amazon, :s3, :bucket),
aws_access_key_id: Rails.application.credentials.dig(:amazon, :s3, :access_key_id),
aws_secret_access_key: Rails.application.credentials.dig(:amazon, :s3, :secret_access_key),
aws_region: Rails.application.credentials.dig(:amazon, :s3, :region)
)

How to properly setup Rails + Paperclip + AWS CDN + Heroku

It seems like I finally figured how to setup Rails + Paperclip + AWS CDN + Heroku.
Everything seems to be working. Both CSS and js files load from cdn, as well as images.
Unfortunately sharing functionality is broken. Open graph can't parse image url. I assume it's because links are in this format https:////drex16ydhdd8s.cloudfront.net/...rest_of_url
Originally, long time ago, I've configured CDN link to be //drex16ydhdd8s.cloudfront.net. I understand I need to remove slashes in front of the link, make it drex16ydhdd8s.cloudfront.net instead.
The problem is, if I do it, Heroku gives me Application Error. (displays their static page)
Logs don't display anything helpful, other than it seems it goes over memory limit pretty much immediately.
I've contacted Heroku support, but their response was
You should not need any slashes, it should just be a host name. (As seen in the documentation for config.action_controller.asset_host.)
If removing the slashes causes errors, you'll want to debug those errors.
I tried to do it locally, everything seems to work as expected.
environments/production.rb
config.action_controller.asset_host = ENV.fetch("ASSET_HOST", ENV.fetch("APPLICATION_HOST"))
config.paperclip_defaults = {
storage: :s3,
s3_protocol: :https,
s3_region: ENV["AWS_REGION"],
url: ":s3_alias_url",
path: "/:class/:attachment/:id_partition/:style/:filename",
s3_host_alias: ENV.fetch("ASSET_HOST"),
s3_credentials: {
bucket: ENV["S3_BUCKET_NAME"],
access_key_id: ENV["AWS_ACCESS_KEY_ID"],
secret_access_key: ENV["AWS_SECRET_ACCESS_KEY"]
},
default_url: "https://s3.amazonaws.com/ezpoisk/missing-small.png"
}
env variable
ASSET_HOST = //drex16ydhdd8s.cloudfront.net
on CDN I have 2 befaviors
/assets/* - that points to domain name
default (*) - that points to s3 bucket
Does anyone have any ideas?
Solution.
I had in production.rb
config.assets.compile = true
I'm not strong on details here, I just remember that I made a note on this line to possibly remove it when switching to cdn.
After digging through this answer I have decided to try it out. So I
removed the lined,
deployed,
all works fine.
Tried updating cdn link then.
At first, same issue persisted, url for some reason was /drex16ydhdd8s.cloudfront.net, but after few seconds it now seems
to be all good.

rails carrierwave + fog speed optimisation

I currently using carrierwave with fog to store and upload images using an s3 bucket but the images load much slower than they should. These images load almost instantly when stored as part of the application - but stored with carrierwave and fog it takes a few seconds.
Is this a problem with my s3 setup or carrierwave/fog? My carrierwave config is the following:
CarrierWave.configure do |config|
config.fog_credentials = {
:provider => 'AWS', # required
:aws_access_key_id => '***', # required
:aws_secret_access_key => '***', # required
}
config.cache_dir = "#{Rails.root}/tmp/uploads" # To let CarrierWave work on heroku
config.fog_directory = 'bucketname' # required NB: having '.' in the bucket name creates an untrusted certificate
config.fog_public = false # optional, defaults to true
config.fog_attributes = {'Cache-Control'=>'max-age=315576000'} # optional, defaults to {}
end
I do have my s3 bucket configured for the US and I'm located in Australia so that might pose a few problems - but my heroku app is also configured to the US and it loads the same images blazingly quick when they're stored as part of the app itself. Maybe aws isn't the best solution?
Anyway any solutions on how I can improve the speed of image load time would be great. It just seems unnecessarily slower than it should be.
It sounds like you want to use CloudFront, Amazon's CDN (content delivery network) service that integrates with S3. Using a CDN will globally replicate the content you're storing in CDN (for a price), which should improve your load times.
After you set up a CloudFront account and link it to S3, add a line like the following to your CarrierWave configuration:
config.asset_host = "http://1234567.cloudfront.net"
With the URL that you get during CloudFront setup.
Unfortunately it looks like you may also need to set config.fog_public = true for Carrierwave to be able to use Amazon's CDN.

Rails 3 Paperclip with file upload/downloads

I have a rails 3 app that allows users to share files by uploading them to Amazon s3 via paperclip, and I want to allow others users to download these files. However, some sort of post-processing seems to be going on with this file somewhere between my app and Amazon s3.
Here's my code:
has_attached_file :attachment,
:storage => :s3, :s3_credentials => "#{RAILS_ROOT}/config/s3.yml",
:path => ':id/:style', :bucket => "test_development"
This works fine, however if I actually go to the amazon s3 developer tools the url for the file just seems to be: http://s3.amazonaws.com/test_development/1/original without the original name or type.
I then tried using something like this: [p.attachment.url(:original, false), p.attachment_file_name].join("/")
which yields: http://s3.amazonaws.com/test_development/1/original/test.pdf
However if I got to this url I get a cryptic xml error:
<Error>
<Code>NoSuchKey</Code>
<Message>The specified key does not exist.</Message>
<Key>1/original/About Downloads.pdf</Key>
<RequestId>7E5CC6A01CADF831</RequestId>
<HostId>
4ruFf0JtdalnaIE/SHUAqT8hVYEda9Ul6gxNmYTIAniw7piTN+Q16uKKCzi9yezl
</HostId>
</Error>
What am I doing wrong here? I just want to upload the file to s3 without any sort of processing then download again later..how should I go about doing this?
Thanks!
The :path option is is used as the full filename. Nothing is added, it's only interpolated. Try :path => ':id/:style/:basename.:extension'.
And when you change :path, you often have to change :url also.
More infos:
http://rdoc.info/github/thoughtbot/paperclip/master/Paperclip/Storage/S3
http://rdoc.info/github/thoughtbot/paperclip/master/Paperclip/Storage/Filesystem
http://rdoc.info/github/thoughtbot/paperclip/master/Paperclip/ClassMethods#has_attached_file-instance_method

Resources