如何抓取Flipkart链接中第11、12、13页的不可见数据(现有代码仅支持前10页)
解决Flipkart三星手机列表后续页面抓取问题
嘿,我来帮你搞定这个后续页面抓不到的问题!你遇到的情况其实很常见,Flipkart对爬虫做了不少限制,而且前10页的分页逻辑和后面的页面有隐性区别。下面我给你拆解问题根源,再给出具体的解决方案。
为什么前10页能抓,后面不行?
核心原因有两个:
- 反爬拦截:你用的
urlopen请求头太简陋了,完全不像真实浏览器的请求,Flipkart很容易识别出来,次数多了就直接拒绝访问或者返回空页面。 - 会话与分页限制:前10页的
page=N参数是直接可访问的,但后续页面需要保持会话(Cookie),否则Flipkart后端会限制你的访问深度,导致页面加载失败。
具体解决方案
方案1:用Requests库优化请求(推荐,轻量高效)
换成requests库,加上完整的浏览器请求头,同时用Session保持Cookie,模拟真实用户的访问行为。
import requests from bs4 import BeautifulSoup import pandas as pd import time # 初始化会话,保持Cookie(关键!) session = requests.Session() # 模拟Chrome浏览器的请求头,别用默认的简陋头 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', 'Referer': 'https://www.flipkart.com/mobiles/samsung~brand/pr?count=40&p%5B%5D=sort%3Drecency_desc&page=1&sid=tyy%2F4io&viewType=list&wid=1.productCard.PMU_V2' } # 要抓取的总页数,比如设置20页 total_pages = 20 all_products = [] for page_num in range(1, total_pages + 1): # 构造分页URL,直接替换page参数就行 url = f"https://www.flipkart.com/mobiles/samsung~brand/pr?count=40&p%5B%5D=sort%3Drecency_desc&page={page_num}&sid=tyy%2F4io&viewType=list&wid=1.productCard.PMU_V2" try: # 发送请求,用会话保持Cookie response = session.get(url, headers=headers) response.raise_for_status() # 如果请求失败(比如403、500),直接抛出错误 # 解析页面 bsObj = BeautifulSoup(response.text, 'html.parser') # 抓取产品数据(这里的类名可能会变,要自己检查页面元素更新!) product_titles = bsObj.find_all(class_='_4rR01T') product_prices = bsObj.find_all(class_='_30jeq3 _1_WHN1') # 把数据存到列表里 for title, price in zip(product_titles, product_prices): all_products.append({ 'title': title.text.strip(), 'price': price.text.strip(), 'page_number': page_num }) print(f"第 {page_num} 页抓取成功,拿到 {len(product_titles)} 个产品") time.sleep(2) # 加个延迟,别太猛,防止被封IP except Exception as e: print(f"第 {page_num} 页抓取失败:{str(e)}") continue # 把数据存成CSV df = pd.DataFrame(all_products) df.to_csv('flipkart_samsung_phones.csv', index=False, encoding='utf-8') print("所有数据已保存到flipkart_samsung_phones.csv!")
方案2:用Selenium模拟浏览器(应对强反爬)
如果上面的方法还是被拦截,说明Flipkart用了JavaScript渲染验证,这时候就需要用Selenium模拟真实浏览器的行为,绕过反爬检测。
from selenium import webdriver from selenium.webdriver.common.by import By from selenium.webdriver.chrome.options import Options import pandas as pd import time # 配置Chrome浏览器选项 chrome_options = Options() chrome_options.add_argument('--headless=new') # 无头模式,不用弹出浏览器窗口 chrome_options.add_argument('--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') chrome_options.add_argument('--disable-blink-features=AutomationControlled') # 避免被检测为自动化工具 # 启动浏览器 driver = webdriver.Chrome(options=chrome_options) total_pages = 20 all_products = [] for page_num in range(1, total_pages + 1): url = f"https://www.flipkart.com/mobiles/samsung~brand/pr?count=40&p%5B%5D=sort%3Drecency_desc&page={page_num}&sid=tyy%2F4io&viewType=list&wid=1.productCard.PMU_V2" try: driver.get(url) time.sleep(3) # 等页面加载完全,尤其是动态内容 # 抓取产品数据 product_titles = driver.find_elements(By.CLASS_NAME, '_4rR01T') product_prices = driver.find_elements(By.CSS_SELECTOR, '._30jeq3._1_WHN1') for title, price in zip(product_titles, product_prices): all_products.append({ 'title': title.text.strip(), 'price': price.text.strip(), 'page_number': page_num }) print(f"第 {page_num} 页抓取成功,拿到 {len(product_titles)} 个产品") except Exception as e: print(f"第 {page_num} 页抓取失败:{str(e)}") continue # 关闭浏览器 driver.quit() # 保存数据 df = pd.DataFrame(all_products) df.to_csv('flipkart_samsung_phones_selenium.csv', index=False, encoding='utf-8') print("所有数据已保存到flipkart_samsung_phones_selenium.csv!")
重要提醒
- 类名可能变化:Flipkart经常更新页面元素的类名,如果发现抓不到数据,一定要打开浏览器的开发者工具,重新检查元素的类名或选择器。
- 控制请求频率:不管用哪种方法,都要加延迟(
time.sleep),建议1-3秒/页,不然很容易被封IP。 - IP代理(可选):如果需要长期大量抓取,建议用代理IP池,避免单一IP被限制。
内容的提问来源于stack exchange,提问作者satish kumar
相关产品推荐
相关产品推荐

