使用go实现Redis服务端(原生net包)

前言

        你是否曾经遇到过这样的困惑:刚开始接触Go语言时,不像java一样有着良好的生态,不知道该从何入手?也许你想参考一下知名项目如 Kubernetes 和 etcd ,但光是看目录就已经让你头晕目眩,更别提从哪里开始阅读源码了。为了帮助解决这个问题,Tiny-Redis项目应运而生。通过这个项目,你将了解开发中间件的思路,涉及到RESP协议的应用,如何开发一个服务端,以及在高并发情况下的解决方案。希望你通过学习这个项目后,能够在秋招中大展身手。

简介

        tiny-redis 是一个由 Go 编写的高性能独立缓存服务器。它实现了完整的 RESP(Redis 序列化协议),因此支持所有的 Redis 客户端。

特点

        *支持基于 RESP 协议的所有客户端。 *支持字符串、列表、集合、哈希数据类型。 *支持 TTL(键-值对将在 TTL 后被删除)。 *完全内存存储。 *支持一些需要的原子操作命令(如 INCR、DECR、INCRBY、MSET、SMOVE 等)。

开始之前

        在开始之前,建议你先克隆 Tiny-Redis 项目的 GitHub 仓库,你可以通过以下命令来实现:

git clone https://github.com/HSn0918/tinyredis.git
cd tinyredis

在这个项目中,你会看到几个重要的文件和目录,它们分别是:

|-- README.md
|-- RESP//RESP协议数据类型和解析RESP函数
|-- config//配置
|-- go.mod
|-- logger//日志
|-- main.go
|-- memdb//数据库数据类型
|-- server//服务端
`-- util
|-- README.md
|-- RESP
|   |-- arraydata.go
|   |-- bulkdata.go
|   |-- errordata.go
|   |-- intdata.go
|   |-- parser_test.go
|   |-- parsestream.go
|   |-- plaindata.go
|   |-- stringdata.go
|   `-- structure.go//解析RESP协议
|-- config
|   `-- config.go
|-- go.mod
|-- logger
|   |-- level.go
|   `-- logger.go
|-- main.go
|-- memdb
|   |-- command.go//方法注册函数
|   |-- concurrentmap.go//ConcurrentMap
|   |-- db.go//内存数据库
|   |-- dblock.go//锁
|   |-- hash.go
|   |-- hash_struct.go
|   |-- keys.go
|   |-- keys_test.go
|   |-- list.go
|   |-- list_struct.go
|   |-- list_test.go
|   |-- set.go
|   |-- set_struct.go
|   |-- string.go
|   |-- string_test.go
|   |-- zset.go
|   `-- zset_struct.go
|-- server
|   |-- handler.go//监听端口
|   `-- server.go//启动服务
`-- util
    `-- util.go//hash函数和正则实现

从源码构建 


go build -o tiny-redis main.go
./tiny-redis -h
Usage of ./tiny-redis:
  -config string
        Appoint a config file: such as /etc/redis.conf
  -host string
        Bind host ip: default is 127.0.0.1 (default "127.0.0.1")
  -logdir string
        Set log directory: default is /tmp (default "./")
  -loglevel string
        Set log level: default is info (default "info")
  -port int
        Bind a listening port: default is 6379 (default 6379)
./tiny-redis

从Docker构建

        值得注意的是,我们已经在 /data 目录为你准备好了 redis-cli 命令行工具方便你调试使用。由于项目未做数据持久化,所以即使你挂载了 /data 目录也只能得到一些日志文件,以及 tiny-redisredis-cli

docker build -t tiny-redis:0.1 .
docker run -d \
  --name tiny-redis \
  -p 6379:6379 \
  -v tinyredis-data:/data\
  tiny-redis:0.1

任何 Redis 客户端都可以与 tiny-redis 服务器通信。

目前支持图形化客户端:Medis、AnotherRedisDesktopManager。然而需要注意的是,这些客户端中显示的关于服务端的信息可能并不是准确的

例如,可以使用 redis-cli 与 tiny-redis 服务器通信:

$ ./tiny-redis 
[info][server.go:25] 2023/09/17 00:55:35 [Server Listen at 127.0.0.1:6379]
[info][server.go:35] 2023/09/17 00:55:40 [127.0.0.1:7810  connected]
$ redis-cli
127.0.0.1:6379> PING
PONG
127.0.0.1:6379> MSET key1 a key2 b
OK
127.0.0.1:6379> MGET key1 key2 nonekey
1) "a"
2) "b"
3) ""
127.0.0.1:6379> RPUSH list1 1 2 3 4 5
(integer) 5
127.0.0.1:6379> LRANGE list1 0 -1
1) "1"
2) "2"
3) "3"
4) "4"
5) "5"
127.0.0.1:6379> TYPE list1
list
127.0.0.1:6379> EXPIRE list1 100
(integer) 1
127.0.0.1:6379> TTL list1
(integer) 96
127.0.0.1:6379> PERSIST list1
(integer) 1
127.0.0.1:6379> TTL list1
(integer) -1

性能基准测试

性能基准测试的结果是基于 redis-benchmark 工具进行的。redis-benchmark 测试在Lenovo Legion R70002021, AMD Ryzen 5 5600H with Redeon Graphics, NVIDA Geforce RTX3050 laptop CPU 4GB, 16GB (3200MHX), Windows11 with Ubuntu 20.04.6 LTS(WSL2) redis-benchmark -c 50-n 200000 -t get

get: 146716.22 requests per second
set: 153433.08 requests per second
incr: 144334.86 requests per second
lpush: 145313.64 requests per second
rpush: 139470.00 requests per second
lpop: 152226.30 requests per second
rpop: 147929.08 requests per second
sadd: 160599.60 requests per second
hset: 147765.06 requests per second
spop: 144109.50 requests per second

lrange_100: 83880.90 requests per second
lrange_300: 50652.36 requests per second
lrange_500: 37703.82 requests per second
lrange_600: 27895.92 requests per second

mset: 126196.26 requests per second

可用命令 

最后 

笔者也是初学 Go,借鉴了其他优秀的开源代码,如果文章/代码有错误的地方,敬请斧正。

项目链接

GitHub - HSn0918/tinyredis: tiny-redis

如需转载,请保留项目链接。

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值