Java 使用 RedisTemplate 从 Redis 获取设置值
声明:本页面是StackOverFlow热门问题的中英对照翻译,遵循CC BY-SA 4.0协议,如果您需要使用它,必须同样遵循CC BY-SA许可,注明原文地址和作者信息,同时你必须将它归于原作者(不是我):StackOverFlow
原文地址: http://stackoverflow.com/questions/31608394/
Warning: these are provided under cc-by-sa 4.0 license. You are free to use/share it, But you must attribute it to the original authors (not me):
StackOverFlow
Get Set value from Redis using RedisTemplate
提问by Zeeshan
I am able to retrieve values from Redis
using Jedis
:
我能够从Redis
使用中检索值Jedis
:
public static void main(String[] args) {
Jedis jedis = new Jedis(HOST, PORT);
jedis.connect();
Set<String> set = jedis.smembers(KEY);
for (String s : set) {
System.out.println(s);
}
jedis.disconnect();
jedis.close();
}
But when I am trying to use Spring's RedisTemplate
, I am not getting any data. My data is stored in Redis
as a Set
.
但是当我尝试使用 Spring 的 时RedisTemplate
,我没有得到任何数据。我的数据存储Redis
为Set
.
// inject the actual template
@Autowired
private RedisTemplate<String, Object> template;
// inject the template as SetOperations
@Resource(name="redisTemplate")
private SetOperations<String,String> setOps;
public String logHome() {
Set<String> set = setOps.members(KEY);
for(String str:set){
System.out.println(str); //EMPTY
}
Set<byte[]> keys = template.getConnectionFactory().getConnection().keys("*".getBytes());
Iterator<byte[]> it = keys.iterator();
while(it.hasNext()){
byte[] data = (byte[])it.next();
System.out.println(new String(data, 0, data.length)); //KEYS are printed.
}
Set<Object> mySet = template.boundSetOps(KEY).members();
System.out.println(mySet); //EMPTY
return "";
}
Can someone please point out to me what am I missing?
有人可以向我指出我错过了什么吗?
EDIT : My xml config for RedisTemplate.
编辑:我的 RedisTemplate xml 配置。
<bean id="redisTemplate" class="org.springframework.data.redis.core.RedisTemplate"
p:connection-factory-ref="jedisConnectionFactory"/>
<bean id="jedisConnectionFactory" class="org.springframework.data.redis.connection.jedis.JedisConnectionFactory"
p:host-name="myhostname" p:port="6379" />
采纳答案by mp911de
In short
简而言之
You have to configure serializers.
您必须配置序列化程序。
Explanation
解释
The Redis template uses serializers for keys, values and hash keys/values. Serializers are used to convert the Java input into the representation that is stored within Redis. If you do not configure anything, the serializer defaults to JdkSerializationRedisSerializer
. So if you ask for a key key
in your Java code, the serializer converts it to
Redis 模板对键、值和哈希键/值使用序列化程序。序列化程序用于将 Java 输入转换为存储在 Redis 中的表示形式。如果你没有配置任何东西,序列化器默认为JdkSerializationRedisSerializer
. 因此,如果您要求key
在 Java 代码中输入密钥,序列化程序会将其转换为
"\xac\xed\x00\x05t\x00\x03key"
and Spring Data Redis uses those bytes as the key to query Redis.
Spring Data Redis 使用这些字节作为查询 Redis 的键。
You can add data with Spring Data Redis and query it using the redis-cli
:
您可以使用 Spring Data Redis 添加数据并使用以下命令进行查询redis-cli
:
template.boundSetOps("myKey").add(new Date());
and then in the redis-cli
然后在 redis-cli
127.0.0.1:6379> keys *
1) "\xac\xed\x00\x05t\x00\x05myKey"
127.0.0.1:6379> SMEMBERS "\xac\xed\x00\x05t\x00\x05myKey"
1) "\xac\xed\x00\x05sr\x00\x0ejava.util.Datehj\x81\x01KYt\x19\x03\x00\x00xpw\b\x00\x00\x01N\xcf#\x9cHx"
As you see, the String and the Date are serialized into some crazy bytes that represent a Java-serialized object.
如您所见,字符串和日期被序列化为一些代表 Java 序列化对象的疯狂字节。
Your code suggests you want to store String-based keys and values. Just set the StringRedisSerializer
in your RedisTemplate
您的代码建议您要存储基于字符串的键和值。只需StringRedisSerializer
在您的RedisTemplate
Java configuration
Java配置
redisTemplate.setKeySerializer(new StringRedisSerializer());
redisTemplate.setValueSerializer(new StringRedisSerializer());
XML configuration
XML 配置
<bean id="stringSerializer" class="org.springframework.data.redis.serializer.StringRedisSerializer"/>
<bean id="redisTemplate" class="org.springframework.data.redis.core.RedisTemplate"
p:connection-factory-ref="jedisConnectionFactory">
<property name="keySerializer" ref="stringSerializer"/>
<property name="valueSerializer" ref="stringSerializer"/>
</bean>
<bean id="jedisConnectionFactory" class="org.springframework.data.redis.connection.jedis.JedisConnectionFactory"
p:host-name="myhostname" p:port="6379"/>
The output after running your code looks like then:
运行代码后的输出如下所示:
value
key
[value]
Spring Data Redis has some interesting serializers that allow message exchange between various systems. You can choose either from the built-in serializers
Spring Data Redis 有一些有趣的序列化器,允许不同系统之间进行消息交换。您可以从内置序列化程序中进行选择
- HymansonJsonRedisSerializer
- Hymanson2JsonRedisSerializer
- JdkSerializationRedisSerializer (default)
- OxmSerializer
- GenericToStringSerializer
- HymansonJsonRedisSerializer
- Hymanson2JsonRedisSerializer
- JdkSerializationRedisSerializer(默认)
- OxmSerializer
- GenericToStringSerializer
or create your own.
或创建自己的。
I used Spring Data Redis 1.5.1.RELEASE and jedis 2.6.2 to verify the result of your question. HTH, Mark
我使用 Spring Data Redis 1.5.1.RELEASE 和 jedis 2.6.2 来验证您的问题的结果。HTH,马克
Further read:
进一步阅读:
回答by Nikita Koksharov
You could do it much easier with Redisson:
public static void main(String[] args) {
Config conf = new Config();
conf.useSingleServer().setAddress(host + ":" + port);
RedissonClient redisson = Redisson.create(conf);
RSet<String> set = redisson.getSet(KEY)
for (String s : set.readAllValues()) {
System.out.println(s);
}
redisson.shutdown();
}
This framewrok handles serialization and work with connection so you don't need to deal with it each time. Work with Redis as you used to work with Java objects (Set, Map, List ...). It supports many popular codecs too.
这个框架处理序列化并处理连接,所以你不需要每次都处理它。像过去使用 Java 对象(Set、Map、List ...)一样使用 Redis。它也支持许多流行的编解码器。