无法使用Python(requests+BeautifulSoup)抓取NSE印度网站债券表格数据的技术求助
解决NSE印度交易所债券数据爬取卡顿问题(无需Selenium)
嘿,我知道你现在卡在这了——用requests和BeautifulSoup爬NSE的债券表格,程序没报错但就是卡着不动,还不想用Selenium对吧?这大概率是NSE的反爬机制在搞鬼,加上你代码里的小问题导致的,我给你梳理下解决方案:
问题根源分析
- 反爬拦截:直接裸奔用
requests.get,NSE服务器一眼就能认出你是爬虫,要么延迟响应要么直接不返回内容,程序自然就卡着了。 - 冗余请求:你代码里连续两次调用
requests.get(url),完全没必要,反而可能加重服务器的怀疑。 - 表格定位模糊:直接用
pd.read_html(html)取第一个表格,万一页面里有其他无关表格,很容易取错数据。
修正后的完整代码
我给你写了一套能正常运行的代码,加了反爬规避,还精准定位到你要的两个表格:
import requests import pandas as pd from bs4 import BeautifulSoup as bs # 目标URL url = "https://www1.nseindia.com/products/content/debt/corp_bonds/cbm_reporting_homepage.htm" # 模拟浏览器的请求头,核心是User-Agent headers = { "User-Agent": "Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/118.0.0.0 Safari/537.36", "Accept-Language": "en-US,en;q=0.9" } try: # 只发起一次请求,加超时防止无限等待 response = requests.get(url, headers=headers, timeout=10) # 检查请求是否成功,失败直接抛出异常 response.raise_for_status() # 解析页面 soup = bs(response.text, 'lxml') # 精准定位两个目标表格:通过页面里的表格ID # 交易所交易债券对应的表格ID是tbldata1 exchange_bond_table = soup.find('table', id='tbldata1') # 场外交易(OTC)对应的表格ID是tbldata2 otc_bond_table = soup.find('table', id='tbldata2') # 把BeautifulSoup的表格对象转成字符串,再用pandas解析 df_exchange = pd.read_html(str(exchange_bond_table))[0] df_otc = pd.read_html(str(otc_bond_table))[0] # 保存到Excel,两个表格分开放在不同工作表 with pd.ExcelWriter('nse_bond_data.xlsx') as writer: df_exchange.to_excel(writer, sheet_name='交易所交易债券', index=False) df_otc.to_excel(writer, sheet_name='场外交易(OTC)', index=False) print("数据抓取并保存成功!") print("\n【交易所交易债券】表格预览:") print(df_exchange.head()) print("\n【场外交易(OTC)】表格预览:") print(df_otc.head()) except requests.exceptions.RequestException as e: print(f"请求过程出错啦:{e}") except Exception as e: print(f"处理数据时遇到问题:{e}")
关键优化点说明
- 请求头伪装:加上
User-Agent和Accept-Language,让请求看起来完全是来自真实浏览器,绕过NSE的基础反爬。 - 超时设置:
timeout=10确保如果服务器没响应,程序不会一直卡着,10秒后会抛出超时异常。 - 精准表格定位:通过页面源代码里的表格ID(
tbldata1和tbldata2)直接找到目标表格,避免取错其他无关数据。 - 异常处理:加上try-except块,能清晰看到哪里出了问题,不会再出现“卡着不动却不知道为啥”的情况。
后续注意事项
如果之后又出现问题,可以试试这些调整:
- 更换
User-Agent的值(比如换成Firefox的UA),避免被识别为固定爬虫。 - 偶尔加个小延迟(比如
time.sleep(2)),不要频繁请求服务器。 - 定期检查页面结构,如果表格ID变了,需要更新代码里的定位参数。
内容的提问来源于stack exchange,提问作者Tech Bro




