重点是注释的部分:
使用redis:
package com.fangdd.esf.web.server.service.impl;
import com.fangdd.esf.customercommon.protocol.Entity.search.house.HouseFilterRequest;
import com.fangdd.esf.customercommon.protocol.Entity.search.house.HouseResult;
import com.fangdd.esf.customercommon.protocol.rest.response.SearchResponse;
import com.fangdd.esf.web.server.adapter.SearchAdapter;
import com.fangdd.esf.web.server.service.EstateSearchService;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Component;
import java.util.List;
@Component
//@CacheConfig(cacheNames = "EstateSearchService")
public class EstateSearchServiceImpl implements EstateSearchService {
private static final Logger logger = LoggerFactory.getLogger(EstateSearchServiceImpl.class);
@Autowired
private SearchAdapter searchAdapter;
// @Autowired
// private RedisTemplate<String, Object> objectRedisTemplate;
@Override
//@Cacheable(key = "'sectionsEstate_'+ #filter.getCompanyId()+'_'+#filter.getCityId()+'_'+#filter.getSectionIds()", condition = "#filter.getCompanyId() != null && #filter.getCityId() != null && #filter.getSectionIds() != null",value="EstateSearchService#180#60",unless = "#result == null") //#${select.cache.timeout:1000}
public SearchResponse<HouseResult> searchHouseByFilter(HouseFilterRequest filter, Integer type) {
/*
String key="sectionsEstate_"+ filter.getCompanyId()+"_"+filter.getCityId()+"_"+filter.getSectionIds();
boolean hasKey = objectRedisTemplate.hasKey(key);
if(hasKey){
SearchResponse<HouseResult> res=new SearchResponse<HouseResult>();
//反序列化成对象
JSONObject obj=(JSONObject)objectRedisTemplate.opsForValue().get(key); //com.alibaba.fastjson.JSONObject
JSONArray jsonArray = obj.getJSONArray("records");
Long total=obj.getLong("total");
Long recommendTotal=obj.getLong("recommendTotal");
List<HouseResult> li= Lists.newArrayList();
for(int i=0;i<jsonArray.size();i++){
li.add(jsonArray.getObject(i,HouseResult.class));
}
res.setRecommendTotal(recommendTotal);
res.setRecords(li);
res.setTotal(total);
return res;
}
*/
long startTime = System.currentTimeMillis();
logger.warn("房源搜索请求开始: {}",startTime);
//搜索房源
SearchResponse<HouseResult> houseSearchResponse = searchHouseByFilter(filter);
List<HouseResult> houseList = houseSearchResponse.getRecords();
houseSearchResponse.setRecommendTotal(new Long(houseList.size()));
startTime = System.currentTimeMillis();
logger.warn("房源搜索请求结束: {}",startTime);
/*
objectRedisTemplate.opsForValue().set(key,houseSearchResponse);
this.objectRedisTemplate.expire(key,1800,TimeUnit.SECONDS); //过期时间
*/
return houseSearchResponse;
}
public SearchResponse<HouseResult> searchHouseByFilter(HouseFilterRequest filter) {
return searchAdapter.searchHouseByFilter(filter);
}
}
配置redis:
package com.fangdd.esf.web.server.configuration;
import com.alibaba.fastjson.support.spring.FastJsonRedisSerializer;
import com.fangdd.esf.web.server.utils.Settings;
import com.fasterxml.jackson.databind.DeserializationFeature;
import com.google.common.collect.ImmutableMap;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.beans.factory.annotation.Value;
import org.springframework.cache.Cache;
import org.springframework.cache.CacheManager;
import org.springframework.cache.annotation.CachingConfigurerSupport;
import org.springframework.cache.annotation.EnableCaching;
import org.springframework.cache.interceptor.CacheErrorHandler;
import org.springframework.cache.interceptor.KeyGenerator;
import org.springframework.context.annotation.Bean;
import org.springframework.context.annotation.Configuration;
import org.springframework.data.redis.cache.RedisCacheManager;
import org.springframework.data.redis.cache.RedisCachePrefix;
import org.springframework.data.redis.connection.RedisConnectionFactory;
import org.springframework.data.redis.connection.jedis.JedisConnectionFactory;
import org.springframework.data.redis.core.RedisTemplate;
import org.springframework.data.redis.core.StringRedisTemplate;
import org.springframework.data.redis.serializer.Jackson2JsonRedisSerializer;
import com.fasterxml.jackson.annotation.JsonAutoDetect;
import com.fasterxml.jackson.annotation.PropertyAccessor;
import com.fasterxml.jackson.databind.ObjectMapper;
import org.springframework.data.redis.serializer.RedisSerializer;
import org.springframework.data.redis.serializer.StringRedisSerializer;
import redis.clients.jedis.JedisPoolConfig;
@EnableCaching
@Configuration
public class RedisCacheConfig extends CachingConfigurerSupport {
private static final Logger logger = LoggerFactory.getLogger(RedisCacheConfig.class);
public static final String PREFIX = "WEBCUSTOMER";
@Autowired
Settings settings;
@Bean
@Override
public KeyGenerator keyGenerator() {
return (target, method, params) -> {
StringBuilder sb = new StringBuilder();
sb.append(target.getClass().getName());
sb.append(method.getName());
for (Object obj : params) {
sb.append(obj.toString());
}
return sb.toString();
};
}
@SuppressWarnings("rawtypes")
@Bean
public CacheManager cacheManager(RedisTemplate redisTemplate) {
RedisCacheManager cacheManager = new RedisCacheManager(redisTemplate);
String env = settings.getEnvironment();
if ("dev".equals(env) || "test".equals(env) || "pre".equals(env)) {
cacheManager.setDefaultExpiration(10);
} else {
cacheManager.setDefaultExpiration(1800);
cacheManager.setExpires(ImmutableMap.of("wechatMiniProgram", 2 * 60 * 60L));
cacheManager.setExpires(ImmutableMap.of("AgentAdapterCache", 1800L));
cacheManager.setExpires(ImmutableMap.of("AgentServiceImplCache", 2 * 60 * 60L));
cacheManager.setExpires(ImmutableMap.of("NccAdapterCache", 1800L));
cacheManager.setExpires(ImmutableMap.of("BrandBlockListInfo", 1800L));
}
cacheManager.setUsePrefix(true);
cacheManager.setCachePrefix(new CachePrefix(PREFIX, "_"));
return cacheManager;
}
@Override
public CacheErrorHandler errorHandler() {
return new CacheErrorHandler() {
@Override
public void handleCacheGetError(RuntimeException exception, Cache cache, Object key) {
logger.error("cache get error, key = {}, ex = ", key, exception);
}
@Override
public void handleCachePutError(RuntimeException exception, Cache cache, Object key, Object value) {
logger.error("cache put error, key = {}, ex = ", key, exception);
}
@Override
public void handleCacheEvictError(RuntimeException exception, Cache cache, Object key) {
logger.error("cache evict error, key = {}, ex = ", key, exception);
}
@Override
public void handleCacheClearError(RuntimeException exception, Cache cache) {
logger.error("cache clear error, ex = ", exception);
}
};
}
@SuppressWarnings({ "rawtypes", "unchecked" })
@Bean
public RedisTemplate<String, String> redisTemplate(RedisConnectionFactory factory) {
StringRedisTemplate template = new StringRedisTemplate(factory);
Jackson2JsonRedisSerializer jackson2JsonRedisSerializer = new Jackson2JsonRedisSerializer(Object.class);
ObjectMapper om = new ObjectMapper();
om.setVisibility(PropertyAccessor.ALL, JsonAutoDetect.Visibility.ANY);
om.enableDefaultTyping(ObjectMapper.DefaultTyping.NON_FINAL);
om.configure(DeserializationFeature.FAIL_ON_UNKNOWN_PROPERTIES, false);
jackson2JsonRedisSerializer.setObjectMapper(om);
template.setValueSerializer(jackson2JsonRedisSerializer);
template.afterPropertiesSet();
return template;
}
/*
@SuppressWarnings({ "rawtypes", "unchecked" })
@Bean
public RedisTemplate<String, Object> objectRedisTemplate(RedisConnectionFactory factory) {
RedisTemplate<String, Object> template = new RedisTemplate<String, Object>();
template.setConnectionFactory(factory);
template.setKeySerializer(new StringRedisSerializer());
template.setValueSerializer(new FastJsonRedisSerializer<Object>(Object.class));
//template.setValueSerializer(new Jackson2JsonRedisSerializer<Object>(Object.class));
return template;
}
*/
@Bean
public RedisConnectionFactory redisConnectionFactory(
@Value("${spring.redis.host}") String host,
@Value("${spring.redis.port}") Integer port,
@Value("${spring.redis.pool.max-idle}") Integer maxIdle,
@Value("${spring.redis.pool.max-wait}") Long maxWaitMillis,
@Value("${spring.redis.pool.max-active}") Integer maxTotal,
@Value("${spring.redis.pool.min-idle}") Integer minIdle){
JedisConnectionFactory factory = new JedisConnectionFactory();
factory.setHostName(host);
factory.setPort(port);
JedisPoolConfig config = new JedisPoolConfig();
config.setMaxIdle(maxIdle);
config.setMaxWaitMillis(maxWaitMillis);
config.setMaxTotal(maxTotal);
config.setMinIdle(minIdle);
factory.setPoolConfig(config);
return factory;
}
}
class CachePrefix implements RedisCachePrefix {
private final RedisSerializer serializer = new StringRedisSerializer();
private final String delimiter;
private final String prefix;
public CachePrefix(String prefix, String delimiter) {
this.delimiter = delimiter;
this.prefix = prefix;
}
@Override
public byte[] prefix(String cacheName) {
return serializer.serialize(String.join(delimiter, prefix, cacheName, ""));
}
}