【问题标题】:Question about authentication in API GET call关于 API GET 调用中的身份验证问题
【发布时间】:2019-10-10 20:01:05
【问题描述】:

我正在尝试使用 USDA 网站上描述的 Food Data Central REST API 访问基本食品信息:

Food Data Central API Guide

对于这个项目,我正在使用 R 中的 httr (v 1.3.1) 包进行调用。

API 调用的文档看起来不错,并提供了一些示例;不幸的是,这些示例都没有使用 R,而且由于我对 API 开发知之甚少,我不确定文档的“内容”应该如何翻译给我。该文档提供了以下示例:

curl -H "Content-Type:application/json"

-d '{"generalSearchInput":"Cheddar cheese"}'

-X POST

https://DEMO_KEY@api.nal.usda.gov/fdc/v1/search

我看到一个“Content-Type”标题和一个正文,其中字符串“Cheddar cheese”被提供给一个名为generalSearchInput的参数。看来我还需要用我自己的 API 密钥替换“DEMO_KEY”字符串。

我宁愿不分享我自己的 API 密钥,而是 it's painless to request one(点击链接,输入姓名/电子邮件,几秒钟后获得密钥,甚至不必确认电子邮件)。

下面是我在 httr 包中复制此调用的尝试:

httr::POST(url = "https://api.nal.usda.gov/fdc/v1/search", 
           authenticate(user = "<MyAPIKey>", password = "", type = "basic"),
           query = list(generalSearchInput = "Cheddar cheese",
           encode = "json")

)

回复如下:

Response [https://api.nal.usda.gov/fdc/v1/search]
  Date: 2019-10-10 20:34
  Status: 403
  Content-Type: application/json
  Size: 141 B
{
  "error": {
    "code": "API_KEY_INVALID",
    "message": "An invalid api_key was supplied. Get one at https://api.nal.usda.gov:443"
  }

这也许不足为奇。我遇到了几个问题:

如何正确地将我的 API 密钥传递给调用?我尝试使用基本 HTTP 身份验证 as described on the api.data.gov website documentation(即,作为用户名和空密码的密钥)这样做,但我认为我这样做不正确。

【问题讨论】:

  • 感谢@Kenna,我更新了我的 API 调用。现在看来,主机正在接收并识别请求,尽管它仍然无法识别我传递 API 密钥的方式。我已经输入了一条更新的错误消息来展示新的结果。

标签: api httr


【解决方案1】:

根据documentation,您可以通过这种方式在POST请求的正文中包含JSON数据:

httr::POST(
    url = "https://api.nal.usda.gov/fdc/v1/search", 
    authenticate(user = "<MyAPIKey>", password = "", type = "basic"),
    body = list(generalSearchInput = "Cheddar cheese"),
    encode = "json"
)

【讨论】:

  • 谢谢;这回答了我关于将参数传递给主机的部分问题,但出于某种原因,他们仍然不喜欢我传递 API 密钥的方式......问题已更新以进行演示。再次感谢!
  • 我收回我之前的声明!显然我请求的 API 密钥不再有效(正如更新的错误消息所暗示的那样......!)感谢您的帮助!
  • 很高兴能帮上忙!
【解决方案2】:

不确定您是否仍在处理此问题,但我从 Github 上的某个人那里找到的这段代码可能会有所帮助。它一直在为我工作。您只需要填写 apiKey 和特定的 foodID。

导入请求 导入json import pandas as pd #如果您想将响应添加到数据框以使其更易于使用(此处未显示该代码)

apiKey = ''

foodID = ''

def nutrition_API(apiKey, foodID): #calls 获取 api 和 json 加载 api_resp = json.loads(requests.get('https://api.nal.usda.gov/fdc/v1/' + foodID + '?api_key=' + apiKey).text) #只返回营养信息 api_nutrients = api_resp['foodNutrients'] #first entry 是它的描述、foodID 和数据库条目类型 NutritionDict = {"FoodID": [api_resp['description'],foodID, api_resp['dataType']]}

for items in api_nutrients:
    if 'amount' in items:
        #each entry includes nutrient name, nutrient id, amount, and its respective unit
        nutrientDict.update({(items['nutrient']['name']): [(items['nutrient']['id']),
            (items['amount']),(items['nutrient']['unitName'])]})
    #print(nutrientDict)
return(nutrientDict)

【讨论】:

    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 2022-11-30
    • 1970-01-01
    • 1970-01-01
    • 2022-07-05
    • 2017-07-14
    • 2019-08-24
    • 2011-01-18
    相关资源
    最近更新 更多