如何使用Kafka Streams将数据写入Redis自定义状态存储

如何使用Kafka Streams将数据写入Redis自定义状态存储,redis,apache-kafka-streams,Redis,Apache Kafka Streams,我最近一直在学习如何使用Kafka Streams客户端,我一直在努力解决的一件事是如何使用Redis之类的工具从默认状态存储(RocksDB)切换到自定义状态存储。Confluent文档清楚地表明,您必须为自定义存储实现StateStore接口,并且必须提供StoreBuilder的实现以创建该存储的实例 这是我到目前为止为我的定制商店准备的东西。我还添加了一个简单的write方法,通过Redis XADD命令将新条目附加到指定的流中 公共类MyCustomStore实现了StateStore

我最近一直在学习如何使用Kafka Streams客户端,我一直在努力解决的一件事是如何使用Redis之类的工具从默认状态存储(RocksDB)切换到自定义状态存储。Confluent文档清楚地表明,您必须为自定义存储实现StateStore接口,并且必须提供StoreBuilder的实现以创建该存储的实例

这是我到目前为止为我的定制商店准备的东西。我还添加了一个简单的write方法,通过Redis XADD命令将新条目附加到指定的流中

公共类MyCustomStore实现了StateStore、MyWriteableCustomStore{ 私有字符串名称; private-volatile boolean-open=false; 私有布尔loggingEnabled=false; 公共MyCustomStore(字符串名称,已启用布尔日志){ this.name=名称; this.loggingEnabled=loggingEnabled; } @凌驾 公共字符串名称(){ 返回此.name; } @凌驾 公共void init(ProcessorContext上下文,StateStore根){ if(root!=null){ //注册商店 寄存器(根,(键,值)->{ 写入(key.toString(),value.toString()); }); } this.open=true; } @凌驾 公共图书馆{ //TODO自动生成的方法存根 } @凌驾 公众假期结束(){ //TODO自动生成的方法存根 } @凌驾 公共布尔持久(){ //TODO自动生成的方法存根 返回true; } @凌驾 公共布尔等参元(){ //TODO自动生成的方法存根 返回false; } @凌驾 公共无效写入(字符串键、字符串值){ 试一试(绝地=新绝地(“本地主机”,6379)){ Map hash=new HashMap(); hash.put(键、值); jedis.xadd(“MyStream”,StreamEntryID.NEW_ENTRY,hash); } } }
公共类MyCustomStoreBuilder实现StoreBuilder{
私有布尔缓存=真;
私有字符串名称;
私有映射logConfig=newhashmap();
启用私有布尔日志;
public MyCustomStoreBuilder(字符串名称,已启用布尔日志){
this.name=名称;
this.loggingEnabled=loggingEnabled;
}
@凌驾
使用cachinegabled()的公共存储生成器{
this.cached=true;
归还这个;
}
@凌驾
带有cachingdisabled()的公共存储生成器{
this.cached=false;
返回null;
}
@凌驾
启用日志的公共存储生成器(映射配置){
loggingEnabled=true;
归还这个;
}
@凌驾
禁用日志的公共存储生成器(){
this.loggingEnabled=false;
归还这个;
}
@凌驾
公共MyCustomStore构建(){
返回新的MyCustomStore(this.name,this.loggingEnabled);
}
@凌驾
公共映射logConfig(){
返回logConfig;
}
@凌驾
公共布尔日志已启用(){
返回日志已启用;
}
@凌驾
公共字符串名称(){
返回名称;
}
}
下面是我的设置和拓扑结构

@Bean
公共卡夫卡斯特团队卡夫卡斯特团队(卡夫卡不勒斯卡夫卡不勒斯){
最终属性道具=新属性();
put(StreamsConfig.BOOTSTRAP_SERVERS_CONFIG,kafkaProperties.getbootstrapserver());
put(StreamsConfig.APPLICATION\u ID\u CONFIG,appName);
put(AbstractKafkschemaserdeconfig.SCHEMA\u REGISTRY\u URL\u CONFIG,schemaRegistryUrl);
put(StreamsConfig.DEFAULT_KEY_SERDE_CLASS_CONFIG,Long().getClass());
put(StreamsConfig.DEFAULT_VALUE_SERDE_CLASS_CONFIG,Double().getClass());
props.put(StreamsConfig.STATE_DIR_CONFIG,“数据”);
put(StreamsConfig.APPLICATION\u SERVER\u CONFIG,appServerConfig);
put(JsonDeserializer.VALUE\u DEFAULT\u类型,JsonNode.class);
put(默认的\u反序列化\u异常\u处理程序\u类\u配置,LogAndContinueExceptionHandler.CLASS);
props.put(ConsumerConfig.AUTO_OFFSET_RESET_CONFIG,“最早”);
最后一个字符串storeName=“客户商店”;
拓扑=新拓扑();
//为自定义门店的门店名称创建CustomStoreSupplier
MyCustomStoreBuilder customStoreBuilder=新的MyCustomStoreBuilder(storeName,false);
topology.addSource(“输入”、“输入选项”);
topology.addProcessor(“redis processor”,()->new RedisProcessor(storeName),“input”);
addStateStore(customStoreBuilder,“redis处理器”);
KafkaStreams KafkaStreams=新的KafkaStreams(拓扑、道具);
kafkaStreams.start();
返回卡夫卡斯特团队;
}
公共类MyCustomStoreType实现QueryableStoreType{
@凌驾
公共布尔接受(StateStore StateStore){
返回MyCustomStore的stateStore实例;
}
@凌驾
公共MyReadableCustomStore创建(最终状态storeProvider storeProvider,最终字符串storeName){
返回新的MyCustomStoreTypeWrapper(storeProvider、storeName、this);
}
}
公共类MyCustomStoreTypeWrapper实现MyReadableCustomStore{
私有最终QueryableStoreType customStoreType;
私有最终字符串storeName;
私人最终状态存储提供程序;
公共MyCustomStoreTypeWrapper(最终状态存储提供程序,
最终字符串storeName,
最终QueryableStoreType(customStoreType){
this.provider=提供者;
this.storeName=storeName;
this.customStoreType=customStoreType;
}
@凌驾
公共字符串读取(字符串键){
试一试(绝地=新绝地(“本地主机”,6379)){