I'm using api request/response on my rails app. To update avatar i've got this request(i took it from development.log file)
Started PUT "/user/avatars.json" for 127.0.0.1 at 2017-07-18 11:47:57 +0300
Processing by AvatarsController#update as JSON
Parameters: {"avatar"=>#<ActionDispatch::Http::UploadedFile:0x007fe6cbedae18 #tempfile=#<Tempfile:/var/folders/n3/5_nb_zks2k91r5ngcmb4fm9r0000gn/T/RackMultipart20170718-26576-1vss7hh.png>, #original_filename="Снимок экрана 2017-07-16 в 21.55.05.png", #content_type="image/png", #headers="Content-Disposition: form-data; name=\"avatar\"; filename=\"\xD0\xA1\xD0\xBD\xD0\xB8\xD0\xBC\xD0\xBE\xD0\xBA \xD1\x8D\xD0\xBA\xD1\x80\xD0\xB0\xD0\xBD\xD0\xB0 2017-07-16 \xD0\xB2 21.55.05.png\"\r\nContent-Type: image/png\r\n">}
Now, I need to send this request from POSTMAN application. But it uses ruby syntax like =>. How can I convert it to json to use in POSTMAN?
http://3dml.free.fr/rubyhashconverter/
I don't know if you need to do it within your code or not, but the above is an online converter, takes ruby hash syntax (old and new) and gives valid JSON.
JSON doesn't support binary data(images). So in order to pass the image, you need to convert image to base64 string and use it in JSON.
Related
I need to send the raw audio data that a user records in the browser to an API.
I'm sending the raw blob object via POST to my Rails backend. It looks like this when recieved.
{"blob"=>#<ActionDispatch::Http::UploadedFile:0x00007f83ad01a7d8 #tempfile=#<Tempfile:/var/folders/cc/f7_d06hs6psbcxl87nwzsplr0000gn/T/RackMultipart20201021-933-1xu271c>, #original_filename="blob", #content_type="audio/wav", #headers="Content-Disposition: form-data; name=\"blob\"; filename=\"blob\"\r\nContent-Type: audio/wav\r\n">, "controller"=>"audios", "action"=>"interview"}
How can I read the actual data and extract it (without headers) to send to the external service?
The ActionDispatch::Http::UploadedFile looks similar to an IO object, so you can probably just:
uploaded_file = params["blob"]
raw_string = uploaded_file.read # do what you want with the raw data
In html, the params like this:
Parameters: {"utf8"=>"✓", "authenticity_token"=>"tLy5M77xdhBr5pyQQsVw43T08THDNQ1z1yDdpC3oM0/jZR/lARPUF8wxNObFa2g/KgtGv5dW/mqDmXCtFmBFSQ==", "post"=>{"title"=>"test text tent"=>"34343", "tag_list"=>"fasd", "skill_list"=>"", "cover"=>#<ActionDispatch::Http::UploadedFile:0x007ff22d2c0688 #tempfile=#<Tempfile:/var/folders/_g/7kks48cd1199yrsgzh965tq00000gn/T/RackMultipart20161011-93895-ub0blw.png>, #original_filename="28_logo.png", #content_type="image/png", #headers="Content-Disposition: form-data; name=\"post[cover]\"; filename=\"28_logo.png\"\r\nContent-Type: image/png\r\n">, "cover_cache"=>""}, "commit"=>"Update Post", "id"=>"1"}
Without file upload,test by reset client use json only will look like this:
Parameters: {"title"=>"test text ", "id"=>"1", "post"=>{"title"=>test text "}}
The problem is ,how could I send Parameters with file to serve on Rest Client/postman tool to use ruby on rails restful api?
Expect wrapped format:
{"title"=>"test text ", "id"=>"1", "post"=>{"title"=>test text ",'cover"=>#<ActionDispatch::Http::UploadedFile.....}}
In Postman their is a two options beside field "value". You can choose file to add image.
I am trying to upload a csv file to Rails and parse it into a db. I have tried using both Paw and Postman to send the http request, specifying POST, attaching the csv file, and specifying Content-Type as application/csv
The request header:
POST /skate_parks/import HTTP/1.1
Content-Type: text/csv
Host: localhost:3000
Connection: close
User-Agent: Paw/2.3.4 (Macintosh; OS X/10.11.5) GCDHTTPRequest
Content-Length: 11663
Name,Address,Suburb,Postcode,State,Business Category,LGA,Region,
Aireys Inlet Skate Park,Great Ocean Road,Aireys Inlet,3231,VIC,Skate Parks,Surf Coast,Barwon S/W, etc...
The controller skate_parks_controller.rb
def import
SkatePark.import(params[:body])
end
The model
class SkatePark < ApplicationRecord
require 'csv'
def self.import(file)
CSV.foreach("file", headers: true) do |row|
skate_park_hash = row.to_hash
skate_park = SkatePark.where(name: skate_park_hash["name"])
if skate_park.count == 1
skate_park.first.update_attributes(skate_park_hash)
else
SkatePark.create!(skate_park_hash)
end
end
end
end
The error
Started POST "/skate_parks/import" for ::1 at 2016-05-26 13:48:34 +1000
Processing by SkateParksController#import as HTML
Completed 500 Internal Server Error in 3ms (ActiveRecord: 0.0ms)
Errno::ENOENT (No such file or directory # rb_sysopen - file):
app/models/skate_park.rb:6:in `import'
app/controllers/skate_parks_controller.rb:7:in `import'
The problem is params[:body] is nil, so you're essentially calling SkatePark.import(nil). Rails doesn't put the raw POST body into params like you've apparently assumed it does.
You have two options. The better option, in my opinion, is to upload the data as multipart/form-data. Rather than putting the raw data into the POST body, you'll do the same thing a browser does when a user chooses a file in an <input type="file">, which is to say you'll encode it as form data. When you do that, you will be able to access the data through params, as described in the Form Helpers Rails Guide under "Uploading Files." (Since you apparently aren't using a form, you can skip to "What Gets Uploaded" to see how to handle the data you receive.)
To test this with Postman, follow the instructions for "form-data" under "Request body" in the Sending Requests docs, which I'll excerpt here for posterity:
multipart/form-data is the default encoding a web form uses to transfer data. This simulates filling a form on a website, and submitting it. The form-data editor lets you set key/value pairs (using the key-value editor) for your data. You can attach files to a key as well.
Your other option is to access the POST body directly via request.raw_post as described here: How to access the raw unaltered http POST data in Rails? This is not very "Railsy," however, and among other things will be harder to test.
I have a client in java that sends form post requests with video file.
I get in the server following POST:
Parameters: {"video"=>#<ActionDispatch::Http::UploadedFile:0x007f26783b49d0
#original_filename="video", #content_type=nil,
#headers="Content-Disposition: form-data; name=\"video\"; filename=\"video\"\r\n",
#tempfile=#<Tempfile:/tmp/RackMultipart20160405-3-106c9nr>>, "id"=>"36"}
I am trying to save the file to s3 using following lines:
I know the connection and actual saving works because I tried with base64 string as parameter and it worked well.
body = params[:video].tempfile
video_temp_file = write_to_file(body)
VideoUploader.new.upload_video_to_s3(video_temp_file, params[:id].to_s+'.mp4')
I see on s3 empty files or 24 bytes.
where do i do wrong?
Edit: I am using carrierwave:
def write_to_file(content)
thumbnail_file = Tempfile.new(['video','.mp4'])
thumbnail_file.binmode # note that the tempfile must be in binary mode
thumbnail_file.write content
thumbnail_file.rewind
thumbnail_file
end
I am building API for Android using RoR, I am getting the Parameters for creating an object from Android is like below,
{"company"=>"{\"description\":\"Description of the company\",\"name\":\"Google\"}", "location"=>"Bangalore", "display_photo"=>#<ActionDispatch::Http::UploadedFile:0xb12dfa8 #tempfile=#<Tempfile:/tmp/RackMultipart20141119-6448-ewg4bk>, #original_filename="Male-Face-A1-icon.png", #content_type="image/*", #headers="Content-Disposition: form-data; name=\"display_photo\"; filename=\"Male-Face-A1-icon.png\"\r\nContent-Type: image/*\r\nContent-Length: 15460\r\nContent-Transfer-Encoding: binary\r\n">}
But this line giving error when parsing
"company"=>"{\"description\":\"Description of the company\",\"name\":\"Google\"}"
Because, It should be like this for Rails,
"company"=>{"description":"Description of the company","name":"Google"}
How to achieve this in Rails...
Refer this link where Android is requesting to Rails Server,
Android Code
In you params:
"company"=>
is a hash key
"{\"description\":\"Description of the company\",\"name\":\"Google\"}"
is a string, hash value
[2] pry(main)> JSON.parse "{\"description\":\"Description of the company\",\"name\":\"Google\"}"
=> {"description"=>"Description of the company", "name"=>"Google"}
gives correct output