Rails Active Storage + AWS Rekognition: How to get IO file - ruby-on-rails

I'm trying to integrate AWS Rekognition into my Rails app. After the user uploads his avatar via Active Storage, Rekognition should show some info about it.
def update
respond_to do |format|
if #user.update(user_params)
if #user.images.attached?
Aws.config.update({
region: 'us-west-2',
credentials: Aws::Credentials.new('ACCESS_KEY', 'SECRET_KEY')
})
rekognition = Aws::Rekognition::Client.new(region: Aws.config[:region], credentials: Aws.config[:credentials])
img = #user.images.first. # original was: File.read(ARGV.first)
#detect faces
resp = rekognition.detect_faces({
image: { bytes: img },
attributes: ["ALL"], # What attributes to return
})
resp.face_details[0].emotions.each do |emo|
puts emo.type + " " + emo.confidence.to_i.to_s #=> Strings "HAPPY", "SAD", "ANGRY"
end
end
end
end
However, I get the error
expected params[:image][:bytes] to be a String or IO object, got value #<ActiveStorage::Attachment id: 4, name: "images", record_type: "User", record_id: 47, blob_id: 9, created_at: ""> (class: ActiveStorage::Attachment) instead.
How can I get the image file property into AWS Rekognition?

There is two way to pass image to Aws::Rekognition.
AWS S3 image url and name
resp = rekognition.detect_faces(
{image:
{s3_object:
{bucket: `bucket name`,
name: `pull path of file`,
},
}, attributes: ['ALL'],
}
)
Via Image object
rekognition.detect_faces({
image: { bytes: File.read(`path of file`) }
})
in your case you are passing ActiveStorage object that can't parse by AWS. that's why it throw error.

Related

RoR - Capsens/universign - SignatureField - The coordinates aren't working

I'm trying to set a transaction to Universign with the "capsens_universign" gem.
Here's my code to create the transaction:
document_from_content = Universign::Document.new(
name: 'another.pdf',
content: File.open("tmp/test.pdf").read
)
signer = Universign::TransactionSigner.new(
first_name: "Signer's first name",
last_name: "Signer's last name",
email: 'test#gmail.com',
phone_number: 'SOME_PHONE_NUMBER',
success_url: 'https://my_app.com',
signature: Universign::SignatureField.new(coordinate: [37,684], page: 5)
)
transaction = Universign::Transaction.create(
documents: [document_from_content],
signers: [signer],
options: { profile: 'default', final_doc_sent: false, handwritten_signature_mode: 0}
)
I got a code 200 response from this. I can sign the pdf BUT signature stamps are not showing in the PDF generated by Universign when the transaction is completed.
Is it because of this configuration ? Or maybe I didn't understand well the different signatures configurations.

Rails Active Storage + AWS Rekognition detect_labels: filtered labels

I'm trying to get AWS Rekognition to work with Rails 6 rc3 with photos stored in S3 via Active Storage.
Aws.config.update({
region: 'us-west-2',
credentials: Aws::Credentials.new(Rails.application.credentials.aws[:access_key], Rails.application.credentials.aws[:secret_access_key])
})
rekognition = Aws::Rekognition::Client.new(region: Aws.config[:region], credentials: Aws.config[:credentials])
#uri = #user.avatar.service_url
#dir = #uri.split("/").fourth
#key = #dir.split("?").first
response = rekognition.detect_labels(
{image:
{s3_object:
{bucket: 'bucket',
name: #key,
},
},
max_labels: 5,
min_confidence: 70
}
)
puts response
#user.update(notes: response)
However the labels in the response shows 'FILTERED'
{:labels=>[{:name=>"[FILTERED]", :confidence=>99.28252410888672, :instances=>[], :parents=>[{:name=>"[FILTERED]"}
Doing the same thing over aws-cli shows the labels. Why does it show 'filtered' and how can I show the labels?
Loop through the response object and print the labels field if you want to see them them unfiltered:
response.labels.each { |label| puts(label.name) }

Paperclip Unpermitted parameter: image

I am trying to get Paperclip to upload an image to s3 from my festival model on form submit but am receiving the Unpermitted parameter: image. error
I have checked the strong params, the model content validation and read through the paperclip documents with no avail.
I think I have narrowed the problem down to my post request to the DB cannot handle the File object that gets assigned to festival.image, but can't figure out how I would represent this in the post request.
I am capturing the data in rails using react on rails on the front end with Rails as the backend. I was following along with this sample code https://github.com/carlbaron/react-file-upload-demo
I also use React-dropzone to capture the uploaded file and it adds the preview attribute for the image preview.
Been stuck on this for some time now, any help greatly appreciated!
Beginning of the post request printed to console
Processing by FestivalsController#create as JSON
Parameters: {"festival"=>{"fest_name"=>"Test Festival", "image"=>{"preview"=>"blob:http://localhost:5000/76b95cb5-45bf-46a9-ba7b-f5b9ad127521"}}}
| Unpermitted parameter: image
Festival object printed to the console
Post Request to the DB via axios
postFestival(festival) {
let config = {
responseType: 'json',
processData: false,
contentType: false,
headers: ReactOnRails.authenticityHeaders(),
};
let str = JSON.stringify(festival);
console.log("ENTITY IS " + str);
//returns
//ENTITY IS {"fest_name":"Test Festival","image":{"preview":"blob:http://localhost:5000/76b95cb5-45bf-46a9-ba7b-f5b9ad127521"}}
return(
request.post('/festivals/create', {festival}, config)
);
},
Festival.rb
class Festival < ApplicationRecord
has_attached_file :image, default_url: "/assets/ASOT-COVER.png"
validates_attachment :image,
content_type: { content_type: ["image/jpeg", "image/gif", "image/png"] }
end
Festivals Controller
def create
#festival = Festival.create(festival_params)
puts "festival.image =" + #festival.image.inspect
#returns = festival.image =#<Paperclip::Attachment:0x007fc288868bf0 #name=:image, #name_string="image", #instance=#
if #festival.save
puts "Festival SAved = + " + #festival.inspect
#returns the festival object saved to the DB minus the image param
else
respond_to do |format|
format.json { render json: #festival.errors, status: :unprocessable_entity}
puts "ERROR = " + #festival.errors.inspect
end
end
private
def festival_params
params.require(:festival).permit(:fest_name, :fest_organizer, :fest_location,
:fest_date, :fest_url, :fest_venue, :fest_description,
:image)
end
end
As the image parameter in your request is a hash "image"=>{"preview"=>"blob:http://localhost:5000/76b95cb5-45bf-46a9-ba7b-f5b9ad127521"}, you will need to modify your festival_params method like this:
def festival_params
params.require(:festival).permit(:fest_name, :fest_organizer, :fest_location,
:fest_date, :fest_url, :fest_venue, :fest_description,
{ image: :preview })
end
Let me know if it solves the error.

How can I fix this unexpected token (JSON parser error)

I am trying to save data from an API to my database, but I'm running into an error. The error states: unexpected token at 'object' (JSON::ParserError)
Here is my code:
require 'rest-client'
require 'pp'
endpoint = "https://api.leaddyno.com/v1/leads"
class TestDyno
def parser(page_number)
## API key
request = {:params => {:key => Rails.application.secrets.LEADDYNO_PRIVATE, page: page_number}}
## Parse JSON
response = JSON.parse(RestClient.get endpoint, request)
#response_count = response.count # Count results on the page.
pp response
puts response_count
end
def data
until #response_count == 0
1.upto(5) do |page_number|
response['object'].each do |item|
LeaddynoLead.save(
leaddyno_lead_id: item['id'],
email: item['email'],
first_name: item['first_name'],
last_name: item['last_name'],
latest_visitor_id: item['latest_visitor']['id'],
latest_visitor_code: item['latest_visitor']['tracking_code'],
url: item['url']['url'],
referrer_id: item['referrer']['id'],
referrer_url: item['referrer']['url'],
leaddyno_affiliate_id: item['affiliate']['id'],
leaddyno_affiliate_email: item['affiliate']['email'],
search_term: item['search_term']['term'],
search_engine: item['search_term']['search_engine'],
leaddyno_tracking_code: item['tracking_code'],
created_at: item['created_at'],
updated_at: item['updated_at']
)
sleep 0.5
end
end
end
end
end
retrieve = TestDyno.new
retrieve.data
I guess I need another set of eyes to look at this and see what is wrong?
The API docs are here if that helps. Thanks.

Rails signature does not match amazon s3

I had uploads to Amazon s3 working with AngularJS and NodeJS but now am using Rails as the backend. So I figured all I'd have to do is translade NodeJS code to Rails. Source: https://github.com/nukulb/s3-angular-file-upload/blob/master/lib/controllers/aws.js
and my conversion:
def aws_signature
mime_type = "image/jpeg"
expiration = Date.new(Time.now.year + 1, 01, 01) #Time.now.utc.strftime('%Y/%m/%d %H:%M:%S+00:00')
s3_policy = {
expiration: expiration,
conditions: [
['starts-with', '$key', '/'],
{bucket: ENV["BUCKET"] },
{acl: 'public-read'},
['starts-with', '$Content-Type', mime_type],
{success_action_status: '201'}
]
}
puts s3_policy.inspect
string_policy = s3_policy.to_json
puts string_policy.inspect
base64_policy = URI.escape(Base64.encode64(string_policy).strip)
puts base64_policy.inspect
digest = OpenSSL::Digest::Digest.new('sha1')
signature = OpenSSL::HMAC.digest(digest, ENV["S3_SECRET"], base64_policy)
puts signature.inspect
s3_credentials = {
s3Policy: base64_policy,
s3Signature: signature,
AWSAccessKeyId: ENV["S3_KEY"]
}
render json: s3_credentials
end
Now I am getting a 304 response from Amazon with SignatureDoesNotMatch in xml.
Did I miss something in the conversion to rails code?
Is there a way to compare the unencrypted params received in amazon?

Resources