Skip to content

ReeseSys/redis-proxy

 
 

Repository files navigation

Redis Proxy

一个用 Go 语言实现的 Redis 代理服务器,支持单节点和集群模式,实现了 RESP 协议。

项目简介

Redis Proxy 是一个轻量级的 Redis 代理服务,可以作为客户端和 Redis 服务器之间的中间层。它支持:

  • ✅ Redis 单节点模式
  • ✅ Redis 集群模式
  • ✅ RESP 协议解析
  • ✅ 常用 Redis 命令支持
  • ✅ Docker 容器化部署

功能特性

支持的 Redis 命令

基础命令

  • PING - 测试连接
  • AUTH - 认证
  • QUIT - 退出连接
  • SELECT - 选择数据库
  • INFO - 服务器信息
  • CONFIG - 配置管理
  • DBSIZE - 数据库大小
  • SCAN - 扫描键

字符串操作

  • GET - 获取值
  • SET - 设置值
  • SETEX - 设置值并指定过期时间
  • INCR - 自增
  • DECR - 自减
  • DEL - 删除键
  • EXISTS - 检查键是否存在
  • EXPIRE - 设置过期时间

哈希表操作

  • HGET - 获取哈希字段值
  • HSET - 设置哈希字段值
  • HDEL - 删除哈希字段

列表操作

  • LPUSH - 左侧插入
  • RPUSH - 右侧插入
  • LPOP - 左侧弹出
  • RPOP - 右侧弹出

集合操作

  • SADD - 添加成员
  • SREM - 删除成员
  • SMEMBERS - 获取所有成员

有序集合操作

  • ZADD - 添加成员
  • ZREM - 删除成员
  • ZRANGE - 范围查询

集群命令

  • CLUSTER - 集群信息
  • MODULE - 模块管理

快速开始

环境要求

  • Go 1.23.5 或更高版本
  • Redis 服务器 (单节点或集群)
  • Docker (可选,用于容器化部署)

安装

  1. 克隆项目
git clone <repository-url>
cd redis-proxy
  1. 安装依赖
go mod download
  1. 配置环境变量

在项目根目录创建 .env 文件:

# Redis 单节点配置
REDIS_HOST=127.0.0.1
REDIS_PORT=6379
REDIS_PASSWORD=your_password
REDIS_DB=0

# Redis 集群配置 (多个节点用逗号分隔)
# REDIS_HOST=192.168.1.1,192.168.1.2,192.168.1.3
# REDIS_PORT=6379,6379,6379

运行

本地运行

go run main.go

服务将在 16379 端口启动。

使用 Docker

从 Docker Hub 拉取镜像

# 拉取最新版本
docker pull hitosea/redis-proxy:latest

# 运行容器
docker run -d \
  -p 16379:16379 \
  -e REDIS_HOST=your_redis_host \
  -e REDIS_PORT=6379 \
  -e REDIS_PASSWORD=your_password \
  -e REDIS_DB=0 \
  --name redis-proxy \
  hitosea/redis-proxy:latest

本地构建镜像

# 构建镜像
docker build -t redis-proxy .

# 运行容器
docker run -d \
  -p 16379:16379 \
  -e REDIS_HOST=your_redis_host \
  -e REDIS_PORT=6379 \
  -e REDIS_PASSWORD=your_password \
  -e REDIS_DB=0 \
  --name redis-proxy \
  redis-proxy

多平台构建和发布

查看 Docker 构建指南 了解如何构建多平台镜像并发布到 Docker Hub。

# 快速开始
source .env.docker.local
./docker-build.sh --push --version v1.0.0

测试连接

使用 redis-cli 连接到代理:

redis-cli -p 16379

测试命令:

127.0.0.1:16379> PING
PONG
127.0.0.1:16379> SET mykey "Hello"
OK
127.0.0.1:16379> GET mykey
"Hello"

项目结构

redis-proxy/
├── cache/              # 缓存层实现
│   ├── cache.go       # 缓存接口定义
│   └── redis_cache.go # Redis 缓存实现
├── config/            # 配置管理
│   └── config.go      # 配置加载和解析
├── proxy/             # 代理服务器
│   └── redis.go       # Redis 协议实现
├── main.go            # 程序入口
├── go.mod             # Go 模块定义
├── go.sum             # 依赖版本锁定
├── Dockerfile         # Docker 构建文件
└── README.md          # 项目文档

配置说明

单节点模式

REDIS_HOST=127.0.0.1
REDIS_PORT=6379
REDIS_PASSWORD=password
REDIS_DB=0

集群模式

REDIS_HOST=192.168.1.1,192.168.1.2,192.168.1.3
REDIS_PORT=6379,6379,6379
REDIS_PASSWORD=password
REDIS_DB=0

注意: 集群模式下,所有节点的端口必须相同。

架构设计

核心组件

  1. Config 模块 (config/)

    • 负责从环境变量加载配置
    • 支持 .env 文件
    • 使用 Viper 进行配置管理
  2. Cache 模块 (cache/)

    • 提供统一的缓存接口
    • 支持单节点和集群模式自动切换
    • 封装 go-redis 客户端
  3. Proxy 模块 (proxy/)

    • 实现 RESP 协议解析
    • 处理客户端连接
    • 命令路由和执行

工作流程

客户端 -> TCP连接 -> RESP协议解析 -> 命令处理 -> Redis执行 -> 响应格式化 -> 客户端

依赖库

  • github.com/redis/go-redis/v9 - Redis 客户端
  • github.com/spf13/viper - 配置管理
  • github.com/joho/godotenv - 环境变量加载
  • github.com/jinzhu/copier - 结构体复制
  • go.uber.org/zap - 日志库

开发指南

添加新命令

  1. proxy/redis.gohandleCommand 方法中添加新的 case:
case "NEWCOMMAND":
    if len(cmd) < 2 {
        return nil, fmt.Errorf("ERR wrong number of arguments for '%s' command", cmd[0])
    }
    if s.client != nil {
        result, err = s.client.NewCommand(ctx, cmd[1]).Result()
    } else {
        result, err = s.clusterClient.NewCommand(ctx, cmd[1]).Result()
    }
  1. 确保正确处理单节点和集群模式

调试

启用详细日志:

// 在 main.go 中配置 zap logger
logger, _ := zap.NewDevelopment()
defer logger.Sync()

性能优化

  • 使用连接池管理 Redis 连接
  • 支持并发处理多个客户端连接
  • RESP 协议高效解析
  • 集群模式支持读写分离

注意事项

  1. 集群模式限制: 集群模式下,所有节点端口必须相同
  2. 数据库选择: 集群模式不支持多数据库,DB 参数将被忽略
  3. 认证: AUTH 命令总是返回 OK,实际认证由后端 Redis 处理
  4. 命令支持: 并非所有 Redis 命令都已实现,请参考支持的命令列表

故障排查

连接失败

Error creating Redis proxy: 无法连接到Redis

解决方案:

  • 检查 Redis 服务是否运行
  • 验证 REDIS_HOST 和 REDIS_PORT 配置
  • 检查网络连接和防火墙设置

集群连接失败

Error creating Redis proxy: 无法连接到Redis集群

解决方案:

  • 确认所有集群节点可访问
  • 验证集群配置正确
  • 检查集群状态: redis-cli --cluster check

命令不支持

ERR unknown command 'XXXX'

解决方案:

  • 参考支持的命令列表
  • 考虑添加新命令支持

贡献指南

欢迎提交 Issue 和 Pull Request!

  1. Fork 项目
  2. 创建特性分支 (git checkout -b feature/AmazingFeature)
  3. 提交更改 (git commit -m 'Add some AmazingFeature')
  4. 推送到分支 (git push origin feature/AmazingFeature)
  5. 开启 Pull Request

许可证

MIT License

联系方式

如有问题或建议,请提交 Issue。

更新日志

v1.0.0

  • 初始版本发布
  • 支持基本 Redis 命令
  • 支持单节点和集群模式
  • Docker 支持

About

Redis 协议转换代理

Resources

Contributing

Stars

Watchers

Forks

Releases

No releases published

Packages

No packages published

Languages

  • Go 55.9%
  • Makefile 21.0%
  • Shell 20.7%
  • Dockerfile 2.4%