并发编程
并发是单核分时间片运行 并行是多核运行(可视作实现并发的手段)
Goroutine
协程:用户态,轻量级线程,栈KB级别
线程:内核态,线程跑多个协程,栈MB手段
使用go关键字为函数创建协程
CSP协程间通信
提倡通过通信共享内存(用通道连接),而不是通过共享内存来实现通信
Channel
make(chan 元素类型,[缓存大小])
无缓冲通道(同步通道) make(chan int)
有缓存通道 make(chan int, 2)
并发安全 Lock 锁
WaitGroup
计数器,处理阻塞主协程,等待子协程完成
Add()加协程数
Done()协程数-1
Wait()等待
依赖管理
方案:GOPATH->Go Vendor->Go Module(目前)
方案
GOPATH
go的环境变量
- bin 项目编译的二进制文件
- pkg 项目编译的中间产物,加速编译
- src 项目源码
go get 下载最新版本到src下
问题:无法实现package的多版本控制
Go Vendor
项目目录增加vendor文件
为每个项目引入依赖副本,解决版本冲突
问题:无法控制依赖版本
Go Module
通过go.mod管理依赖包版本
通过go get/go mod管理依赖包
三要素
- 配置文件,描述依赖——go.mod
- 中心仓库管理依赖库——Proxy
- 本地工具——go get/mod
依赖配置
version
- 语义化版本
${MAJOR}.${MINOR}.${PATCH}
大版本(可以不兼容),新增功能,代码bug修复 V1.3.0
- 基于commit伪版本
vx.0.0-时间戳-12位hash码前缀
v0.0.0-20220401081311-c38fb59326b7
indirect
非直接依赖
incompatible
主版本2+模块要在模块路径增加/vN后缀
没有go.mod且主版本在2+的依赖要加+incompatible
依赖图
依赖多个版本时,选择最低的兼容版本(最小可用版本)
Proxy
用来保证下载依赖的稳定和可靠性
GOPROXY="proxy1.cn, proxy2.cn, dirct",URL列表
工具
go get 下载/删除指定依赖
go mod 管理一系列依赖
测试
回归测试->集成测试->单元测试
单元测试
保证质量、提高效率
通过go test xxx_test.go xxx.go
规则
- 测试文件以_test.go结尾
func TestXxx(* *testing.T)- 初始化逻辑放到TestMain中
- 实现测试前数据装载、配置初始化
- 测试后释放资源
用assert包比较也行
覆盖率
测试参数加--cover
Tips
- 一般覆盖率:50%~60%,较高80%+
- 测试分支相互独立、全面覆盖
- 测试单元粒度足够小、函数单一职责
依赖
幂等:任何时刻结果相同
稳定:测试函数可独立运行
Mock
可用开源包monkey
打桩,有点像手动替换一些依赖的函数,是测试能够进行下去
基准测试
func BenchmarkXxx- 用rand并发测试时可用fastrand替代,更快些,因为rand用并发的锁
实践
用例图
ER图
分层结构
- 数据层:数据Model,外部数据的增删改查
- 逻辑层:业务Entity,处理核心业务逻辑输出
- 视图层:视图view,处理和外部的交互逻辑