V2EX = way to explore
V2EX 是一个关于分享和探索的地方
现在注册
已注册用户请  登录
• 请不要在回答技术问题时复制粘贴 AI 生成的内容
dfgddgf
V2EX  ›  程序员

请问最佳的爬虫语言是什么

  •  3
     
  •   dfgddgf · 2022-09-15 02:27:22 +08:00 · 11649 次点击
    这是一个创建于 826 天前的主题,其中的信息可能已经有所发展或是发生改变。

    如果需要多线程(多端口)下载网页,保证下载速度和网页解析速度和开发速度的在合理的范围之内,哪一款语言是最优的。

    golang 并发使用最强的,在正则匹配速度,爬虫软件包的丰富程度上和 perl 、python 还有不小差距。

    pyhon 的异步下载引擎貌似使用不是特别方便(个人对 pyhon 不熟,勿喷)

    php 有 https://github.com/walkor/Workerman 这样的高性能网页服务器框架,有没有易用的爬虫框架?

    node.js 异步下载貌似很强大,有没有大型爬虫项目使用 node.js 做爬虫,同时网页解析,文件处理,unicode 转码全部使用这个语言的爬虫案例?

    perl 有一个 mojo::useragent 配合 libEV ,并发能力很强大。perl 在文本正则处理、文本编码转换,网页 dom 解析都有成熟的处理方案和软件包,这个是目前作者最喜欢的平台。

    c# 据说是最强大爬虫平台,没接触多少。

    java 平台性能很强劲,软件包也丰富,笔者知之甚少。

    rust 貌似爬虫全套组件都有,而且比较新。貌似可以做出极致压榨硬件性能的方案。

    第 1 条附言  ·  2022-09-15 11:09:18 +08:00
    php 爬虫框架:

    https://github.com/ares333/php-curl
    The best php curl library. 利用 php-curl 内置 IO 事件循环实现,具备高性能、高通用性、高扩展性,尤其适合复杂业务逻辑大批量请求的应用场景。


    https://github.com/kiddyuchina/Beanbun 这个是基于 Workerman 的爬虫框架(@wxf666 27 楼提供)



    rust 爬虫框架:

    下面的资源是作者收集的,貌似 rust 可以做出把带宽和 CPU 压榨到机制。
    先进的内存释放模式,接近 c c++的速度,丰富的配套软件,不禁让人神往。



    https://rolisz.ro/2020/03/01/web-crawler-in-rust/



    https://github.com/tensor-programming/rust_web_crawler
    https://github.com/mattsse/voyager

    Multithreaded Web spider crawler written in Rust.


    https://github.com/madeindjs/spider


    Tokio 是一个事件驱动的非阻塞 I/O 平台,用于使用 Rust 编程语言编写异步应用程序。
    https://github.com/tokio-rs/tokio

    Rust 标准库的异步版本
    https://github.com/async-rs/async-std


    Rayon 是 Rust 的数据并行库。它非常轻巧,可以轻松地将顺序计算转换为并行计算。它还保证了数据竞争的自由。
    https://github.com/rayon-rs/rayon


    hyper: Rust 的快速且正确的 HTTP/1.1 和 HTTP/2 实现。
    https://github.com/hyperium/hyper


    如果您正在寻找方便的 HTTP 客户端,那么您不妨考虑 reqwest 。
    https://github.com/seanmonstar/reqwest
    如果您正在寻找方便的 HTTP 服务器,那么您不妨考虑 warp 。
    https://github.com/seanmonstar/warp




    rdbc:用于 MySQL 、Postgres 和 SQLite 的 Rust 数据库连接库。
    https://github.com/tokio-rs/rdbc


    bytes:用于处理字节的实用程序,包括高效的字节缓冲区。
    https://github.com/tokio-rs/bytes

    HTML 解析
    https://github.com/causal-agent/scraper
    https://github.com/servo/html5ever


    选择器
    一个从 HTML 文档中提取有用数据的库,适用于网络抓取。
    https://github.com/utkarshkukreti/select.rs



    字符编码
    https://github.com/hsivonen/encoding_rs
    https://github.com/lifthrasiir/rust-encoding


    json
    https://github.com/serde-rs/json
    https://github.com/maciejhirsz/json-rust
    第 3 条附言  ·  2022-09-15 21:03:24 +08:00
    一段 perl 代码展示如何 all in one 优雅地编写一个异步爬虫

    https://www.v2ex.com/t/880334
    67 条回复    2022-09-16 04:36:57 +08:00
    shuimugan
        1
    shuimugan  
       2022-09-15 04:30:43 +08:00   ❤️ 14
    不一定要 all in one ,任务调度、发送请求、解析内容、数据入库等可以用微服务的理念拆分开来,这样也方便扩展和重构,这玩意没有万金油的。
    从事件驱动的玩法上看,在异步里面做 cpu 复杂度高的计算都会降低时间循环的效率,所以解析复杂度高的东西都是拆分出去的,避免阻塞发送请求的代码。

    如果你观察过云服务商的 serverless ,你会发现它们那些通过队列事件触发的函数本质上也是一个 http 函数,因为可以和 api 网关 /k8s 结合,在更新版本时候可以把新流量导到新版本上,老版本等原有的 http 连接都关闭完就销毁。

    我目前在用 Node.js 写的爬虫也是这么设计的,目前是基于 NestJS 这个 web 框架做爬虫,结合 nsq 做任务调度,每个外发请求都是用 http 接口来触发,用 traefik 做网关和灰度切换,再结合 k8s 和部署和健康检查做滚动更新。

    目前用的到库:
    jsonata:用来解析复杂 json ,降低代码复杂度
    cheerio:服务端的 jquery ,在 python 有 BeautifulSoup ,在 java 有 jsoup ,也是类似的功能
    cld:语言检测,在 python 里有 langdetect

    不过也准备重构了,目前碰到的问题是任务堆积多了之后内存涨得快回落得慢,说白了就是 gc 回收不及时,打算先用 C# 把调度和发送请求的部分重构一下,再不行就换 rust ,解析和入库还是用回 nodejs 。
    dfgddgf
        2
    dfgddgf  
    OP
       2022-09-15 04:44:57 +08:00   ❤️ 1
    @shuimugan 这个思路新奇,复杂的问题拆解为更为简单的基础问题。

    这是 linux shell 编程的基本思路。

    您的观点可以得到验证。在异步的环境里做网页解析,确实占用率比较高。大概异步使用高精度的时间作为时间的区分标准,不停地查询 io 状态,这个比较耗费资源。

    按照这样的逻辑推断。应该把异步交给一个专门的组件(软件)来搞,而同步的工作、大量耗费 cpu 资源的用队伍列表的方式使用常规的软件来搞。

    学习了。这种专业的问题,只有资深专家,做过大型项目的前辈才能了解其中的诀窍。
    LeeReamond
        3
    LeeReamond  
       2022-09-15 04:51:47 +08:00
    爬虫没有什么特定一个阶段兴起快速抢占市场的问题,所以基本上市占率比较高的就是好用的。
    另外 python 异步挺简单的,确实只是你不了解而已
    laolaowang
        4
    laolaowang  
       2022-09-15 08:46:59 +08:00
    golang
    focuxin
        5
    focuxin  
       2022-09-15 08:52:17 +08:00
    Nodejs ,DOM 和 JavaScript 的优势
    ciming
        6
    ciming  
       2022-09-15 08:53:40 +08:00
    前几天好看到一个 nodejs 的爬虫框架
    https://crawlee.dev/
    bl4ckoooooH4t
        7
    bl4ckoooooH4t  
       2022-09-15 09:13:30 +08:00   ❤️ 1
    我这的做法是把要抓取的 url 放 redis ,Python 多线程从 redis 取任务爬取,结果通过 kafka 给下游解析。 可以分布式部署。目前 3 台机器,带宽在 50MB~100MB/s 左右,每日爬 200w url 左右。
    MEIerer
        8
    MEIerer  
       2022-09-15 09:14:32 +08:00
    Python 爬虫大概是最简单的
    xz410236056
        9
    xz410236056  
       2022-09-15 09:27:05 +08:00
    虽然我是喜欢 golang 的。但是 Python 的库是真他妈强,你数据搞下来不得处理吗,Python 数据处理的库功能是真强。

    “pyhon 的异步下载引擎貌似使用不是特别方便”
    Python 的逻辑是有需要你开多个进程,同进程内用协程,多线程属于骗自己。
    encro
        10
    encro  
       2022-09-15 09:28:52 +08:00
    encro
        11
    encro  
       2022-09-15 09:38:15 +08:00
    当然 Scrapy 也许仍然是最简单容易的分布式爬虫。

    一般的爬虫需要异步吗?
    答案是重点要考虑架构异步,而不是程序上的异步。
    就是说要考虑分布式任务调度 /并发防重爬 /广度有限 OR 深度优先这样的问题,而不是爬虫代码里面多写几个 await 。
    ragnaroks
        12
    ragnaroks  
       2022-09-15 09:38:45 +08:00
    任何可以调用 chromium 的语言都是最佳
    lmshl
        13
    lmshl  
       2022-09-15 09:41:28 +08:00
    不考虑生态的话我觉得是 NodeJS ,7-8 年前我就开始用它写爬虫了
    考虑生态的话应该是 Python
    tulongtou
        14
    tulongtou  
       2022-09-15 09:45:27 +08:00 via iPhone
    自己熟练的才是最佳的
    shenjinpeng
        15
    shenjinpeng  
       2022-09-15 10:01:16 +08:00
    十多年前网络小说最火那会, 满大街 PHP 盗版小说网站, 小说内容全是爬虫采集的,
    sunwei0325
        16
    sunwei0325  
       2022-09-15 10:02:59 +08:00 via iPhone   ❤️ 2
    爬的好的都在里面踩缝纫机呢吧
    zzzkkk
        17
    zzzkkk  
       2022-09-15 10:06:09 +08:00
    @ragnaroks
    速度太慢了
    一个 chromium 实例最多并发 10 个请求
    zbatman
        18
    zbatman  
       2022-09-15 10:10:30 +08:00
    有请八方辩手入场
    v2yllhwa
        19
    v2yllhwa  
       2022-09-15 10:13:29 +08:00 via Android
    @xz410236056 python io 时释放 gil 锁,多线程爬虫也还好吧
    kaiger
        20
    kaiger  
       2022-09-15 10:14:04 +08:00
    scrapy 我感觉挺简单的
    wangtian2020
        21
    wangtian2020  
       2022-09-15 10:14:36 +08:00
    最佳的爬虫语言是你最擅长最熟悉的语言
    因为我只会 nodejs ,随意就是它了
    tzar
        22
    tzar  
       2022-09-15 10:16:04 +08:00
    无意义的问题
    zhuangzhuang1988
        23
    zhuangzhuang1988  
       2022-09-15 10:19:36 +08:00
    熟悉啥语言用啥。
    dcsuibian
        24
    dcsuibian  
       2022-09-15 10:36:07 +08:00   ❤️ 1
    我觉得是 Node.js ,毕竟 web 本来就是 js 的主战场
    1 、对 JSON 的处理好得不得了(毕竟就是来源于 js 的)
    2 、方便处理 DOM ,这基本就是前端的工作
    3 、异步支持极好(因为 js 的单线程特性,不异步就卡死了)
    4 、部分网页的 DOM 其实是 js 生成的,如果你选的就是 js ,那么会比较熟悉
    5 、puppeteer 、playwright 这种爬虫杀手锏,都是优先支持 js 的


    我是先学的 Python 的 Scrapy ,然后又用了 Node.js 。
    我感觉 Node.js 不需要什么爬虫框架,直接 axios 请求下来,然后 cheerio 解析就好了。(最主要是可以复用写前端的经验)

    唯有对速度不敢确定,因为我都限制请求频率的,怕踩缝纫机
    Dganzh
        25
    Dganzh  
       2022-09-15 10:36:58 +08:00
    写 Go 的人喜欢造轮子,是时候造一个大而全的爬虫框架了
    wxf666
        26
    wxf666  
       2022-09-15 10:47:44 +08:00
    @dfgddgf 你每秒要爬多少网页啊?

    要不你放点要爬的网页出来?可能有热心观众给出自己的爬法,和爬取速度统计
    CodeSorcerer
        27
    CodeSorcerer  
       2022-09-15 10:49:56 +08:00
    用 PHP 的话 https://github.com/kiddyuchina/Beanbun 这个是基于 Workerman 的爬虫框架
    或者使用 swoole 的一些框架也 OK
    wxf666
        28
    wxf666  
       2022-09-15 10:57:36 +08:00
    @dfgddgf 毕竟能了解这么多语言生态各自的爬虫方案的网友,可能不多

    估计给出同一具体场景,各位网友给出自认为最好的方案,最后才容易对比
    placeholder
        29
    placeholder  
       2022-09-15 11:01:19 +08:00   ❤️ 1
    要做爬虫就先用当前技术栈做呗,性能差能差到哪去,

    你给性能整上去了给人网站干崩了,你性能再好有屁用

    反正都是偷着爬,最多尊重一下 robots 文件
    Aumujun
        30
    Aumujun  
       2022-09-15 11:05:49 +08:00
    单站爬虫的速度倒是其次,能取到数据就是最好的结果,慢点都无所谓;也就是用啥都一样,性能要求不会太高(至少没有高到你换语言的程度)
    815979670
        31
    815979670  
       2022-09-15 11:07:00 +08:00
    php 有一个 querylist 用起来还挺方便的 写数组就行了 http://querylist.cc/
    777777
        32
    777777  
       2022-09-15 11:19:43 +08:00
    golang ,我们现在日均 1500w 网站
    herozzm
        33
    herozzm  
       2022-09-15 11:19:47 +08:00
    我觉得是 go ,多线程完美匹配多线程爬虫
    Jirajine
        34
    Jirajine  
       2022-09-15 11:31:01 +08:00
    爬虫这种经常变化的场景,不宜用静态语言,尤其不宜用 rust 这种类型严格的静态语言。
    haolongsun
        35
    haolongsun  
       2022-09-15 12:38:38 +08:00
    如果真的有时间来学习的话,就 all in rust 吧,rust 的网络库质量非常的高,库的作者专门研究 http 的.
    kkocdko
        36
    kkocdko  
       2022-09-15 13:12:09 +08:00
    rsshub ,使用 nodejs 的大型(中型)爬虫项目。
    we9ta
        37
    we9ta  
       2022-09-15 13:16:46 +08:00
    必须是易语言,不接受反驳
    charmToby
        38
    charmToby  
       2022-09-15 13:25:37 +08:00
    上招聘 APP ,搜索关键字爬虫,绝大部分都是 Python 。
    terranboy
        39
    terranboy  
       2022-09-15 13:50:54 +08:00
    一般的随便什么语言都一样, 要爬真正有价值的内容 还得整合浏览器进去 , 想要性能就得堆机器
    iwh718
        40
    iwh718  
       2022-09-15 14:05:13 +08:00 via Android
    perl
    zzzkkk
        41
    zzzkkk  
       2022-09-15 14:25:16 +08:00
    @815979670
    用 puppeteer 写了个爬虫 美区 3000 个 lambda 用 php guzzlehttp 根本起不来 3000 个链接
    最后用 aws go client 解决了
    php 真的步 per 后尘了
    dfgddgf
        42
    dfgddgf  
    OP
       2022-09-15 14:39:20 +08:00
    @zzzkkk guzzle 看了一些源代码,底层貌似没有依赖 c 或者 c++

    应该是底层没有设计成高度可靠的组件。

    perl 的爬虫模块 mojo::useragent 配合 libEV ,确实很强大。

    cygwin 平台并发 50 轻轻松松,而且还保持 http 连接可以复用
    sunnysab
        43
    sunnysab  
       2022-09-15 14:54:45 +08:00 via Android
    还真用 rust 写过爬虫,是先拿 Python 做原形,然后用 rust 重写。rust 的网页解析性能和浏览器相当,但是 python 明显慢多了(数秒,不可接受)。
    不过 rust 里解析 HTML 的代码不好看,也不排除是我思想没转过弯用了太多 unwrap()。😂😂
    Cbdy
        44
    Cbdy  
       2022-09-15 14:56:02 +08:00 via Android
    我只知道 Google 搜索引擎的爬虫主要是 C++和 Java 写的
    zzzkkk
        45
    zzzkkk  
       2022-09-15 15:02:20 +08:00
    @dfgddgf
    perl 已死 倒闭了活该 there is more than one way to do it , 不要说控制结构 连变量在不同 context 都取不同的值 增加码农的大脑 负担
    zzzkkk
        46
    zzzkkk  
       2022-09-15 15:04:15 +08:00
    @sunnysab
    rust 写解析代码生成 dom 树?
    私以为单纯的 html 选择器还不够 一定要生成 dom 树 那样才能获取节点的 parent 节点
    wxf666
        47
    wxf666  
       2022-09-15 15:13:35 +08:00
    @sunnysab 你 python 用啥做 html 的 parser ? lxml 的速度也不够吗?
    yekern
        48
    yekern  
       2022-09-15 15:28:29 +08:00
    php querylist 可以写好规则就可以了. 同时可以支持插件扩展, 支持无头浏览器
    laravel
        49
    laravel  
       2022-09-15 15:35:03 +08:00
    我在用 nodejs 写爬虫,用 puppeteer cheerio axios 这些库,都是针对特定网站写爬虫。
    buyan3303
        50
    buyan3303  
       2022-09-15 16:05:43 +08:00
    熟悉哪种编程语言,就用哪种语言的爬虫框架。

    多数学 python 的人,使用的是 scrapy 。python 以及 scrapy 有较为丰富的教程,我曾经就一边看着某课网的爬虫实战教程,一边自己学着爬虾米音乐,即使有些内容不适配,但是那个实战教程,从采集到入库一成套都教了,还教了 xpath lxml 匹配失败的原因之类的东西。
    shyling
        51
    shyling  
       2022-09-15 16:07:45 +08:00
    爬虫种类多啊。。

    爬量的和爬有保护的内容的不一样
    fuxkcsdn
        52
    fuxkcsdn  
       2022-09-15 16:13:58 +08:00
    反正不是 python 就对了,python 除了 bs 库比较好用外,并没看出有啥特别的优势
    加上现在 cdp 协议的普及,很多反爬还是得靠 cdp 来实现,cdp 就是 nodejs 的地盘了
    ljtnine
        53
    ljtnine  
       2022-09-15 16:18:27 +08:00
    aiohttp
    www5070504
        54
    www5070504  
       2022-09-15 16:29:40 +08:00
    肯定是库多 省事的那个 爬虫性能大多数浪费在 io 上 啥语言性能也不会有明显优势
    zzl22100048
        55
    zzl22100048  
       2022-09-15 16:47:13 +08:00
    @ljtnine aiohttp 这个库 bug 太多了
    xieren58
        56
    xieren58  
       2022-09-15 18:01:16 +08:00
    nodejs + playwright + cheerio, 谁使用谁知道. (刑
    ljtnine
        57
    ljtnine  
       2022-09-15 18:21:55 +08:00
    @zzl22100048 啊?我用这个库写过一个简单的爬虫,还没遇到过问题
    wxf666
        58
    wxf666  
       2022-09-15 18:32:52 +08:00
    @zzl22100048 有啥 bug 吗?我用这个库爬了好多小说了

    @dfgddgf 我提供一个 Python 异步 + 多线程 的数据:

    环境:Redmi Note 5 (高通骁龙 636 )的 Linux Deploy 里,Debian 11 arm64 ,Python 3.10 ,百兆 WIFI ,电池供电

    流程:sqlite3 读取网址,aiohttp 并发下载多个章节,json 解析,每本书所有章节合并成一个 json ,编码成 UTF-16 ,多线程 lzma 压缩,每一千本保存一个 tar

    速度:峰值 700 章节 /秒(每个章节需下载一个页面,大约在凌晨 3 点 ~ 7 点)
    ox180
        59
    ox180  
       2022-09-15 19:22:20 +08:00
    js
    Aloento
        60
    Aloento  
       2022-09-15 19:40:19 +08:00
    看需求吧,我个人用的是 C#,自带的那个 driver 是真的强大
    uqf0663
        61
    uqf0663  
       2022-09-15 21:02:56 +08:00
    如果有一天 楼上的人熟悉易语言,就会知道论搞爬虫这方面,在易语言面前楼主列的这些外国玩意都是渣渣。
    zzl22100048
        62
    zzl22100048  
       2022-09-15 21:52:28 +08:00
    @ljtnine
    @wxf666
    - 之前版本超时控制有问题,task 放入 eventloop 开始算,现在独立出来一个 timeout 类;
    - 高并发下有概率出现读取 tcp 流的异常和 broken pipe 异常;
    - session 不能携带之前的 cookie ;
    duke807
        63
    duke807  
       2022-09-15 21:54:58 +08:00 via Android
    python
    tikazyq
        64
    tikazyq  
       2022-09-15 21:56:55 +08:00
    python
    tikazyq
        65
    tikazyq  
       2022-09-15 21:57:30 +08:00
    比较 popular 的爬虫合集,不用谢
    https://github.com/BruceDone/awesome-crawler
    wxf666
        66
    wxf666  
       2022-09-15 23:22:34 +08:00
    @zzl22100048

    > 高并发下有概率出现读取 tcp 流的异常和 broken pipe 异常;

    Emm 。。反正我做了错误检测,超时 /错了就重试。也不知道频不频繁


    > session 不能携带之前的 cookie ;

    也没注意这个问题,因为爬的小说不要求登录。。
    locoz
        67
    locoz  
       2022-09-16 04:36:57 +08:00 via Android
    想用啥用啥啊,为什么要局限于一个语言?语言只是个工具而已
    关于   ·   帮助文档   ·   博客   ·   API   ·   FAQ   ·   实用小工具   ·   5372 人在线   最高记录 6679   ·     Select Language
    创意工作者们的社区
    World is powered by solitude
    VERSION: 3.9.8.5 · 32ms · UTC 07:20 · PVG 15:20 · LAX 23:20 · JFK 02:20
    Developed with CodeLauncher
    ♥ Do have faith in what you're doing.