ruby 如何使用 HTTParty 实现这个 POST 请求?

声明:本页面是StackOverFlow热门问题的中英对照翻译,遵循CC BY-SA 4.0协议,如果您需要使用它,必须同样遵循CC BY-SA许可,注明原文地址和作者信息,同时你必须将它归于原作者(不是我):StackOverFlow 原文地址: http://stackoverflow.com/questions/19461333/
Warning: these are provided under cc-by-sa 4.0 license. You are free to use/share it, But you must attribute it to the original authors (not me): StackOverFlow

提示:将鼠标放在中文语句上可以显示对应的英文。显示中英文
时间:2020-09-06 06:14:31  来源:igfitidea点击:

How can I implement this POST request using HTTParty?

rubycurlhttparty

提问by John Kelly Ferguson

I am having difficulty making a POST request to an API endpoint using Ruby's HTTParty library. The API I'm interacting with is the Gittip APIand their endpoint requires authentication. I have been able to successfully make an authenticated GET request using HTTParty.

我无法使用 Ruby 的 HTTParty 库向 API 端点发出 POST 请求。我正在与之交互的 API 是Gittip API,它们的端点需要身份验证。我已经能够使用 HTTParty 成功发出经过身份验证的 GET 请求。

You can see in the example code:

您可以在示例代码中看到:

user = "gratitude_test"
api_key = "5962b93a-5bf7-4cb6-ae6f-aa4114c5e4f2"
# I have included real credentials since the above is merely a test account.

HTTParty.get("https://www.gittip.com/#{user}/tips.json", 
             { :basic_auth => { :username => api_key } })

That request works and returns the following as expected:

该请求有效并按预期返回以下内容:

[
  {
    "amount" => "1.00",
    "platform" => "gittip",
    "username" => "whit537"
  },
  {
    "amount" => "0.25",
    "platform" => "gittip",
    "username" => "JohnKellyFerguson"
  }
]

However, I have been unable to make a successful POST request using HTTParty. The Gittip API describes making a POST request using curl as follows:

但是,我一直无法使用 HTTParty 发出成功的 POST 请求。Gittip API 描述了使用 curl 发出 POST 请求,如下所示:

curl https://www.gittip.com/foobar/tips.json \
  -u API_KEY: \
  -X POST \
  -d'[{"username":"bazbuz", "platform":"gittip", "amount": "1.00"}]' \
  -H"Content-Type: application/json"

I have tried (unsuccessfully) structuring my code using HTTParty as follows:

我已经尝试(不成功)使用 HTTParty 构建我的代码,如下所示:

user = "gratitude_test"
api_key = "5962b93a-5bf7-4cb6-ae6f-aa4114c5e4f2"

HTTParty.post("https://www.gittip.com/#{user}/tips.json",
              { 
                :body => [ { "amount" => "0.25", "platform" => "gittip", "username" => "whit537" } ],
                :basic_auth => { :username => api_key },
                :headers => { 'Content-Type' => 'application/json' }
               })

The first argument is the url and the second argument is an options hash. When I run the code above, I get the following error:

第一个参数是 url,第二个参数是选项哈希。当我运行上面的代码时,出现以下错误:

NoMethodError: undefined method `bytesize' for [{"amount"=>"0.25", "platform"=>"gittip", "username"=>"whit537"}]:Array
  from /Users/John/.rvm/rubies/ruby-2.0.0-p247/lib/ruby/2.0.0/net/http/generic_request.rb:179:in `send_request_with_body'

I have tried various other combinations of structuring the API call, but can't figure out how to get it to work. Here's another such example, where I do not user an array as part of the body and convert the contents to_json.

我尝试了构建 API 调用的各种其他组合,但无法弄清楚如何让它工作。这是另一个这样的例子,我不使用数组作为主体的一部分并转换内容to_json

user = "gratitude_test"
api_key = "5962b93a-5bf7-4cb6-ae6f-aa4114c5e4f2"

HTTParty.post("https://www.gittip.com/#{user}/tips.json",
          {
            :body => { "amount" => "0.25", "platform" => "gittip", "username" => "whit537" }.to_json,
            :basic_auth => { :username => api_key },
            :headers => { 'Content-Type' => 'application/json' }
           })

Which returns the following (a 500 error):

返回以下内容(500 错误):

<html>
  <head>
    <title>500 Internal Server Error</title>
  </head>
  <body>\n        Internal server error, program!\n        <pre></pre>  
  </body>
</html>

I'm not really familiar with curl, so I'm not sure if I am incorrectly translating things to HTTParty.

我对 curl 不是很熟悉,所以我不确定我是否错误地将内容转换为 HTTParty。

Any help would be appreciated. Thanks.

任何帮助,将不胜感激。谢谢。

回答by d_ethier

Just a guess, but it looks like you're passing a hash in the body when JSON is expected.

只是一个猜测,但看起来您在预期 JSON 时在正文中传递了一个哈希值。

Try replacing the :bodydeclaration with:

尝试将:body声明替换为:

:body => [{ "amount" => "0.25", 
             "platform" => "gittip", 
             "username" => "whit537" }].to_json

Edit: I suggested the to_jsonserializer, but misplaced it by putting it after the hash instead of the array and removing the array altogether. The example uses multiple records, so the array is necessary.

编辑:我建议使用to_json序列化程序,但是通过将它放在散列而不是数组之后并完全删除数组而将其放错了位置。该示例使用多条记录,因此数组是必需的。

After looking at this thread, it looks like Gittip is picky about the accept header.

看了这个帖子后,看起来 Gittip 对 accept 标头很挑剔。

:headers => { 'Content-Type' => 'application/json', 'Accept' => 'application/json'}

So, the full suggestion is:

所以,完整的建议是:

HTTParty.post("https://www.gittip.com/#{user}/tips.json",
  { 
    :body => [ { "amount" => "0.25", "platform" => "gittip", "username" => "whit537" } ].to_json,
    :basic_auth => { :username => api_key },
    :headers => { 'Content-Type' => 'application/json', 'Accept' => 'application/json'}
  })