You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

调用New York Times API无返回结果的问题排查求助

问题排查与代码修正

核心代码错误

  • URL参数拼接错误:原代码中facet_fields=facet_fields}存在两处问题:多了一个多余的闭合大括号,且未将变量facet_fields的值传入,而是把字符串"facet_fields"作为参数值传递,导致API无法正确解析该参数。正确写法应为facet_fields={facet_fields}。
  • filter_query格式与编码问题:filter_query中的双引号未做处理,直接拼接进URL会破坏参数结构。手动拼接URL参数容易出现编码错误,建议使用urllib.parse.urlencode统一处理参数编码。
  • 全局变量依赖:page、sort等变量为全局定义,send_request函数直接依赖这些全局变量,后续扩展翻页或排序逻辑时会导致代码混乱。
  • 缺失错误处理:当API返回结构不符合预期(如response['response']不存在)或请求失败时,代码会直接抛出异常,没有容错机制。

修正后的代码

import requests
import pandas as pd
import time
from urllib.parse import urlencode

api_key = "my_NYT_api_key"
query = "Israel Palestine"
# 调整引号写法,避免后续编码问题
filter_query = 'news_desk:("Foreign" OR "Politics" OR "World") AND type_of_material:("News" OR "Article") AND pub_date:([2023-10-07 TO 2023-11-21])'
page = 0
sort = "relevance"
facet_fields = "news_desk,section_name"

def send_request(query, filter_query, facet_fields, api_key, page, sort):
    base_url = "https://api.nytimes.com/svc/search/v2/articlesearch.json"
    # 使用urlencode处理参数,避免手动拼接的编码错误
    params = {
        "q": query,
        "fq": filter_query,
        "facet_fields": facet_fields,
        "page": page,
        "sort": sort,
        "facet": "true",
        "facet_filter": "true",
        "api-key": api_key
    }
    url = f"{base_url}?{urlencode(params)}"
    
    headers = {
        'User-Agent': 'Mozilla/5.0 (Macintosh; Intel Mac OS X 10_15_7) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/119.0.0.0 Safari/537.36'
    }
    
    try:
        response = requests.get(url, headers=headers)
        response.raise_for_status()  # 捕获HTTP错误(如4xx/5xx)
        print("HTTP Status Code:", response.status_code)
        # 打印速率限制相关头信息,排查是否触发限制
        print("Remaining Requests:", response.headers.get('X-RateLimit-Remaining'))
        print("Rate Limit Reset Time:", response.headers.get('X-RateLimit-Reset'))
        print("Raw Response:", response.text)
        
        time.sleep(6)
        return response.json()
    except requests.exceptions.RequestException as e:
        print(f"Request Failed: {str(e)}")
        return None

def parse_response(response):
    data = {
        'headline': [],
        'pub_date': [],
        'web_url': [],
        'image_url': [],
        'timestamp': [],
    }
    
    # 检查响应结构是否合法
    if not response or 'response' not in response or 'docs' not in response['response']:
        print("Invalid Response Structure")
        return pd.DataFrame(data)
    
    articles = response['response']['docs']
    for article in articles:
        # 处理字段缺失的情况,避免KeyError
        data['headline'].append(article.get('headline', {}).get('main', 'No Headline'))
        data['pub_date'].append(article.get('pub_date', 'No Date'))
        data['web_url'].append(article.get('web_url', 'No URL'))
        data['timestamp'].append(article.get('pub_date', 'No Date'))
        
        multimedia = article.get('multimedia', [])
        # 补全图片完整URL,原API返回的是相对路径
        image_url = f"https://www.nytimes.com/{multimedia[0]['url']}" if multimedia else 'No Image'
        data['image_url'].append(image_url)
    
    return pd.DataFrame(data)

def get_data(query, filter_query, facet_fields, api_key, page, sort):
    response = send_request(query, filter_query, facet_fields, api_key, page, sort)
    df = parse_response(response)
    print(f"Collected Articles: {len(df)}")
    return df

# 调用示例
result_df = get_data(query, filter_query, facet_fields, api_key, page, sort)

额外排查要点

  • 确认速率限制状态:每次请求后查看X-RateLimit-Remaining和X-RateLimit-Reset响应头,NYT免费API通常限制每分钟5次请求、每天1000次请求,即使返回空结果,请求次数也会被计数。
  • 验证filter_query语法:在NYT API官方测试工具中测试你的filter_query,确认语法是否正确、是否能返回预期结果。
  • 处理翻页逻辑:NYT API的page参数最大支持到100(对应1000条结果),若需更多数据,可通过response['response']['meta']['hits']获取总结果数,循环请求不同页码。
  • 检查API密钥权限:在NYT开发者平台的"Apps"页面确认你的密钥是否拥有Articles Search API的访问权限。

内容的提问来源于stack exchange,提问作者Peizhi Zhang

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.07.05 18:20:57