2024年Go爬虫学习笔记_go爬虫的知识储备

  • 扩展性
  • 一致性
  • 可用性
  • 高并发
  • 微服务

爬虫:

  • 前端
  • 数据解析
  • 数据存储
  • 数据可视化分析
  • 高并发

项目流程:

  • 需求
  • image

项目特点:

  • 故障容错
  • 扩展性
  • 领域驱动微服务

微服务治理:

image

image

个人展望:

  • Go基础巩固
  • 分布式、微服务入门
  • 代码更加优美
  • 工程化管理

项目启动篇

谷歌:软件工程服务中的语言设计

语言特性:

  • 面向组合而不是继承,鸭子类型

  • 并发原语:协程、通道

  • 简单健壮性

    • 没有隐式的数值转换
    • 没有指针运算
    • 运行时会检查数组的边界
    • 垃圾回收。
    • 内存逃逸,这意味着我们可以传递栈上变量的地址,而这在 C 语言中会产生类似野指针的问题。
  • 强大丰富的标准库与工具集

开发环境

  • Go语言环境:GOPATH、GOMOD、GOPROXY
  • VS Code、Goland、Vim
  • 环境切换(Goland有,同时你可以配合docker或wsl进行切换到linux)
  • 项目模板
  • 快捷键
  • GO命令:build、clean、fmt、genernate、get、list、mod、run、testtoolinstallwork

基础语法

  • 变量与类型

    • 声明与赋值
    • 内置类型
    • 命名规则
    • 生命周期
    • 作用域
  • 表达式与运算符

    • 算术运算符
    • 关系运算符
    • 逻辑运算符
    • 位运算符
    • 赋值运算符
    • 地址运算符
    • 优先级
      优先级(由高到低)              操作符
        5                *  /  %  <<  >>  &  &^
        4                +  -  |  ^
        3                ==  !=  <  <=  >  >=
        2                &&
        1                ||
    
    
  • 基本控制结构

    • if else
    • switch
    • for:C风格、条件、loop、range
  • 函数

    • 声明
    • 多返回值
    • 可变参数
    • 递归
    • 函数参数
    • 函数返回值
    • 函数值
  • 复合类型

    • 数组

    • 切片

      • 声明与赋值
      • 添加
      • 截取,底层
      • 删除
    • 哈希表

      • 声明、初始化
      • 访问
      • 赋值
      • 删除
    • 结构体

      • 声明与赋值
      • 匿名结构体:测试和序列化
      • 可比较性

假设我们需要学习一门新的语言,你认为我们需要把握哪些核心的知识,又应该沿着什么样的路径去学习呢?

  • 设计之初、语法、特性、、调试、编程模式
  • 小项目
  • 开源项目

语法特性

  • defer

    • 资源释放
    • panic捕获
    • 延迟执行
    • 参数预计算
    • LIFO
  • 接口

    • 空接口
    • 定义、声明
    • 实现
    • 调用
    • 组合
    • 断言
    • 动态类型 v.(type)
    • 比较
  • 并发

    • 协程

    • 通道

      • 声明、初始化
      • 读写
      • 关闭
      • 作为参数
      • 作为返回值
      • 单方向的通道,用于只读和只写场景
      • select,随机执行
    • context

      • 协程优雅退出
      • 级联退出
    • 原子锁:atomic

    • 互斥锁

    • 读写锁:适合多读少写场景。

    • sync.Once、sync.Cond、sync.WaitGroup

  • 项目组织

  • 依赖管理:gomod

  • 组合

  • 工具与库

    • 编辑
    • 测试:
    • 编译
    • 部署:
    • 调试
    • 分析
  • 工具:代码分析与代码规范

    • 静态:检查代码的结构、代码风格以及语法错误,这种工具也被称为 Linter。

  • 测试

    • go test
    • go test -cover
    • go tool cover
    • go test -bench
  • 调试

    • dlv
    • gdb
    • pprof
    • trace:我们在 pprof 的分析中,能够知道一段时间内 CPU 的占用、内存分配、协程堆栈等信息。这些信息都是一段时间内数据的汇总,但是它们并没有提供整个周期内事件的全貌。例如,指定的协程何时执行,执行了多长时间,什么时候陷入了堵塞,什么时候解除了堵塞,GC 是如何影响协程执行的,STW 中断花费的时间有多长等。而 Go1.5 之后推出的 trace 工具解决了这些问题。trace 的强大之处在于,提供了程序在指定时间内发生的事件的完整信息,让我们可以精准地排查出程序的问题所在,在后面的课程中,还会用 trace 完成对线上实战案例的分析。
    • gops:gops 是谷歌推出的调试工具,它的作用是诊断系统当前运行的 Go 进程。gops 可以显示出当前系统中所有的 Go 进程,并可以查看特定进程的堆栈信息、内存信息等。
  • 标准库

  • 三方库

你如何理解 Go 语言的一句名言:“不要通过共享内存来通信,通过通信来共享内存”?

  • 共享内存

    • 需要额外的控制机制来确保通信内存中内容的正确性。
    • 容易出bug
  • 通信

    • 一定时正确的,只要等待即可
    • 减少bug
    • 通道一种所有权转移的机制,为我们屏蔽了锁等机制。 通过一些简单的并发模型(例如fan-in、fan-out),开发并行程序会变得非常容易

通过共享内存通信相当于双方必须依靠额外的控制机制来确保通信时内存中的内容是正确的,这一点需要共享双方设置同步机制,并不通用, 还容易有bug。但是通过通信共享内存则可以利用通用的通信基建, 凡是经过通信传递的信息一定是发送方确认正确的, 接收方只需要等待即可, 不用再依赖额外的同步机制,减少了出bug的机会。

并发编程

项目组织

工具与库

master开发与原理篇

etcd

etcd etcd doc #etcd#​

简介

etcd 这个名字是 etc distributed 的缩写。我们知道,在 Linux 中 etc 目录存储了系统的配置文件,所以 etcd 代表了分布式的配置中心系统。然而,它能够实现的功能远不是同步配置文件这么简单。etcd 可以作为分布式协调的组件帮助我们实现分布式系统。

架构

etcd 的第一个版本 v0.1 于 2013 年发布,现在已经更新到了 v3,在这个过程中,etcd 的稳定性、扩展性、性能都在不断提升。我们先来从整体上看一看 etcd 的架构。

image

etcd 从大的方面可以分为几个部分,让我们结合图片从右往左说起。

  • raft-http 模块:由于 etcd 通常为分布式集群部署方式,该层用于处理和其他 etcd 节点的网络通信。etcd 内部使用了 HTTP 协议来进行通信,由于 etcd 中的消息类型很多,心跳探活的数据量较小,快照信息较大(可达 GB 级别),所以 etcd 有两种处理消息的通道,分别是 Pipeline 消息通道与 Stream 消息通道。​#raft#​

    • Stream 消息通道是 etcd 中节点与节点之间维护的长连接,它可以处理频繁的小消息,还能复用 HTTP 底层的连接,不必每次都建立新的连接。
    • Pipeline 消息通道用于处理快照这样数据量大的信息,处理完毕后连接会关闭。
  • etcd-raft 模块:它是 etcd 的核心。该层实现了 Raft 协议,可以完成节点状态的转移节点的选举数据处理等重要功能,确保分布式系统的一致性故障容错性。之前我们也介绍过,Raft 中的节点有 3 种状态,分别是 Leader(领导者),Candidates(候选人)和 Follower(跟随者)。在此基础上,etcd 为 Raft 节点新增了一个 PreCandidate(预候选人)。
    我们在讲解 Raft 协议时介绍过,如果节点收不到来自 Leader 的心跳检测,就会变为 Candidates 开始新的选举。如果当前节点位于不足半数的网络分区中,短期内不会影响集群的使用,但是当前节点在不断发起选举的过程中,当前选举周期的 Term 号会不断增长,当网络分区消失后,由于该节点的 Term 号高于当前集群中 Leader 节点的 Term 号,Raft 协议就会迫使当前的 Leader 切换状态并开始新一轮的选举。
    但是,这种选举是没有意义的。为了解决这样的问题,etcd 在选举之前会有一个新的阶段叫做 PreVote,当前节点会先尝试连接集群中的其他节点,如果能够成功连接到半数以上的节点,才开始新一轮的选举。
    image

  • raft-node 模块:在 etcd-raft 模块基础之上还封装,这个模块主要是上层模块和下层 Raft 模块沟通的桥梁,它同时还有一个重要任务,就是调用 storage 模块,将记录(Record)存储到 WAL ​日志文件中落盘。WAL 日志文件可以存储多种类型的记录,包括下面几种。
    WAL 日志文件非常重要,它能保证我们的消息在大部分节点达成一致且应用到状态机之前,让记录持久化。这样,在节点崩溃并重启后,就能够从 WAL 中恢复数据了。​#wal#​
    WAL 日志的数量与大小随着时间不断增加,可能超过可容纳的磁盘容量。同时,在节点宕机后,如果要恢复数据就必须从头到尾读取全部的 WAL 日志文件,耗时也会非常久。为了解决这一问题,etcd 会定期地创建快照并保存到文件中,在恢复节点时会先加载快照数据,并从快照所在的位置之后读取 WAL 文件,这就加快了节点的恢复速度。快照的数据也有单独的 snap 模块进行管理。

    • WAL 文件的元数据,记录节点 ID、集群 ID 信息。
    • Entry 记录,即客户端发送给服务器处理的数据。
    • 集群的状态信息,包含集群的任期号、节点投票信息。
    • 数据校验信息,它可以校验文件数据的完整性与正确性。
    • 快照信息,包含快照的相关信息,但不包含实际的快照数据。它可以校验快照数据的完整性。
    type Record struct {
      Type                 int64    `protobuf:"varint,1,opt,name=type" json:"type"`
      Crc                  uint32   `protobuf:"varint,2,opt,name=crc" json:"crc"`
      Data                 []byte   `protobuf:"bytes,3,opt,name=data" json:"data,omitempty"`
    }
    
    
  • **etcd-server 模块:**它最核心的任务是执行 Entry 对应的操作,在这个过程中包含了限流操作与权限控制的能力。所有操作的集合最终会使状态机到达最新的状态。etcd-server 同时还会维护当前 etcd 集群的状态信息,并提供了线性读的能力。
    etcd-server 提供了一些供外部访问的 GRPC API 接口,同时 etcd 也使用了 GRPC-gateway 作为反向代理,使服务器也有能力对外提供 HTTP 协议。

  • 最后,etcd 还提供了客户端工具 etcdctl 和 clientv3 代码库,使用 GRPC 协议与 etcd 服务器交互。客户端支持负载均衡、节点间故障自动转移等机制,极大降低了业务使用 etcd 的难度,提升了开发的效率。

  • 此外,etcd 框架中还有一些辅助的功能,例如权限管理、限流管理、重试、GRPC 拦截器等。由于不是核心点,图中并没有一一列举出来。

优点
  • 高内聚:从 etcd 整体的架构图上可以看出,etcd 将相关的核心功能(例如鉴权、网络、Raft 协议)都聚合起来形成了一个单独的模块。功能之间联系紧密,并且只提供核心的接口与外部进行交互。这非常便于理解与开发,也便于后期对功能进行组合。
  • 低耦合:各个模块之间边界清晰,用接口来进行交流与组合的设计给了程序极大的扩展性。举一个例子,数据存储的 store 就是一个 interface。

type Storage interface {
  InitialState() (pb.HardState, pb.ConfState, error)
  Entries(lo, hi, maxSize uint64) ([]pb.Entry, error)
  Term(i uint64) (uint64, error)
  LastIndex() (uint64, error)
  FirstIndex() (uint64, error)
  Snapshot() (pb.Snapshot, error)
}

在 etcd 代码库中有一个示例代码,该示例代码基于 etcd-raft 模块实现了一个最简单的分布式内存 KV 数据库。在示例代码中实现了上游的 KVServer 服务器与 raft-node 节点,并与 etcd-raft 模块进行交互,去掉了 etcd 实现的日志落盘等逻辑,将键值对存储到了内存中。如果你有志于深入地学习 etcd,从这个实例入手是非常不错的选择。

  • 优雅的数据同步:在 etcd 中,我们极少看到使用互斥锁的场景。更多的时候,它是借助协程与通道的相互配合来传递信息的,这就既完成了通信又优雅地解决了并发安全问题。
  • 更快的读取性能:etcd 在 etcd-raft 模块中实现了 Raft 协议。我们知道 Raft 并不能够保证读取的线性一致性,也就是说,它有可能读取到过时的数据。

怎么解决呢?办法有很多。

+ Follower 可以将读请求直接转发给 Leader,不过这样的话 Leader 的压力会很大,并且 Leader 可能已经不是最新的 Leader 了。
+ 第二种解决方案是 etcdv3.2 之前的处理方式。也就是将该请求记录为一个 Entry,从而借助 Raft 机制来保证读到的数据是最新的。
+ 还有一种更轻量级的方法。在 v3.2 之后,etcd 实现了 ReadIndex 机制,这也是在 Raft 论文当中提到过的。Follower 向 Leader 读取当前最新的 Commit Index,同时 Leader 需要确保自己没有被未知的新 Leader 取代。它会发出新一轮的心跳,并等待集群中大多数节点的确认。一旦收到确认信息,Leader 就知道在发送心跳信息的那一刻,不可能存在更新的 Leader 了。也就是说,在那一刻,ReadIndex 是集群中所有节点见过的最大的 Commit Index。Follower 会在自己的状态机上将日志至少执行到该 Commit Index 之后,然后查询当前状态机生成的结果,并返回结果给客户端。
  • 可靠的 Watch 机制与高性能的并发处理:相对于 etcdv2,etcdv3 版本将所有键值对的历史版本都存储了起来,这就让 Watch 机制的可靠性更高了,它实现的 MVCC 机制也提高了系统处理并发请求的数量。
MVCC

​#mvcc#​

etcd 存储了当前 Key 过去所有操作的版本记录。这样做的好处是,我们可以很方便地获取所有的操作记录,而这些记录常常是实现更重要的特性的基础,例如要实现可靠的事件监听就需要 Key 的历史信息。

etcd v2 会在内存中维护一个较短的全局事件滑动窗口,保留最近的 1000 条变更事件。但是当事件太多的时候,就需要删除老的事件,可能导致事件的丢失。

最后

Python崛起并且风靡,因为优点多、应用领域广、被大牛们认可。学习 Python 门槛很低,但它的晋级路线很多,通过它你能进入机器学习、数据挖掘、大数据,CS等更加高级的领域。Python可以做网络应用,可以做科学计算,数据分析,可以做网络爬虫,可以做机器学习、自然语言处理、可以写游戏、可以做桌面应用…Python可以做的很多,你需要学好基础,再选择明确的方向。这里给大家分享一份全套的 Python 学习资料,给那些想学习 Python 的小伙伴们一点帮助!

👉Python所有方向的学习路线👈

Python所有方向的技术点做的整理,形成各个领域的知识点汇总,它的用处就在于,你可以按照上面的知识点去找对应的学习资源,保证自己学得较为全面。

👉Python必备开发工具👈

工欲善其事必先利其器。学习Python常用的开发软件都在这里了,给大家节省了很多时间。

👉Python全套学习视频👈

我们在看视频学习的时候,不能光动眼动脑不动手,比较科学的学习方法是在理解之后运用它们,这时候练手项目就很适合了。

👉实战案例👈

学python就与学数学一样,是不能只看书不做题的,直接看步骤和答案会让人误以为自己全都掌握了,但是碰到生题的时候还是会一筹莫展。

因此在学习python的过程中一定要记得多动手写代码,教程只需要看一两遍即可。

👉大厂面试真题👈

我们学习Python必然是为了找到高薪的工作,下面这些面试题是来自阿里、腾讯、字节等一线互联网大厂最新的面试资料,并且有阿里大佬给出了权威的解答,刷完这一套面试资料相信大家都能找到满意的工作。

需要这份系统化学习资料的朋友,可以戳这里无偿获取

一个人可以走的很快,但一群人才能走的更远!不论你是正从事IT行业的老鸟或是对IT行业感兴趣的新人,都欢迎加入我们的的圈子(技术交流、学习资源、职场吐槽、大厂内推、面试辅导),让我们一起学习成长!

  • 14
    点赞
  • 21
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值