I've been searching for a way to construct an image from my LinkedIn profile picture and use the url with Carrierwave but it bugs out because of the missing extension in the LI url that gets retrieved.
Example of LI url: "https://media.licdn.com/mpr/mprx/......." with no .jpeg .jpg .png
When I try to do user.remote_image_url = linkedin_url and proceed to do user.save it complains about the file type not being allowed which in this case would be ''
Anyone have any ideas as to how I can achieve this or if it's even possible?
Since I couldn't find a way to get the extension from LI I went away and hacked something out which seems to work fine now
image = open(user.linkedin_url) { |f| f.read }
File.rename(image.path, "#{image.path}.jpg")
user.image = File.open("#{image.path}.jpg")
user.save!
Related
Currently users can download an ActiveStorage blob in my app using the following link:
link_to 'download', rails_blob_path(pj.document.file, disposition: 'attachment')
However, I would like to update an attribute in the database for the associated model to register when the file was first downloaded. This field is called the downloaded_at field.
I have made the following attempt:
Changed the link_to > button_to as I'm updating the model.
Added the appropriate route
Added the following code in the database:
def download
#proofreading_job = ProofreadingJob.find(params[:id])
#proofreading_job.update(downloaded_at: Time.current) if current_user == #proofreading_job.proofreader.user
response.headers["Content-Type"] = #proofreading_job.document.file.content_type
response.headers["Content-Disposition"] = "attachment; #{#proofreading_job.document.file.filename.parameters}"
#proofreading_job.document.file.download do |chunk|
response.stream.write(chunk)
end
ensure
response.stream.close
end
However, this does not do anything except redirect to the #proofreading_job page which is not what I want.
Has anyone done this before and if so how can I accomplish this task.
I think you can also try using your action controller as a proxy, the concept is this:
download the file in your action
check if it is downloaded successfully and other validations
perform clean up operations (in your case the added code in your #3)
send the file back to user using the send_data/send_file rendering method
E.g. in your controller:
def download
file = open(params[:uri])
validate!
cleanup!
send_file file.path
end
Then in your view:
link_to 'download', your_controller_path
Above is just concept and I apologize for only providing pseudo code in advance.
In the end I just used some javascript to capture the click of the button as follows:
td = link_to rails_blob_path(pj.document.file, disposition: 'attachment'),
id: pj.document.id,
download: pj.document.file_name,
class: "btn btn-outline-secondary btn-sm btn-download" do
=pj.document.file_name
i.fa.fa-download.ml-3 aria-hidden="true"
coffee script:
$('.btn-download').on 'click', (e) ->
id = $(this).attr('id')
$.ajax {url: Routes.document_path(id), type: 'PUT'}
routes.rb
resources :documents, only: [:show, :update]
documents_controller.rb:
def update
document = Document.find(params[:id])
authorize([:proofreaders, document])
document.update(downloaded_at: Time.current) if document.downloaded_at.nil?
head :ok
end
This seems to work very well. It updates the database and the user gets the file downloaded to their computer.
I have a user module and I have generated paperclip attachment: profile_pic
user.rb:
has_attached_file :profile_pic,
style: { :medium => "300x300>", thumb: "100x100>" },
default_url: "/images/:style/missing.png"
controller:
image_base = params[:manager][:profile_pic]
if image_base != nil
image = Paperclip.io_adapters.for(image_base)
image.original_filename = params[:manager][:file_name]
current_user.profile_pic = image
current_user.errors.delete(:profile_pic)
current_user.save
end
config/initializers/paperclip.rb:
Paperclip::DataUriAdapter.register
It's not showing any errors but If I am trying to display the image, it gives me following error:
ActionController::RoutingError (No route matches [GET] "/system/managers/profile_pics/000/000/008/original/icon_new.png"):
When I am trying in console like:
user.profile_pic.display
/system/managers/profile_pics/000/000/008/original/icon_new.png?
1556082410 => nil
Picture was saved in public folder
The default folder is the following, so Paperclip uploaded to the right place:
:rails_root/public/system/:class/:attachment/:id_partition/:style/:filename
But it looks like you are having troubles accessing the right location. Have you tried user.profile_pic.url? I tried on my working example, both .display and .url are the same but I use an AWS S3 bucket.
user.profile_pic.url should be where to find the file on the web.
user.profile_pic.path should be where to find the file on the file system.
The problem is with production mode and Solved this by adding the following line in production.rb
config.public_file_server.enabled = true
I have a rails 4 app with a Grape API and Swagger through the gem grape-swagger and grape-swagger-ui gems.
In dev everything works well, I load http://localhost:3000/api/swagger and the swagger header's text input along the top loads the expected url, http://localhost:3000/api/swagger_doc. This points properly to the file it seeks, swagger_doc.json.
I've pushed this app to heroku, which forces https connections. Unfortunately, when loading https://my-app.herokuapp.com/api/swagger the swagger header's text input along the top loads http://my-app.herokuapp.com/api/swagger_doc instead of loading https://my-app.herokuapp.com/api/swagger_doc (http vs https).
I've tried coming at this from the heroku side with things like:
routes.rb
unless Rails.env.development?
get "*path" => redirect("https://my-app.herokuapp.com%{path}"), :constraints => { :protocol => "http://" }
post "*path" => redirect("https://my-app.herokuapp.com%{path}"), :constraints => { :protocol => "http://" }
end
config/environments/production
config.force_ssl = false
config/environments/production
#config.force_ssl = false
And I've come at it with trying to set or manipulate the base_path attribute of add_swagger_documentation.
app/controllers/api/base.rb
base_path: "my-app.herokuapp.com",
app/controllers/api/base.rb
base_path: "http://my-app.herokuapp.com",
app/controllers/api/base.rb
base_path: = lambda do |request|
return "http://my-app.herokuapp.com"
end
app/controllers/api/base.rb
base_path: lambda { |request| "http://#{request.host}:#{request.port}" }
I recently clicked "view raw" on one of my resources and noticed that it was picking up my changes to base_path but that base_path isn't even used to populate the url in the text input in the swagger header. It seems to be generated from a js file. I'm unable to edit it and would happily accept a hack to do so as a solution. Here's that raw output:
https://gist.github.com/johnnygoodman/5fd246765dc5236fb8c4
The line of interest is:
"basePath":"http://localhost:3000/my-app.herokuapp.com"
Which would break the app if it was being populated and used, but it is not. I don't see an option in the grape-swagger gem that I can use to pass in this variable and change the path to https.
In conclusion:
I'd like the swagger text input box to load https://my-app.herokuapp.com/api/swagger_doc when I visit https://my-app.herokuapp.com/api/swagger.
Anyone know a hack to accomplish this on heroku?
I was able to work around this. I suggest:
Do not use + uninstall #gem 'grape-swagger-ui'
Use and install gem 'grape-swagger-rails' and follow the docs here: https://github.com/ruby-grape/grape-swagger-rails
I'm having a really weird problem with my rails app and facebook's open graph beta. Whenever I post an action to an object, Facebook returns an error that seems to indicate the URL of the object can't be reached, or the og scraper isn't scraping the URL correctly.
However, when I take the URL the app is generating for the post to Facebook and manually use the HTTParty gem to post it, it works.
Here's my code:
class Post < ActiveRecord::Base
FB_CONFIG = YAML.load_file("#{Rails.root}/config/initializers/facebook.yml")[Rails.env]
def self.to_facebook_og(obj, obj_id, verb, auth, extra)
#requires that a user has granted `publish_actions`
found_obj = obj.classify.constantize.find(obj_id) #find the actual object we're talking about
post_url = self.construct_facebook_action_url(obj, found_obj, verb, auth, extra) #create the URL
begin
ret = HTTParty.post(post_url)
logger.info "Facebook Post Action Response = #{ret}"
rescue HTTParty::ResponseError => e #handle any errors
logger.error {"FACEBOOK Response #{ret.code} / #{e.inspect}"}
flash.alert {"There was a Facebook problem. Please try again."}
return
end
end
def self.construct_facebook_action_url(obj, found_obj, verb, auth, extra)
base = 'https://graph.facebook.com/'
uid = auth.uid
namespace = FB_CONFIG['namespace']
token = "?access_token=#{auth.token}"
og_url = "#{obj}=http://theshortestfiction.com/#{obj.pluralize}/#{found_obj.id}"
fb_url = base + uid + '/' + namespace + ':' + verb + token + '&' + og_url + extra
logger.info fb_url
fb_url
end
def self.lint_og_object(obj_url)
lint_ret = HTTParty.post("https://developers.facebook.com/tools/lint/?url=#{obj_url}&format=json")
logger.info "Facebook Linter Response = #{lint_ret}"
end
end
When an object is read via its controller's show method, the app calls Post.to_facebook. From my logs, I can see that that Post.construct_facebook_action_url is constructing the proper url (because like I said, I can pull the URL from the logs and manually post it from the console). So, I'm assuming there's so problem with how I'm passing the URL to HTTParty? Facebook seems able to tell what object URL it should be looking at. Why does the code I've written not work, but manually in the console, it does?
Even weirder -- once there's been a sucessful post action on the object once, the code seems to work consistently. Facebook insists the problem is that the objects' URLs aren't reachable, but I can't understand how they're not, since I can browse to them.
I think this is actually a timeout issue.
I had the exact same issue as you, using HTTParty and getting the URL can't be reached error.
I moved the code to a background process using Resque and it fixed the problem.
Using rails 3.0.10, we need to send mail messages with html and plain text alternative where the html part references images sent along as inline attachments.
The code:
def invite(secure_share)
#share = secure_share
attachments.inline['download.png'] = File.read "#{Rails.root}/public/images/download.png"
mail( :to => secure_share.recipient,
:from => 'dummy#example.com',
) do |format|
format.html { render :layout => 'cargo_secureshare_mailer' }
format.text
end
end
The templates are in place, the inline attachment works and we get a mail with the following structure:
Content-type "multipart/related"
Part "multipart/alternative"
Part "text/html"
Part "text/plain"
Part "image/png" (inline attachment)
Neither Apple Mail nor Thunderbird seem to like this, they will not show the HTML version but only a text version with two "normal" attachments. It seems like the multipart structure is wrong - shouldn't it have "multipart/alternative" as the content type and then "multipart/related" as a wrapper for the html with inline attachments?
Anyone a hint how to fix this?
Found here: http://www.shortround.net/2011/04/07/multipart-alternative-multipart-related-email-with-actionmailer-for-rails-3/
It almost works. i.e. it works for regular attchments but fails for inlined