☰
速卖通商品数据爬取全攻略:Python选品调研自动化
2026/10/9 2:22:40 网站建设 项目流程

简介:面向跨境电商数据分析与爬虫学习场景,这份源码包提供了一套速卖通数据采集的完整实现。工具通过自动化浏览器登录获取登录凭证,支持多线程爬取、自定义关键词与页面数,并在图形界面中展示结果及导出表格文件,能有效解决手动收集商品数据效率低、难以批量处理的问题。压缩包共六个文件,三个核心脚本分别承担控制逻辑、登录与爬取执行、图形界面交互,另含依赖清单及忽略规则等配置文件,整体仅11KB,结构轻量便于阅读和二次改造。目前已有104人学习,适合想入门爬虫与界面结合开发的中初级开发者,也适合有速卖通选品分析需求的运营人员参考。源码模块划分清晰,使用者可直接运行或扩展,从中学习登录凭证维护、多线程任务调度及数据导出的工程化写法。 这套工具是我在去年做跨境选品调研时,被逼出来的产物。当时需要大量分析速卖通上同行产品的销量趋势、价格带分布和评价关键词,每天手动复制粘贴到Excel里,效率低到怀疑人生,而且数据一多就乱。后来索性用Python写了一套自动抓取速卖通商品数据的脚本,从搜索结果页到商品详情,再到评价信息,基本覆盖了选品调研的核心数据需求。今天把这套工具的完整实现思路和关键源码拆出来,给同样在折腾跨境数据的朋友一条明路。

先说清楚这套东西能干什么:输入关键词,自动抓取速卖通搜索结果里的商品标题、价格、月销量、店铺名、链接,再点进详情页把评价数、评分、卖家信息拉下来,最终落成一份结构化的CSV表格。整个流程全自动,跑一次几百条数据,比手动效率高很多。代码我整理过,新手拿来改改关键词就能用,有一定基础的还能照着这个思路扩展成定时监控或竞品追踪。

1. 项目整体设计与技术选型

1.1 核心需求解析

动手写代码之前,先把需求拆明白。当时我给自己定的目标是:输入一个搜索关键词,程序自动完成“搜索结果采集 → 商品链接提取 → 详情页信息补全 → 数据落盘”这一整条链路,中间不需要人为干预。

拆解下来,核心需求就是下面这张表里列的:

需求模块说明优先级
搜索结果采集输入关键词,抓取搜索结果列表页中的商品卡片信息必须
详情页补全进入每个商品的详情页,补抓评价数、评分、卖家类型必须
数据落盘统一输出为CSV文件,字段要规整必须
断点续跑部分商品抓取失败时,记录日志,再次运行只补抓失败项建议
频率控制限制请求频率,避免对目标站点造成压力必须

这些需求看着简单,真正落地时才发现坑一个接一个。速卖通的页面是典型的前后端分离结构,网页HTML里只有初始骨架,真正的商品数据都是通过接口异步返回的。这就意味着传统的“requests拿HTML + BeautifulSoup解析DOM”策略直接失效,必须先定位接口。

1.2 技术选型

技术栈我选的是Python,理由很简单:生态全、上手快,爬虫这块的轮子基本都齐了。核心依赖就四样:

  • requests:发送HTTP请求,拿接口数据
  • json:解析接口返回的JSON结构(标准库,不需要装)
  • csv:数据落盘(标准库)
  • time/random:控制请求间隔,模拟人工操作节奏

没有用Scrapy,因为这套工具规模不大,用不着上分布式爬虫框架,requests一把梭反而更轻量。后续要扩展成多关键词批量跑,无非就是加层循环,框架化反而碍手碍脚。

这里补充一点关于Pycharm和VS Code的选择,如果你平时有本地Python开发环境,直接开干;如果没有,装个Anaconda然后配Pycharm社区版,十分钟就能跑起来。代码不要用Jupyter Notebook跑,长任务跑起来容易断,我吃过亏。

2. 速卖通数据爬取的关键技术点拆解

2.1 接口定位与分析

拿到速卖通搜索结果页,第一步不是急着写代码,而是先把页面和接口结构摸清楚。我用的方法是:打开浏览器无痕模式,进入速卖通搜索页,按F12打开开发者工具,切到Network面板,勾选Fetch/XHR过滤,然后手动搜索一个商品关键词,观察页面刷出了哪些异步请求。

实际观察下来,搜索结果页的数据核心是search?keywords=xxx这个接口。它返回的JSON结构里,有个data字段,里面是mods->itemList->content这样一个嵌套结构,每一组对象代表一个商品卡片,包含title、itemId、price、tradeDesc(销量描述)、sellerName、productDetailUrl这些关键信息。

这个接口有意思的一点是,它的参数里没有传统意义上的“页号”,而是通过page和pageSize控制。也就是说,你要翻页,直接改这两个参数就行,不用像有些平台那样还得找nextPageToken之类的游标参数,省了不少事。

再来是商品详情页。搜索结果列表里的信息到底还是太薄,像评价数、评分这种选品核心指标,得进详情页才有。详情页也是走接口,接口路径大致是/item/itemdetail这样的格式,后面跟一串商品ID。返回结构里,data下有个priceModule和titleModule,分别对应价格和标题信息,评价数据则在reviewModule里。

2.2 反爬机制与应对策略

说到速卖通的反爬,我真心觉得它的策略就是“大量速率限制+少量动态参数”。没有像某些国内电商平台那样玩非常复杂的滑块验证,它会优先控制你的请求频率和总量。刚开始测试时,我图省事,把请求间隔设成了0.5秒,结果跑了不到100个商品,就出现了频繁的响应体异常,直接被平台限流了。

应对策略上,我的经验是速度和伪装两手抓:

  • 请求间隔控制:相邻请求至少间隔2到3秒,这个值是个人经验,如果触发限流就在原基础上再翻倍。
  • Header伪装:设置完整的User-Agent、Referer、Accept-Language,越像真实浏览器越好。
  • Cookie策略:首次访问搜索结果页时,先请求一次首页拿基础Cookie,后续所有请求带上这个Cookie池。
  • 随机化:在2到3秒的基础上加入随机浮动,比如2.3秒到2.8秒之间随机取一个值,避免节奏太规律被机器识别。

这些策略合在一起,配合合理的抓取规模,基本能保证工具稳定运行几百条数据不翻车。

3. 核心代码实现与完整源码解析

3.1 项目结构

代码我做了模块化,看起来清爽,也好维护:

aliexpress_spider/ ├── config.py # 配置文件,存放Header、基础URL、请求间隔 ├── search_parser.py # 搜索结果解析模块 ├── detail_parser.py # 商品详情解析模块 ├── storage.py # 数据存储模块 └── main.py # 主流程入口

这里把配置单独拆出来,主要是一个习惯问题:Header、URL、间隔时间这些高频调整的东西集中放,改起来方便,也避免在主逻辑里翻来翻去找魔法数字。

3.2 配置模块实现

# config.py import random BASE_HEADERS = { 'User-Agent': 'Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/126.0.0.0 Safari/537.36', 'Accept': 'application/json, text/plain, */*', 'Accept-Language': 'en-US,en;q=0.9', 'Referer': 'https://www.aliexpress.com/', 'Origin': 'https://www.aliexpress.com', } SEARCH_URL = 'https://www.aliexpress.com/search' def get_headers(): headers = BASE_HEADERS.copy() return headers def get_delay(): return round(random.uniform(2.3, 2.8), 1)

BASE_HEADERS里这个User-Agent我是从自己浏览器复制的最新Chrome版本。有朋友可能会问,UA是不是越新越好?其实不是,关键是别用那种明显的爬虫默认UA,比如Python-requests/2.x这种,一眼就被识别了。

3.3 搜索结果解析模块

# search_parser.py import requests import json import config def search_products(keyword, page=1): params = { 'keywords': keyword, 'page': page, 'pageSize': 50, } resp = requests.get( config.SEARCH_URL, params=params, headers=config.get_headers(), timeout=10 ) if resp.status_code != 200: print(f"[搜索页] HTTP {resp.status_code}") return [] raw = resp.json() products = [] try: content = raw['data']['mods']['itemList']['content'] except KeyError: print("[搜索页] 数据结构异常,可能被限流或接口升级") return [] for item in content: product = { 'title': item.get('title', ''), 'item_id': item.get('itemId', ''), 'price': item.get('price', ''), 'trade_desc': item.get('tradeDesc', ''), 'seller_name': item.get('sellerName', ''), 'detail_url': item.get('productDetailUrl', ''), } products.append(product) return products

这里有个小细节,解析时我没有用item['title']而是用item.get('title', '')。原因很简单:搜索结果里偶尔会有广告位或其他类型的卡片,字段缺失的情况时有发生。用get方法取值,缺了就给个空字符串,程序不会崩。

3.4 商品详情解析模块

# detail_parser.py import requests import json import config DETAIL_URL = 'https://www.aliexpress.com/item/itemdetail' def fetch_detail(item_id): params = { 'itemId': item_id, } resp = requests.get( DETAIL_URL, params=params, headers=config.get_headers(), timeout=10 ) if resp.status_code != 200: print(f"[详情页] 商品{item_id} HTTP {resp.status_code}") return {} raw = resp.json() data = raw.get('data', {}) price_module = data.get('priceModule', {}) review_module = data.get('reviewModule', {}) title_module = data.get('titleModule', {}) return { 'item_id': item_id, 'detail_title': title_module.get('subject', ''), 'final_price': price_module.get('finalPrice', ''), 'review_count': review_module.get('totalNum', 0), 'rating': review_module.get('rating', 0), }

详情接口返回的数据结构里,评价数据在reviewModule下面,但有些商品没有评价模块,或者评价模块是空的,get方法在这里又发挥了兜底作用。totalNum是评价总数,rating是评分,这两个字段是选品时判断一个商品是否值得跟款的核心指标。

3.5 存储模块

# storage.py import csv def save_to_csv(rows, filename='aliexpress_data.csv'): if not rows: print("[存储] 无数据可保存") return fieldnames = [ 'title', 'item_id', 'price', 'trade_desc', 'seller_name', 'detail_url', 'final_price', 'review_count', 'rating', 'detail_title' ] with open(filename, 'w', newline='', encoding='utf-8-sig') as f: writer = csv.DictWriter(f, fieldnames=fieldnames) writer.writeheader() writer.writerows(rows) print(f"[存储] 已保存 {len(rows)} 条数据到 {filename}")

编码用了utf-8-sig而不是utf-8,这是个细节坑。后者生成的CSV用Excel直接打开,中文会乱码,而utf-8-sig加了BOM头,Excel能正确识别编码,这算是老爬虫的常识了。

3.6 主流程入口

# main.py import time import json import search_parser import detail_parser import storage import config def main(): keyword = input("请输入搜索关键词: ").strip() if not keyword: print("[主流程] 关键词不能为空") return total_results = [] # 第一步:抓取搜索结果,这里先跑前3页,可根据需要调整 for page in range(1, 4): print(f"[主流程] 正在抓取第 {page} 页搜索结果...") products = search_parser.search_products(keyword, page) if not products: print("[主流程] 本页无数据,提前结束") break total_results.extend(products) delay = config.get_delay() print(f"[主流程] 第 {page} 页抓取到 {len(products)} 个商品,等待 {delay} 秒") time.sleep(delay) print(f"[主流程] 共抓取 {len(total_results)} 个搜索结果,开始补全详情...") # 第二步:遍历每个商品补全详情 for idx, product in enumerate(total_results): item_id = product['item_id'] detail = detail_parser.fetch_detail(item_id) product.update(detail) delay = config.get_delay() print(f"[主流程] 进度 {idx + 1}/{len(total_results)},补全商品 {item_id},等待 {delay} 秒") time.sleep(delay) # 第三步:保存数据 storage.save_to_csv(total_results) print("[主流程] 全部完成") if __name__ == '__main__': main()

这套代码跑起来,输入一个关键词,大概几分钟后就能拿到一份完整的CSV数据表,包含商品标题、价格、销量描述、卖家名称、评价数、评分等信息。我实际用的时候,一次跑3页搜索结果,大概能拿到60到100个商品,每个商品补全详情,按2.5秒左右的间隔算,整个流程大约4到6分钟,属于可以接受的等待范围。

4. 常见问题与排查技巧实录

4.1 问题速查表

现象可能原因排查思路
搜索结果始终为空列表数据结构变更或触发限流打印原始raw的keys(),对比接口返回是否变化
接口返回HTTP 403被识别为爬虫检查User-Agent和Cookie,加大请求间隔
详情页补全大量为空商品ID无效或商品已下架检查itemId是否与搜索结果一致,部分商品确实无评价模块
CSV中文乱码编码用了utf-8改为utf-8-sig
程序运行中途卡死请求超时未设置给所有requests调用加上timeout=10

这里挑两个遇到最多的展开说说。

4.2 搜索结果空列表的深度排查

这是新手最容易卡住的问题,接口返回200但解析出来没有数据。问题大概率不是爬虫被封,而是页面布局变了,接口里的字段结构调整了。我的排查习惯是先缓存一次原始响应到本地文件,再仔细检查JSON结构。比如有一次我发现itemList不见了,变成了itemListNew,这时候只要把解析逻辑改成新的字段名就行,不算伤筋动骨。

另一个可能是老接口失效,平台迁移到了新接口。这个比较隐蔽,建议在浏览器里重新搜一次,看Network里实际走的哪个接口路径和参数,用新接口替换配置里的URL即可。

4.3 翻页时的页大小选择

pageSize我建议设成50,这是我在实际测试中验证过相对稳定的值。改成100试过,接口响应速度明显变慢,还容易触发限流;改成20虽然更稳,但翻页次数变多,总耗时反而更长。50是一个平衡点,单页数据量足够,请求频率又不会太激进。

关于页数上限,我默认就是3页。真要大批量抓数据,建议加个参数控制并分段跑,每次抓完歇几分钟再跑下个关键词,别一根筋连续跑通宵,大概率第二天醒来发现所有请求都失效了。

4.4 平台登录与Cookie处理

这套工具最初是按未登录状态设计的,因为搜索和详情接口在未登录时就能正常返回数据。但如果你需要抓的数据涉及更高的频率或更深的内容,就可能要处理登录态了。注意,登录功能会引入验证码、短信验证、账号风控等一系列问题,个人项目里最好不要动这个念头,用登录态加频繁请求,账号被限制的风险很大。

有个折中的办法是手动登录后在浏览器里复制完整Cookie字符串,放到config.py里作为请求头带上。这种方式对低频数据抓取够用,不用写自动登录代码,也不触发验证码机制。

5. 扩展思路与合规提醒

这套工具目前定位是“选品调研辅助工具”,但核心链路搭好之后,扩展空间其实挺大的。比如加上定时任务,每天早上自动跑一遍核心类目关键词,生成一份当天的价格与销量变化报告,就能从“查数据”升级成“盯数据”。再比如把CSV输出改成直接写入SQLite或MySQL,数据量大了之后查询和过滤会方便得多。

关于合规,这里必须多说两句。爬虫工具本身是中性的,但使用边界一定要注意:只抓公开数据,不绕过登录验证;控制请求频率,不干扰平台正常服务;数据仅用于个人调研分析,不批量复制他人原创内容用于商业发布。我自己的原则是,抓下来的数据人工二次加工后才使用,原始数据不转发、不售卖、不公开。

6. 关于这套工具的使用心得

工具写完之后,我实际用了一阵子,最直观的感受是,做跨境选品不再靠感觉了。以前看一个类目,感觉销量不错,但说不出具体数字,也没法横向比价。现在跑一次数据下来,哪个价格带竞争最激烈,哪个商品评价数断层领先,一目了然,节奏感完全不同。

最后再分享一个很实用的小技巧:如果搜索结果里有大量商品没有评价数据,这类商品往往是一些刚上架的新品或者没有太多销量的展示位。如果你在做选品,这类数据不用删除,它们本身就是一种信号。把这些“零评价商品”单独筛出来,看它们的价格和标题写作方式,往往能发现平台上正在发生的新趋势。这个功能用现成的CSV在Excel里加个筛选就能实现,不需要额外写代码。

代码是死的,思路是活的,这套工具的价值不在那几百行Python,而在于帮你把“看看别人卖什么”变成一项有系统、可复用的流程。希望这篇文章能帮你少走几步弯路,折腾出属于自己的数据工作流。

本文还有配套的精品资源,点击获取

需要专业的网站建设服务?

联系我们获取免费的网站建设咨询和方案报价,让我们帮助您实现业务目标

立即咨询