通过Lettuce实现PB3格式对象在Redis中的存储与查询

1. Java实现代码(Lettuce客户端)

java 复制代码
import io.lettuce.core.RedisURI;
import io.lettuce.core.RedisClient;
import io.lettuce.core.api.sync.RedisCommands;
import com.google.protobuf.InvalidProtocolBufferException;
import your.package.UserPB; // 替换为您的PB3生成类

public class RedisStorage {
    private static final String HOST = "your-redis-host";
    private static final int PORT = 6379;
    private static final String PASSWORD = "your-password";
    private static final int DATABASE = 0;

    public static void main(String[] args) throws InvalidProtocolBufferException {
        // 创建Redis连接
        RedisURI uri = RedisURI.builder()
                .withHost(HOST)
                .withPort(PORT)
                .withPassword(PASSWORD.toCharArray())
                .withDatabase(DATABASE)
                .build();

        RedisClient client = RedisClient.create(uri);
        StatefulRedisConnection<String, byte[]> connection = client.connect(new PB3RedisCodec());
        RedisCommands<String, byte[]> sync = connection.sync();
            
            // 创建PB3对象
            UserPB.User user = UserPB.User.newBuilder()
                    .setId(1)
                    .setName("xxx")
                    .setEmail("xxx@example.com")
                    .build();
            
            // 序列化存储
            byte[] userBytes = user.toByteArray();
            sync.set("user:1", userBytes);
            
            // 查询反序列化
            byte[] storedBytes = sync.get("user:1");
            UserPB.User storedUser = UserPB.User.parseFrom(storedBytes);
            
            System.out.println("Retrieved User: " + storedUser);
					
					connection.close();
        
    }
}
  • 自定义 RedisCodec
java 复制代码
import io.lettuce.core.codec.RedisCodec;

import java.nio.ByteBuffer;

public class PB3RedisCodec implements RedisCodec<String, byte[]> {
    @Override
    public String decodeKey(ByteBuffer bytes) {
        return bytes.toString();
    }

    @Override
    public byte[] decodeValue(ByteBuffer bytes) {
        return toByteArray(bytes);
    }

    @Override
    public ByteBuffer encodeKey(String key) {
        return ByteBuffer.wrap(key.getBytes());
    }

    @Override
    public ByteBuffer encodeValue(byte[] value) {
        return ByteBuffer.wrap(value);
    }

    public static byte[] toByteArray(ByteBuffer buffer) {
        byte[] bytes = new byte[buffer.remaining()];
        buffer.get(bytes);
        buffer.rewind(); // 恢复原始状态
        return bytes;
    }
}
  • 使用连接池配置
java 复制代码
GenericObjectPool<StatefulRedisConnection<String, byte[]>> pool = 
    ConnectionPoolSupport.createGenericPool(
        () -> client.connect(new PB3RedisCodec()), 
        new GenericObjectPoolConfig()
);

2. 关键配置说明

  1. PB3序列化

    java 复制代码
    // 序列化
    byte[] data = protoObject.toByteArray();
    
    // 反序列化
    ProtoClass obj = ProtoClass.parseFrom(data);
  2. Lettuce连接池优化

    java 复制代码
    // 连接池配置
    RedisURI uri = RedisURI.builder()
            .withHost("host")
            .withPassword("pass".toCharArray())
            .withTimeout(Duration.ofSeconds(10))
            .build();
    
    RedisClient client = RedisClient.create(uri);
    StatefulRedisConnection<String, byte[]> connection = client.connect();

3. 替代方案(Python实现)

若环境限制Java使用,可使用Python方案:

python 复制代码
import redis
from user_pb2 import User  # 需先编译.proto文件

# 连接Redis Labs
r = redis.Redis(
    host='your-redis-host',
    port=6379,
    password='your-password',
    decode_responses=False
)

# 序列化存储
user = User(id=1, name="John Doe", email="john.doe@example.com")
r.set("user:1", user.SerializeToString())

# 查询反序列化
stored_bytes = r.get("user:1")
stored_user = User.FromString(stored_bytes)
print(f"Retrieved User: {stored_user}")

4. 常见问题处理

  1. 依赖安装

    bash 复制代码
    # Java项目
    <dependency>
        <groupId>io.lettuce</groupId>
        <artifactId>lettuce-core</artifactId>
        <version>6.3.0.RELEASE</version>
    </dependency>
    
    # Python项目
    pip install redis protobuf
  2. 连接问题排查

    • 检查防火墙设置(开放6379端口)
    • 验证密码正确性
    • 测试网络连通性:telnet host 6379
  3. 性能优化

    • 使用连接池(Lettuce自动管理)
    • 启用压缩选项(PB3支持)
    • 设置合理超时时间(建议10-30秒)

注意:生产环境建议:

  • 使用SSL/TLS加密连接
  • 配置Redis访问白名单
  • 启用持久化存储(RDB/AOF)
  • 监控内存使用情况(免费套餐有30MB限制)

netty中实现Protobuf协议编解码与传输
Protobuf序列化机制的核心原理
lettuce支持的redis模式

相关推荐
欢呼的太阳5 小时前
数据库设计Step by Step (10)——范式化
服务器·数据库·oracle
喜欢的名字被抢了7 小时前
MySQL基础入门:从零理解数据库与SQL
数据库·mysql·教程
Elastic 中国社区官方博客7 小时前
如何比较两个 Elasticsearch 索引并找出缺失的文档
大数据·运维·数据库·elasticsearch·搜索引擎
DLYSB_8 小时前
生命通道:如何用 HIS 医疗系统直连网络声光终端,打造“零延误”的危急值响应网关?
java·网络·数据库·报警灯
儒雅的大叔8 小时前
MySQL数据库InnoDB数据恢复工具使用总结
数据库·mysql·adb
观远数据8 小时前
ChatBI选型对比:从意图识别到SQL修复,六个维度打分决定是否值得投产
数据库·人工智能·sql
嘉&年华8 小时前
【第008篇】通过dexp和dimp命令导出和导入dmp文件(适用于达梦数据库)
数据库·sql
哥是强混10 小时前
Means:基于 .NET 10 打造的开源自部署 S3 兼容对象存储服务
网络·数据库·.net
ffqws_10 小时前
redis面试:如何保证双写一致
数据库·redis·缓存
水无痕simon10 小时前
6 数据库同义词
数据库