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

如何修改HTMLSession爬虫代码解决NoneType错误,获取MD-BL-13站点数据

问题解决:修复爬虫代码中的"NoneType object has no attribute html"错误

错误原因分析

你遇到的错误是因为table = r.html.find('table.Grid', first=True)返回了None,说明POST请求后没有找到目标表格。主要问题有几个:

  • 会话范围错误:原代码中with HTMLSession() as s:的缩进不正确,POST请求不在会话块内,导致会话失效,请求无法正确携带必要的会话信息
  • 隐藏参数缺失/参数名错误:ASP.NET页面需要的__VIEWSTATE参数名被写成了_VIEWSTATE(少一个下划线),而且还缺少__VIEWSTATEGENERATOR、__EVENTVALIDATION这类必要的隐藏参数
  • 未验证请求是否成功:没有检查POST请求的响应状态,可能请求本身就失败了

修改后的代码

import requests
from requests_html import HTMLSession
import pandas as pd

# 把所有请求逻辑放到会话块内,保持会话持续
with HTMLSession() as s: 
    # 第一步:获取初始页面,提取所有必要的隐藏参数
    r = s.get('https://www.cocorahs.org/ViewData/StationPrecipSummary.aspx')
    r.raise_for_status()  # 检查请求是否成功

    # 提取ASP.NET所需的隐藏参数
    viewstate = r.html.find('input[name=__VIEWSTATE]', first=True).attrs.get('value')
    viewstate_generator = r.html.find('input[name=__VIEWSTATEGENERATOR]', first=True).attrs.get('value')
    event_validation = r.html.find('input[name=__EVENTVALIDATION]', first=True).attrs.get('value')

    # 构造请求参数,修正参数名并补充缺失的隐藏参数
    payload = {
        '__EVENTTARGET': '',
        '__VIEWSTATE': viewstate,
        '__VIEWSTATEGENERATOR': viewstate_generator,
        '__EVENTVALIDATION': event_validation,
        'obsSwitcher:ddlObsUnits': 'usunits',
        'tbStation1': 'MD-BL-13',
        'ucDateRangeFilter:dcStartDate': '8/1/2019',
        'ucDateRangeFilter_dcStartDate_p': '2019-8-1-0-0-0-0',
        'ucDateRangeFilter:dcEndDate': '8/10/2019',
        'ucDateRangeFilter_dcEndDate_p': '2019-8-10-0-0-0-0',
        'btnSubmit': 'Get Summary'
    }

    # 第二步:发送POST请求获取数据页面
    r = s.post('https://www.cocorahs.org/ViewData/StationPrecipSummary.aspx', data=payload)
    r.raise_for_status()

    # 查找目标表格,增加判断避免None错误
    table = r.html.find('table.Grid', first=True)
    if not table:
        print("未找到目标表格,请检查参数或页面结构是否变化")
    else:
        # 读取表格并提取需要的列
        df = pd.read_html(table.html, header=0)[0]
        # 提取Date和Precip In列
        result_df = df[['Date', 'Precip In']]
        print(result_df)

关键修改点说明

  • 缩进修正:将所有请求操作放到with HTMLSession() as s:块内,确保会话上下文持续有效
  • 参数修正:把_VIEWSTATE改为__VIEWSTATE,并补充了__VIEWSTATEGENERATOR和__EVENTVALIDATION参数,这些是ASP.NET表单提交必须的验证参数
  • 异常处理:增加r.raise_for_status()检查请求是否成功,避免在请求失败时继续执行后续代码;增加表格存在性判断,提前处理找不到表格的情况
  • 数据提取:最后提取出你需要的Date和Precip In两列,直接得到目标数据

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

相关产品推荐
方舟 Agent Plan

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

最近更新时间:2026.06.12 21:04:59