Scrapy实战:5sing原创音乐网多页数据爬取(完整可运行,附避坑指南)

Scrapy实战:5sing原创音乐网多页数据爬取(完整可运行,附避坑指南)

今天给大家带来一个高频实战案例------使用Scrapy框架爬取5sing原创音乐网的多页歌曲数据。作为爬虫领域的经典场景,「列表页多页爬取+详情页深度解析」是企业开发中最常遇到的需求,也是新手从入门到进阶的必经之路。

本次实战全程干货,不仅提供可直接复制运行的完整代码,还会拆解爬取逻辑、分析反爬应对方案、分享实际开发中的踩坑经验,无论是有Scrapy基础的小伙伴,还是想进阶提升的爬虫爱好者,都能有所收获。话不多说,直接进入正题。

一、实战背景与需求分析

5sing是酷狗旗下的中国原创音乐基地,汇聚了大量原创音乐人及作品,其原创音乐列表页包含歌曲名称、上传时间、人气等基础信息,而歌手、作词、作曲、曲风等详细信息则需要进入详情页获取。本次实战的核心需求的如下:

  • 爬取目标:5sing原创音乐列表页(https://5sing.kugou.com/yc/list?t=1\&l=\&s=\&p=1)及前7页数据

  • 爬取字段:歌曲名称、上传时间、人气、歌手、作词、作曲、曲风(7个核心字段,覆盖歌曲核心信息)

  • 核心逻辑:列表页提取基础信息+详情页链接 → 详情页解析完整信息 → 自动多页翻页 → 数据整合输出

  • 反爬应对:配置请求头、携带Cookie,避免被网站拦截,确保爬取稳定性

补充说明:5sing作为正规音乐平台,爬取数据仅用于个人学习、技术交流,严禁用于商业用途,爬取频率不宜过高,尊重平台规则和原创作者权益。

二、项目环境准备

工欲善其事,必先利其器。在开始编写代码前,我们需要完成环境配置和项目搭建,步骤简单易懂,新手也能快速上手。

2.1 环境配置

本次实战基于Python 3.8+,核心依赖Scrapy框架,若未安装Scrapy,直接执行以下命令即可完成安装:

bash 复制代码
pip install scrapy
# 验证安装是否成功
scrapy version

若安装过程中出现依赖冲突,建议使用虚拟环境隔离,避免影响本地其他项目环境。

2.2 项目搭建

打开终端(Windows用CMD或PowerShell,Mac/Linux用终端),执行以下命令,一步步创建Scrapy项目:

bash 复制代码
# 1. 创建Scrapy项目(项目名:music51,可自定义)
scrapy startproject music51

# 2. 进入项目目录
cd music51

# 3. 创建爬虫文件(爬虫名:sing51,爬取域名:5sing.kugou.com)
scrapy genspider sing51 5sing.kugou.com

执行完成后,项目结构如下(重点关注标记文件):

plain 复制代码
music51/
├── music51/          # 项目核心目录
│   ├── __init__.py
│   ├── items.py      # 数据字段定义(重点)
│   ├── middlewares.py
│   ├── pipelines.py  # 数据处理(可选)
│   ├── settings.py   # 项目配置(重点)
│   └── spiders/      # 爬虫文件目录
│       ├── __init__.py
│       └── sing51.py # 核心爬虫代码(重点)
└── scrapy.cfg        # 项目配置文件

三、核心代码编写(完整可运行)

项目搭建完成后,我们依次编写items.py(定义数据字段)、sing51.py(核心爬虫逻辑),代码均已测试通过,可直接复制替换,无需修改额外配置。

3.1 定义数据字段(items.py

items.py用于定义我们需要爬取的字段,相当于一个"数据容器",明确字段名称和类型,方便后续数据存储和处理。修改items.py如下:

python 复制代码
import scrapy

class Music51Item(scrapy.Item):
    # 歌曲名称
    name = scrapy.Field()
    # 歌手
    singer = scrapy.Field()
    # 上传时间
    time = scrapy.Field()
    # 人气
    rq = scrapy.Field()
    # 作词
    zuoci = scrapy.Field()
    # 作曲
    zuoqu = scrapy.Field()
    # 曲风
    qufeng = scrapy.Field()

# 说明:Field()可指定类型(如type=str),此处简化配置,满足基础爬取需求

3.2 核心爬虫逻辑(sing51.py

sing51.py是本次实战的核心文件,包含列表页解析、详情页请求、多页翻页、数据整合等逻辑。以下是完整代码,每一行都添加了详细注释,方便理解:

python 复制代码
from music51.items import Music51Item
import scrapy

class Sing51Spider(scrapy.Spider):
    # 爬虫名称(必须唯一,执行爬虫时需要用到)
    name = "sing51"
    # 允许爬取的域名(防止爬取到其他无关网站)
    allowed_domains = ["5sing.kugou.com"]
    # 起始爬取URL(第一页列表页)
    start_urls = ['https://5sing.kugou.com/yc/list?t=1&l=&s=&p=1']
    # 可选:爬取1-50页(注释掉的代码,需要时可解锁)
    # start_urls = [f"https://5sing.kugou.com/yc/list?t=1&l=&s=&p={i}" for i in range(1,51)]

    # 配置请求头和Cookie(反爬核心,避免被网站拦截)
    custom_settings = {
        "DEFAULT_REQUEST_HEADERS": {
            'accept': 'text/html,application/xhtml+xml,application/xml;q=0.9,image/avif,image/webp,image/apng,*/*;q=0.8,application/signed-exchange;v=b3;q=0.7',
            'accept-language': 'zh-CN,zh;q=0.9',
            'upgrade-insecure-requests': '1',
            # User-Agent:模拟浏览器请求,避免被识别为爬虫
            'user-agent': 'Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/142.0.0.0 Safari/537.36',
            # Cookie:携带浏览器Cookie,模拟登录状态,提升爬取稳定性
            'cookie': 'kg_mid=eaa1ae32c74a32d8cfe0529ae9e09aff; kg_dfid=1bq3jP1k0ric0hvjTb0xJFJn; wsp_volume=0.8; sl-session=Q4CYAEJrGGnq5/t9G0NxZQ==; ACK_SERVER_10015=%7B%22list%22%3A%5B%5B%22bjlogin-user.kugou.com%22%5D%5D%7D; kg_dfid_collect=d41d8cd98f00b204e9800998ecf8427e; kg_mid_temp=eaa1ae32c74a32d8cfe0529ae9e09aff; ACK_SERVER_10016=%7B%22list%22%3A%5B%5B%22bjreg-user.kugou.com%22%5D%5D%7D; ACK_SERVER_10017=%7B%22list%22%3A%5B%5B%22bjverifycode.service.kugou.com%22%5D%5D%7D; cct=f4b14310',
        }
    }

    # 解析列表页(核心方法1):提取基础信息和详情页链接
    def parse(self, response):
        # Scrapy自带xpath解析,无需额外导入lxml,直接使用response.xpath()
        # 定位列表页中的歌曲列表(通过F12开发者工具查看页面结构获取xpath)
        dls = response.xpath('//div[@class="lists"]/dl')
        
        # 遍历每首歌曲的容器,提取基础信息
        for dl in dls:
            # 歌曲名称(xpath定位到标题标签,get()获取文本内容)
            name = dl.xpath('./dd[@class="l_info"]/h3/a/text()').get()
            # 上传时间
            time = dl.xpath('./dd[@class="l_time"]/text()').get()
            # 人气(rq对应页面中的"人气"字段)
            rq = dl.xpath('./dd[@class="l_rq"]/text()').get()

            # 详情页链接(获取a标签的href属性,拼接完整URL)
            href = dl.xpath('./dd[@class="l_info"]/h3/a/@href').get()
            # 拼接完整URL(页面中href是相对路径,需加上域名)
            href = "https://5sing.kugou.com" + href

            # 发起详情页请求,将列表页提取的基础信息通过meta传递给详情页解析方法
            yield scrapy.Request(
                url=href,                  # 详情页URL
                callback=self.parse_detail, # 详情页解析方法
                meta={'name': name,'time': time,'rq': rq} # 传递数据(列表页→详情页)
            )

        # 多页翻页逻辑:爬取第2-7页(可根据需求修改范围)
        for i in range(2,8):
            # 拼接第i页的URL,发起请求,回调自身(继续解析列表页)
            yield scrapy.Request(
                url=f"https://5sing.kugou.com/yc/list?t=1&l=&s=&p={i}",
                callback=self.parse
            )

    # 解析详情页(核心方法2):提取歌手、作词、作曲、曲风等详细信息
    def parse_detail(self, response):
        # 接收列表页传递过来的数据(meta参数)
        meta = response.meta
        
        # 解析详情页字段(通过F12查看详情页结构,定位对应标签)
        # 歌手(定位到歌手标签,get()获取文本,若为空则返回空字符串)
        singer = response.xpath('//ul[@class="lt mb15"]/li[1]/a/text()').get() or ""
        # 作词
        zuoci = response.xpath('//ul[@class="lt mb15"]/li[2]/a/text()').get() or ""
        # 作曲
        zuoqu = response.xpath('//ul[@class="lt mb15"]/li[3]/a/text()').get() or ""
        # 曲风(第8个li标签是曲风,get()获取后去除多余空格)
        qufeng = response.xpath('//ul[@class="lt mb15"]/li[8]/text()').get() or ""
        qufeng = qufeng.strip() if qufeng else ""

        # 数据整合:将列表页和详情页的信息存入Music51Item容器
        item = Music51Item({
            'name': meta['name'],       # 列表页传递的歌曲名称
            'singer': singer,           # 详情页解析的歌手
            'time': meta['time'],       # 列表页传递的上传时间
            'rq': meta['rq'],           # 列表页传递的人气
            'zuoci': zuoci,             # 详情页解析的作词
            'zuoqu': zuoqu,             # 详情页解析的作曲
            'qufeng': qufeng            # 详情页解析的曲风
        })
        
        # 输出数据(Scrapy会自动处理,可后续配置 pipelines 存储到文件/数据库)
        yield item

3.3 项目配置优化(settings.py

默认的settings.py无需大量修改,只需调整3个关键配置,提升爬取稳定性和效率,避免被反爬:

python 复制代码
# 1. 禁止遵循robots协议(部分网站robots协议限制爬虫,可关闭)
ROBOTSTXT_OBEY = False

# 2. 设置下载延迟(单位:秒),避免请求频率过高被拦截(建议0.5-1秒)
DOWNLOAD_DELAY = 0.8

# 3. 开启日志(可选,方便调试,爬取成功后可关闭)
LOG_LEVEL = 'INFO'

# 其他配置保持默认即可,无需修改

四、爬虫运行与结果查看

代码编写完成后,我们就可以运行爬虫,查看爬取结果了。步骤如下:

4.1 运行爬虫

在终端中,进入music51项目目录,执行以下命令运行爬虫:

bash 复制代码
scrapy crawl sing51 -o music_data.csv

命令说明:

  • scrapy crawl sing51:运行名称为"sing51"的爬虫

  • -o music_data.csv:将爬取到的数据保存为CSV文件(方便用Excel查看,也可改为.json、.xml格式)

4.2 结果查看

运行完成后,项目目录下会生成music_data.csv文件,打开后即可看到爬取的所有数据,示例如下(部分数据):

name(歌曲名称) singer(歌手) time(上传时间) rq(人气) zuoci(作词) zuoqu(作曲) qufeng(曲风)
聘猫记 心然 2025-09-07 627617 未知 未知 古风
秋风词 于文华 2025-09-08 418852 未知 未知 古风
注:部分歌曲的作词、作曲信息可能为空,这是因为页面中未显示该信息,属于正常情况,可在代码中添加判断,将空值替换为"未知",提升数据完整性。

五、实战踩坑经验与优化建议

在实际开发中,我遇到了几个常见问题,这里分享给大家,帮助大家避坑,提升爬虫的稳定性和效率。

5.1 常见踩坑点及解决方案

  • 坑点1:请求被拦截,爬取失败(报403 Forbidden错误)

解决方案:配置请求头(User-Agent)和Cookie,模拟浏览器登录状态,避免被网站识别为爬虫。本文代码中已配置好Cookie和User-Agent,可直接使用,若后续失效,可自行在浏览器中复制(F12→Network→刷新页面→找到任意请求→Headers→Cookie和User-Agent)。

  • 坑点2:xpath定位失败,提取不到数据

解决方案:通过F12开发者工具精准定位标签,避免xpath路径错误。重点注意:页面标签可能存在动态加载(本次案例无动态加载,直接xpath定位即可),若遇到动态加载,可使用Selenium或Scrapy-Splash辅助爬取。

  • 坑点3:多页翻页逻辑出错,只爬取第一页

解决方案:检查翻页URL的规律(本次翻页仅改变p参数,如p=1、p=2),确保循环范围正确,回调函数指定为parse(自身),避免回调错误。

  • 坑点4:数据为空,出现None值

解决方案:在提取数据时添加判断(or ""),将None值替换为空字符串,避免后续数据处理报错。如本文代码中:singer = response.xpath(...).get() or ""。

5.2 优化建议(进阶提升)

如果想进一步提升爬虫的性能和实用性,可以参考以下优化方向:

  1. 数据存储优化:将CSV文件改为存储到MySQL、MongoDB等数据库,使用Scrapy的pipelines.py实现数据持久化,适合大量数据爬取。

  2. 反爬升级:添加IP代理池,避免单一IP被封禁;随机修改User-Agent,模拟不同浏览器请求;增加随机延迟,避免请求频率固定。

  3. 异常处理:添加try-except异常捕获,处理页面加载失败、xpath定位失败等异常,确保爬虫不会中途中断。

  4. 爬取范围扩展:解锁start_urls中的注释代码,实现1-50页自动爬取;添加曲风筛选功能,爬取指定曲风(如古风、流行)的歌曲。

六、总结与拓展

本次实战通过Scrapy框架,成功实现了5sing原创音乐网的多页数据爬取,核心掌握了「列表页+详情页」的联动爬取逻辑、请求头与Cookie的反爬配置、多页翻页实现等关键技能。整个案例难度适中,贴近实际开发场景,适合作为Scrapy进阶练习的案例。

从技术层面来说,Scrapy的优势在于其高效的异步请求、灵活的解析方式和完善的生态,相比requests+BeautifulSoup,Scrapy更适合多页、大量数据的爬取,能够极大提升开发效率。本次案例的代码可直接复用,只需替换Cookie和User-Agent,即可适配其他类似的列表页+详情页爬取场景(如小说网、新闻网)。

最后提醒大家,爬虫开发需坚守合法合规的原则,尊重网站的robots协议和数据版权,不恶意爬取、不滥用爬取的数据。如果大家在实践过程中遇到问题,欢迎在评论区留言,我会及时回复解答。

后续我还会分享更多Scrapy实战案例(如动态页面爬取、分布式爬虫),关注我,了解更多爬虫技巧和实战案例经验!

相关推荐
老白干2 小时前
jjwt 0.9.1 在 JDK 11+ 上的两个“坑”与完整解决方案
java·python·log4j
笨鸟先飞,勤能补拙8 小时前
AI 赋能网络安全:技术全景、成熟度评估与实战案例
人工智能·python·安全·web安全·网络安全·sqlite·github
长和信泰光伏储能9 小时前
京津冀光伏发电:绿色能源的未来之路
python·能源
浦信仿真大讲堂9 小时前
从重复操作到自动化闭环:如何让 CST 与 Python 真正协同起来
python·自动化·cst·仿真软件·达索软件
Gu Gu Study10 小时前
ScoutLoop开放域深度研究引擎(agent的初步设计想法)
人工智能·python
卷无止境11 小时前
写代码这件事,到底该讲究点什么?
后端·python
卷无止境11 小时前
循环复杂度到底在算什么,Python 代码怎么才能写得让人一看就懂
后端·python
lpfasd12311 小时前
MediaCrawler 项目深度分析
chrome·python·chrome devtools
Dxy123931021611 小时前
Python项目打包成EXE完整教程(PyInstaller实战避坑)
开发语言·python
bamb0012 小时前
一个项目带你入门AI应用开发01
python