1. 项目概述当AI遇上爬虫是帮手还是“猪队友”去年底ChatGPT刚出来那会儿整个圈子都炸了。我当时就在想这玩意儿对我们这些天天跟网页结构斗智斗勇、写爬虫写到头秃的开发者来说到底意味着什么是能解放双手的“神器”还是又一个需要花时间去“调教”的新玩具五个月过去GPT-4都出来了各种基于大模型的应用层出不穷是时候亲自下场用最实际的项目来检验一下了AI到底能不能写网页爬虫我的结论先摆在这儿指望AI看一眼网站就能给你吐出一个完美、即插即用的爬虫目前还不太现实。它给的代码语法上可能没错但那些关键的、决定成败的CSS选择器或XPath路径往往都是些通用、笼统的玩意儿放到具体网站上基本没法用。除非你让它爬的是像维基百科、亚马逊这类结构极其标准、网上教程满天飞的知名站点它或许能“回忆”起一些现成的方案。但现实是我们面对的大多是结构独特、甚至有点“奇葩”的定制化网站。所以这次我选了一个相对小众的时尚电商网站——Gianvito Rossi的意大利站作为我们的“小白鼠”看看在明确的指引下ChatGPT能交出怎样的答卷。2. 核心思路如何与AI“有效沟通”来构建爬虫直接丢一句“给我写个爬这个网站的爬虫”给AI得到的多半是垃圾。关键在于你得像带一个聪明但缺乏经验的实习生一样把任务拆解清楚把已知的“坑”和“路标”都告诉它。2.1 明确框架与工具链我选择了Python的Scrapy框架。原因很简单Scrapy是爬虫领域的“重工业”标准生态成熟异步处理能力强适合结构化、大规模的数据抓取。告诉AI使用Scrapy就等于给它框定了一个成熟的开发范式它只需要在这个范式里填充逻辑而不是从零发明轮子。同时我指定使用XPath作为数据提取工具。XPath比CSS选择器在某些复杂嵌套场景下更强大、更精确对于需要精准定位的爬虫任务来说是更可靠的选择。2.2 设计清晰的爬取逻辑与数据流一个健壮的爬虫不是一蹴而就的它需要清晰的路线图。我为这个电商网站设计了一个三层递进的爬取策略入口层抓取分类从首页出发找到所有产品分类的链接。列表层遍历产品列表页进入每个分类抓取该分类下所有产品的详情页链接并处理可能存在的分页“加载更多”按钮。详情层解析产品数据进入每个产品详情页提取我们需要的具体字段。这个“分类 - 列表 - 详情”的漏斗模型是爬取电商、博客、论坛等具有层级结构网站的经典模式。提前规划好这个流程并在提示词中清晰地描述出来是引导AI写出正确逻辑的关键。2.3 利用结构化数据Schema.org降维打击这是本次实践中最取巧、也最体现经验的一点。很多现代网站尤其是电商为了SEO搜索引擎优化会在页面中嵌入遵循Schema.org标准的结构化数据JSON-LD格式。这简直就是给爬虫开发者开的后门与其费劲地去分析复杂的HTML DOM树用脆弱的XPath去定位一个可能随时变动的div不如直接去script type”application/ldjson”标签里找现成的、结构化的产品信息。在给ChatGPT的提示词中我明确指出了这一点“产品详情页包含一个我们所需大部分数据的JSON。可以通过查找第一个script type”application/ldjson”并提取其中的文本来获得。” 并且我还直接给出了字段映射关系product_code对应JSON里的mpn制造商零件编号price对应offers对象里的price字段。这就把最复杂的解析工作从“猜结构”变成了“读文档”。实操心得在动手写爬虫之前先用浏览器的开发者工具F12查看网页源代码搜索“ldjson”或“schema.org”是事半功倍的第一步。如果网站提供了这个你的爬虫稳定性和开发效率会提升一个数量级。3. 实操过程从提示词到可运行爬虫的完整记录下面就是我最终提交给ChatGPTGPT-4模型的完整提示词。请注意这不是我第一次尝试的结果而是经过几轮迭代、补充细节后形成的“终极版本”。好的提示词本身就是一份精简的需求文档。创建一個使用Scrapy框架和XPath选择器的Python網頁爬蟲。 start_urls參數應包含要爬取的URL[https://www.gianvitorossi.com/it_it](https://www.gianvitorossi.com/it_it)。 爬取第一頁後爬蟲應進入一個名為get_categories的函數。 在此函數中爬蟲使用以下XPath選擇器提取所有指向不同產品類型的相對鏈接product_pages response.xpath(//a[rolemenuitem]/href).extract() 對於每個產品頁面它應該進入一個名為get_product_list的函數。 使用XPath選擇器提取頁面上的產品列表(’//a[contains(class, “b-product_tile-image_link”)]/href)。 如果有更多產品要顯示則使用XPath (‘//a[data-event-click.prevent”loadMore”]/href).extract()[0]爬行到下一個產品頁面該選擇器包含指向下一頁的絕對路徑並將此選擇器包含在try/except子句中。 如果選擇器沒有匹配項則應在except子句中使用pass指令。 對於提取的每個產品進入一個名為get_product_details的函數。 編寫邏輯以爬取以下字段 - 產品代碼 (product_code) - 原價 (full_price) - 售價 (price) - 產品鏈接 (product_url) 產品詳細信息頁面包含一個JSON其中包含我們需要的大部分數據。可以通過查找第一個script type”application/ldjson”並從那裡提取文本來找到它。 它遵循標準的Product Schema.org類型您可以將字段product_code映射到Json的mpn字段。 可以通過進入JSON中的offers字典並選擇price字段來映射price字段。 而product_url字段可以改用response.url值進行映射。 由於該網站沒有折扣full_price字段可以映射為price字段。3.1 AI生成的代码与逐行解析ChatGPT根据以上提示生成了如下代码。我们来逐部分拆解看看它理解得怎么样import scrapy import json class GianvitoRossiSpider(scrapy.Spider): name gianvitorossi start_urls [https://www.gianvitorossi.com/it_it] def parse(self, response): # 提取产品分类 product_pages response.xpath(//a[rolemenuitem]/href).extract() for product_page in product_pages: yield scrapy.Request(response.urljoin(product_page), callbackself.get_product_list)解析这里有个小问题但无伤大雅。按照我的设计parse方法应该调用get_categories函数。但AI直接在这里实现了分类提取的逻辑。这其实更简洁因为Scrapy的入口方法就是parse。它正确使用了我们提供的XPath来获取分类链接并用response.urljoin()将相对URL拼接成绝对URL然后生成新的请求回调函数设为get_product_list。逻辑完全正确。def get_product_list(self, response): # 提取产品链接 product_links response.xpath(//a[contains(class, b-product_tile-image_link)]/href) for link in product_links: yield scrapy.Request(response.urljoin(link.extract()), callbackself.get_product_details) # 检查是否有更多产品页 try: next_page response.xpath(//a[data-event-click.preventloadMore]/href).extract()[0] yield scrapy.Request(response.urljoin(next_page), callbackself.get_product_list) except: pass解析这部分实现得相当漂亮。它先抓取当前列表页的所有产品详情链接并为每个链接创建请求。关键点在于分页处理它用一个try/except块包裹了“下一页”链接的提取。如果找到loadMore按钮的链接就继续请求下一页并回调自身get_product_list实现递归翻页。如果没找到即extract()[0]引发IndexError则except块中的pass会让程序安静地跳过结束当前分类的爬取。这种处理方式非常稳健兼容有分页和无分页两种情况。def get_product_details(self, response): # 提取JSON数据 json_data response.xpath(//script[typeapplication/ldjson]/text()).extract_first() data json.loads(json_data) # 提取产品详情 product_code data[mpn] full_price data[offers][price] price full_price product_url response.url # 返回Item yield { product_code: product_code, full_price: full_price, price: price, product_url: product_url }解析这是核心的数据解析部分。AI完全遵循了我的指示使用XPath定位JSON-LD脚本标签提取文本然后用json.loads()解析。字段映射也完全正确。这里体现了利用结构化数据的巨大优势代码极其简洁清晰没有复杂的HTML解析逻辑。response.url直接作为产品URL也是标准做法。运行结果我将这段代码复制到Scrapy项目中运行爬虫顺利启动成功遍历了分类、列表页并抓取了所有产品详情页的指定字段数据。从功能上讲AI交出了一份满分答卷。3.2 效率反思AI真的节省时间了吗这是最有趣的问题。对我这样一个有经验的Python开发者来说这次并没有节省时间。为什么因为最耗时、最需要经验的部分——分析网站结构、找到正确的XPath选择器、发现并利用JSON-LD数据源——这些工作仍然需要我手动完成。我只是把“用键盘敲出代码”这个步骤换成了“用键盘敲出详细的提示词”。两者花费的脑力和时间几乎是对等的。甚至为了写出能让AI准确理解的提示词你需要更结构化、更无歧义地描述你的意图这本身也是一种劳动。所以在这个场景下AI更像是一个严格按需求书写的代码生成器而不是一个能自主解决问题的工程师。4. AI的闪光点调试与跨语言移植虽然初级开发没省时间但AI在另外两个场景下展现了巨大价值。4.1 秒级Bug定位与修复我手动在之前的代码里制造了两个典型的Bug在XPath字符串中删掉了一个引号造成语法错误xpath(//script[typeapplication/ldjson]/text())缺少闭合引号。在返回的字典中误写了一个未定义的变量名product_code: product_code3。我把这段错误的代码丢给ChatGPT问它有什么问题。它不仅立刻给出了修正后的正确代码还附上了清晰的解释“原始代码中的错误是用于提取JSON数据的XPath选择器存在语法错误。闭合引号放错了位置导致选择器无效。修正后的代码将闭合引号放在了正确的位置……此外yield语句中的字段名称存在拼写错误已在修正后的代码中修复。”这简直是“神器”对于这类琐碎的、因手误或拼写导致的语法错误和运行时错误NameError人类开发者往往需要依赖IDE提示或仔细的肉眼排查而AI可以瞬间定位并解释。它尤其适合解决那些“明明刚才还好好的怎么就报错了”的瞬间懵圈时刻能极大缩短调试时间。4.2 零基础跨语言开发这才是本次实验最惊艳的部分。我几乎不懂Node.js但我把几乎相同的提示词只把“Scrapy”换成“Node.js” “XPath”换成“Cheerio”这是Node.js的HTML解析库扔给了ChatGPT。它生成了一段完全可用的Node.js代码使用了axios进行HTTP请求cheerio进行jQuery风格的DOM操作。代码结构清晰采用了async/await语法处理异步完美复现了Python版本的三层爬取逻辑、分页处理和JSON-LD数据提取。const axios require(axios); const cheerio require(cheerio); // ... 其余代码见上文我安装了依赖npm install axios cheerio后直接运行爬虫成功工作。这意味着借助AI一个开发者可以快速地将自己在一个领域的知识爬虫逻辑、网站结构分析迁移到另一个不熟悉的语言生态中。它极大地降低了学习新语言并立即产出可用工具的初始门槛。你不需要先花几周时间学习Node.js的所有语法和生态你只需要知道你想要什么并用清晰的语言告诉AI。5. 常见问题、局限性与实战避坑指南基于这次实践和更多后续测试我总结了与AI协作编写爬虫时的关键注意事项。5.1 AI生成爬虫的典型局限局限点具体表现原因与对策选择器过于通用AI常生成像//div[class”content”]或//a这类选择器无法精确定位。AI缺乏对具体网页的视觉和交互理解。必须由人工分析页面后将精确的XPath或CSS选择器写入提示词。无法处理动态内容对于依赖JavaScript渲染数据的页面如单页应用SPAAI给出的基础请求无法获取有效内容。它通常只生成基于静态HTML的爬虫。需要提示它使用Selenium、Playwright或Scrapy-Splash等工具并描述等待元素出现的逻辑。逻辑健壮性不足可能缺少异常处理如网络超时、元素缺失、重试机制、反爬虫应对User-Agent轮换、代理IP、请求间隔。AI倾向于生成实现核心功能的“理想流程”代码。必须明确要求添加错误处理、延迟设置等生产级代码。无法理解反爬机制对验证码、登录态、复杂签名等反爬措施束手无策。这超出了当前通用AI的能力范围。需要开发者自己研究反爬策略并将破解步骤如模拟登录、计算签名分解后喂给AI。5.2 提升AI协作效率的提示词技巧扮演角色在提示词开头指定角色如“你是一个经验丰富的Python爬虫工程师”这能引导AI以更专业的口吻和逻辑思考。分步指示不要一次性要求所有功能。可以“第一步请写出爬取列表页链接的代码第二步请增加分页处理第三步请添加异常处理”。提供范例如果你有一个类似的爬虫代码可以提供片段作为参考告诉AI“请参考以下代码的结构和风格为XX网站编写爬虫”。明确约束除了功能还要说明环境Python 3.8、库的版本、代码风格PEP 8、是否需要保存到文件如JSON、CSV或数据库。持续迭代AI第一次生成的代码很少是完美的。把运行错误信息、不符合预期的输出结果直接反馈给它让它修正。这是一个“对话式调试”的过程。5.3 我的核心工作流建议经过多次实践我目前与AI协作开发爬虫的流程已经固定下来人工侦察手动打开目标网站使用开发者工具分析网络结构确定数据加载方式静态HTML / AJAX / WebSocket。数据位置优先寻找script type”application/ldjson”其次是隐藏在HTML中的>