Authored by hugufei

缓存代码优化

@@ -7,7 +7,8 @@ import com.yoho.search.base.utils.ProductIndexEsField; @@ -7,7 +7,8 @@ import com.yoho.search.base.utils.ProductIndexEsField;
7 import com.yoho.search.core.es.model.SearchParam; 7 import com.yoho.search.core.es.model.SearchParam;
8 import com.yoho.search.core.es.model.SearchResult; 8 import com.yoho.search.core.es.model.SearchResult;
9 import com.yoho.search.models.SearchApiResult; 9 import com.yoho.search.models.SearchApiResult;
10 -import com.yoho.search.recall.scene.beans.BacthSknInfoComponent; 10 +import com.yoho.search.recall.scene.beans.CacheRecallSknRequestResponseBean;
  11 +import com.yoho.search.recall.scene.beans.CacheSknInfoRequestResponseBean;
11 import com.yoho.search.recall.scene.strategy.helper.SortBuilderHelper; 12 import com.yoho.search.recall.scene.strategy.helper.SortBuilderHelper;
12 import com.yoho.search.recall.scene.models.*; 13 import com.yoho.search.recall.scene.models.*;
13 import com.yoho.search.recall.scene.builder.request.RecallParamsBuilder; 14 import com.yoho.search.recall.scene.builder.request.RecallParamsBuilder;
@@ -42,10 +43,9 @@ public class SceneRecallService { @@ -42,10 +43,9 @@ public class SceneRecallService {
42 @Autowired 43 @Autowired
43 private SearchCommonService searchCommonService; 44 private SearchCommonService searchCommonService;
44 @Autowired 45 @Autowired
45 - private BacthSknInfoComponent bacthSknInfoComponent; 46 + private CacheRecallSknRequestResponseBean cacheRecallSknRequestResponseBean;
46 @Autowired 47 @Autowired
47 - private RecallService recallService;  
48 - 48 + private CacheSknInfoRequestResponseBean cacheSknInfoRequestResponseBean;
49 49
50 public SearchApiResult sceneRecall(Map<String, String> paramMap) { 50 public SearchApiResult sceneRecall(Map<String, String> paramMap) {
51 try { 51 try {
@@ -58,7 +58,7 @@ public class SceneRecallService { @@ -58,7 +58,7 @@ public class SceneRecallService {
58 //2、构造召回相关参数 58 //2、构造召回相关参数
59 RecallSknParams recallSknParams = recallParamsBuilder.buildRecallParams(paramMap,pageSize); 59 RecallSknParams recallSknParams = recallParamsBuilder.buildRecallParams(paramMap,pageSize);
60 //3、执行召回 60 //3、执行召回
61 - RecallSknResult recallSknResult = recallService.doRecallSknResult(recallSknParams); 61 + RecallSknResult recallSknResult = cacheRecallSknRequestResponseBean.doRecallSknResult(recallSknParams);
62 //4、根据召回结果查询商品信息 62 //4、根据召回结果查询商品信息
63 List<Map<String, Object>> productList = this.queryProductList(recallSknParams,recallSknResult,page,pageSize); 63 List<Map<String, Object>> productList = this.queryProductList(recallSknParams,recallSknResult,page,pageSize);
64 //5、构造返回结果 64 //5、构造返回结果
@@ -86,7 +86,7 @@ public class SceneRecallService { @@ -86,7 +86,7 @@ public class SceneRecallService {
86 //3、过滤召回的skn,修改真实页码,执行查询 86 //3、过滤召回的skn,修改真实页码,执行查询
87 productSkns = this.queryProductSknByFilterSkn(recallSknParams, recallSknResult.getSknList(), recallTotalPage-page, pageSize); 87 productSkns = this.queryProductSknByFilterSkn(recallSknParams, recallSknResult.getSknList(), recallTotalPage-page, pageSize);
88 } 88 }
89 - return bacthSknInfoComponent.queryProductListBySkn(productSkns,productSkns.size()); 89 + return cacheSknInfoRequestResponseBean.queryProductListBySkn(productSkns,productSkns.size());
90 } 90 }
91 91
92 /** 92 /**
1 -package com.yoho.search.recall.scene.cache; 1 +package com.yoho.search.recall.scene.beans;
2 2
3 import com.alibaba.fastjson.JSON; 3 import com.alibaba.fastjson.JSON;
4 import com.yoho.core.redis.cluster.operations.serializer.RedisKeyBuilder; 4 import com.yoho.core.redis.cluster.operations.serializer.RedisKeyBuilder;
@@ -5,9 +5,10 @@ import com.yoho.search.base.utils.ProductIndexEsField; @@ -5,9 +5,10 @@ import com.yoho.search.base.utils.ProductIndexEsField;
5 import com.yoho.search.core.es.model.SearchParam; 5 import com.yoho.search.core.es.model.SearchParam;
6 import com.yoho.search.core.es.model.SearchResult; 6 import com.yoho.search.core.es.model.SearchResult;
7 import com.yoho.search.recall.scene.cache.CacheRequestResponseComponent; 7 import com.yoho.search.recall.scene.cache.CacheRequestResponseComponent;
8 -import com.yoho.search.recall.scene.cache.CacheRecallRequestResponse;  
9 import com.yoho.search.recall.scene.models.RecallRequest; 8 import com.yoho.search.recall.scene.models.RecallRequest;
10 import com.yoho.search.recall.scene.models.RecallResponse; 9 import com.yoho.search.recall.scene.models.RecallResponse;
  10 +import com.yoho.search.recall.scene.models.RecallSknParams;
  11 +import com.yoho.search.recall.scene.models.RecallSknResult;
11 import com.yoho.search.service.base.SearchCommonService; 12 import com.yoho.search.service.base.SearchCommonService;
12 import org.apache.commons.collections.MapUtils; 13 import org.apache.commons.collections.MapUtils;
13 import org.slf4j.Logger; 14 import org.slf4j.Logger;
@@ -21,17 +22,11 @@ import java.util.List; @@ -21,17 +22,11 @@ import java.util.List;
21 import java.util.Map; 22 import java.util.Map;
22 23
23 @Component 24 @Component
24 -public class BatchRecallComponent { 25 +public class CacheRecallRequestResponseBean extends CacheRequestResponseComponent<RecallRequest,RecallResponse,CacheRecallRequestResponse>{
25 26
26 - private static final Logger logger = LoggerFactory.getLogger(BatchRecallComponent.class);  
27 -  
28 - @Autowired  
29 - private CacheRequestResponseComponent cacheRequestResponseHelper;  
30 @Autowired 27 @Autowired
31 private SearchCommonService searchCommonService; 28 private SearchCommonService searchCommonService;
32 29
33 - private static final boolean useEhCache = false;  
34 -  
35 /** 30 /**
36 * 批量召回入口 31 * 批量召回入口
37 * 32 *
@@ -39,55 +34,34 @@ public class BatchRecallComponent { @@ -39,55 +34,34 @@ public class BatchRecallComponent {
39 * @return 34 * @return
40 */ 35 */
41 public List<CacheRecallRequestResponse> batchRecallAndCache(final List<RecallRequest> batchRequests) { 36 public List<CacheRecallRequestResponse> batchRecallAndCache(final List<RecallRequest> batchRequests) {
42 - //1、构造返回结果  
43 - final List<CacheRecallRequestResponse> recallRequestResponses = new ArrayList<>(); 37 + //1、构造请求
  38 + final List<CacheRecallRequestResponse> results = new ArrayList<>();
44 for (RecallRequest request : batchRequests) { 39 for (RecallRequest request : batchRequests) {
45 - recallRequestResponses.add(new CacheRecallRequestResponse(request)); 40 + results.add(new CacheRecallRequestResponse(request));
46 } 41 }
47 - //2、先从缓存中填充response  
48 - cacheRequestResponseHelper.batchFillResponseFromCache(recallRequestResponses,useEhCache);  
49 -  
50 - //3、构造未命中缓存的请求-最多透传x个  
51 - final List<CacheRecallRequestResponse> missCacheRequests =cacheRequestResponseHelper.filterMissCacheRequests(recallRequestResponses);  
52 -  
53 - //4、如果remainRequests为空,则说明全部命中了缓存,直接返回即可  
54 - if (missCacheRequests.isEmpty()) {  
55 - return recallRequestResponses;  
56 - }  
57 -  
58 - //5、处理剩余请求  
59 - Map<String,RecallResponse> notCacheResults = this.queryNotCachedResult(missCacheRequests);  
60 -  
61 - //6、填充recallRequestResponses  
62 - cacheRequestResponseHelper.batchFillResponseWithQueryResults(recallRequestResponses,notCacheResults);  
63 -  
64 - //7、将尚未缓存的对象加入缓存  
65 - cacheRequestResponseHelper.batchAddResponseToCache(recallRequestResponses,useEhCache);  
66 -  
67 - return recallRequestResponses; 42 + //2、执行查询
  43 + this.bacthFillResponseWithCache(results,false);
68 44
  45 + //3、返回结果
  46 + return results;
69 } 47 }
70 48
71 - /**  
72 - * 查询命中缓存的请求  
73 - * @param notCachedRequests  
74 - * @return  
75 - */  
76 - private Map<String,RecallResponse> queryNotCachedResult(List<CacheRecallRequestResponse> notCachedRequests) { 49 + @Override
  50 + public Map<RecallRequest, RecallResponse> queryMissCacheRequestResults(List<CacheRecallRequestResponse> missCacheRequests) {
77 //1、构造请求参数 51 //1、构造请求参数
78 List<SearchParam> searchParams = new ArrayList<>(); 52 List<SearchParam> searchParams = new ArrayList<>();
79 - for (CacheRecallRequestResponse requestResponse : notCachedRequests) { 53 + for (CacheRecallRequestResponse requestResponse : missCacheRequests) {
80 searchParams.add(requestResponse.getRequest().searchParam()); 54 searchParams.add(requestResponse.getRequest().searchParam());
81 } 55 }
82 //2、执行搜索 56 //2、执行搜索
83 List<SearchResult> searchResults = searchCommonService.doMutiSearch(ISearchConstants.INDEX_NAME_PRODUCT_INDEX, searchParams); 57 List<SearchResult> searchResults = searchCommonService.doMutiSearch(ISearchConstants.INDEX_NAME_PRODUCT_INDEX, searchParams);
84 //3、构造返回结果 58 //3、构造返回结果
85 - Map<String,RecallResponse> notCachedResults = new HashMap<>();  
86 - for (int i = 0; i < notCachedRequests.size(); i++) {  
87 - RecallRequest request = notCachedRequests.get(i).getRequest(); 59 + Map<RecallRequest,RecallResponse> notCachedResults = new HashMap<>();
  60 + for (int i = 0; i < missCacheRequests.size(); i++) {
  61 + RecallRequest request = missCacheRequests.get(i).getRequest();
88 SearchResult searchResult = searchResults.get(i); 62 SearchResult searchResult = searchResults.get(i);
89 RecallResponse response = this.buildResonse(searchResult); 63 RecallResponse response = this.buildResonse(searchResult);
90 - notCachedResults.put(request.redisKeyBuilder().getKey(),response); 64 + notCachedResults.put(request,response);
91 } 65 }
92 return notCachedResults; 66 return notCachedResults;
93 } 67 }
1 -package com.yoho.search.recall.scene.cache; 1 +package com.yoho.search.recall.scene.beans;
2 2
3 import com.alibaba.fastjson.JSON; 3 import com.alibaba.fastjson.JSON;
4 import com.yoho.search.base.utils.Transfer; 4 import com.yoho.search.base.utils.Transfer;
1 -package com.yoho.search.recall.scene; 1 +package com.yoho.search.recall.scene.beans;
2 2
3 import com.yoho.search.recall.scene.builder.request.BrandRecallRequestBuilder; 3 import com.yoho.search.recall.scene.builder.request.BrandRecallRequestBuilder;
4 import com.yoho.search.recall.scene.builder.request.CommonRecallRequestBuilder; 4 import com.yoho.search.recall.scene.builder.request.CommonRecallRequestBuilder;
5 import com.yoho.search.recall.scene.builder.request.SortPriceRecallRequestBuilder; 5 import com.yoho.search.recall.scene.builder.request.SortPriceRecallRequestBuilder;
6 import com.yoho.search.recall.scene.builder.response.RecallResponseBatchBuilder; 6 import com.yoho.search.recall.scene.builder.response.RecallResponseBatchBuilder;
7 import com.yoho.search.recall.scene.builder.response.RecallSknResultBuilder; 7 import com.yoho.search.recall.scene.builder.response.RecallSknResultBuilder;
8 -import com.yoho.search.recall.scene.cache.CacheRecallRequestResponse;  
9 -import com.yoho.search.recall.scene.beans.BatchRecallComponent;  
10 -import com.yoho.search.recall.scene.models.*; 8 +import com.yoho.search.recall.scene.cache.CacheRequestResponseComponent;
  9 +import com.yoho.search.recall.scene.models.RecallRequest;
11 import com.yoho.search.recall.scene.models.RecallResponseBatch; 10 import com.yoho.search.recall.scene.models.RecallResponseBatch;
  11 +import com.yoho.search.recall.scene.models.RecallSknParams;
  12 +import com.yoho.search.recall.scene.models.RecallSknResult;
12 import com.yoho.search.recall.scene.persional.PersionalFactor; 13 import com.yoho.search.recall.scene.persional.PersionalFactor;
13 import com.yoho.search.recall.scene.persional.RecallPersionalService; 14 import com.yoho.search.recall.scene.persional.RecallPersionalService;
14 import org.springframework.beans.factory.annotation.Autowired; 15 import org.springframework.beans.factory.annotation.Autowired;
15 import org.springframework.stereotype.Component; 16 import org.springframework.stereotype.Component;
16 17
17 import java.util.ArrayList; 18 import java.util.ArrayList;
  19 +import java.util.HashMap;
18 import java.util.List; 20 import java.util.List;
  21 +import java.util.Map;
19 22
20 @Component 23 @Component
21 -public class RecallService { 24 +public class CacheRecallSknRequestResponseBean extends CacheRequestResponseComponent<RecallSknParams,RecallSknResult,CacheRecallSknRequestResponse>{
22 25
23 @Autowired 26 @Autowired
24 private RecallPersionalService recallPersionalService; 27 private RecallPersionalService recallPersionalService;
25 @Autowired 28 @Autowired
26 - private BatchRecallComponent bacthRecallComponent; 29 + private CacheRecallRequestResponseBean bacthRecallComponent;
27 @Autowired 30 @Autowired
28 private RecallResponseBatchBuilder recallResponseBatchBuilder; 31 private RecallResponseBatchBuilder recallResponseBatchBuilder;
29 @Autowired 32 @Autowired
@@ -35,17 +38,42 @@ public class RecallService { @@ -35,17 +38,42 @@ public class RecallService {
35 @Autowired 38 @Autowired
36 private SortPriceRecallRequestBuilder sortPriceRequestBuilder; 39 private SortPriceRecallRequestBuilder sortPriceRequestBuilder;
37 40
  41 + /**
  42 + * 召回入口
  43 + * @param recallSknParams
  44 + * @return
  45 + */
38 public RecallSknResult doRecallSknResult(RecallSknParams recallSknParams){ 46 public RecallSknResult doRecallSknResult(RecallSknParams recallSknParams){
39 - RecallSknResult recallSknResult = this.doRecall(recallSknParams);  
40 - return recallSknResult; 47 + //1、构建请求
  48 + List<CacheRecallSknRequestResponse> requests = new ArrayList<>();
  49 + requests.add(new CacheRecallSknRequestResponse(recallSknParams));
  50 +
  51 + //2、执行父类方法
  52 + this.bacthFillResponseWithCache(requests,true);
  53 +
  54 + //3、判断
  55 + if(requests.size()==1 && requests.get(0).getResponse()!=null){
  56 + return requests.get(0).getResponse();
  57 + }
  58 + return null;
  59 + }
  60 +
  61 + @Override
  62 + public Map<RecallSknParams, RecallSknResult> queryMissCacheRequestResults(List<CacheRecallSknRequestResponse> missCachseRequests) {
  63 + Map<RecallSknParams, RecallSknResult> results = new HashMap<>();
  64 + for (CacheRecallSknRequestResponse request: missCachseRequests) {
  65 + RecallSknResult response = this.doRealRecall(request.getRequest());
  66 + results.put(request.getRequest(),response);
  67 + }
  68 + return results;
41 } 69 }
42 70
43 /** 71 /**
44 - * 召回入口 72 + * 真正的召回入口
45 * @param param 73 * @param param
46 * @return 74 * @return
47 */ 75 */
48 - private RecallSknResult doRecall(RecallSknParams param) { 76 + private RecallSknResult doRealRecall(RecallSknParams param) {
49 //1、获取个性化因子 77 //1、获取个性化因子
50 PersionalFactor persionalFactor = recallPersionalService.queryPersionalFactor(param); 78 PersionalFactor persionalFactor = recallPersionalService.queryPersionalFactor(param);
51 //2、构造请求 79 //2、构造请求
@@ -65,7 +93,7 @@ public class RecallService { @@ -65,7 +93,7 @@ public class RecallService {
65 * @param persionalFactor 93 * @param persionalFactor
66 * @return 94 * @return
67 */ 95 */
68 - public List<RecallRequest> buildBatchRequests(RecallSknParams param, PersionalFactor persionalFactor) { 96 + private List<RecallRequest> buildBatchRequests(RecallSknParams param, PersionalFactor persionalFactor) {
69 //1、构造召回请求 97 //1、构造召回请求
70 List<RecallRequest> allRequests = new ArrayList<>(); 98 List<RecallRequest> allRequests = new ArrayList<>();
71 //2、构造非个性化的请求 99 //2、构造非个性化的请求
@@ -80,4 +108,5 @@ public class RecallService { @@ -80,4 +108,5 @@ public class RecallService {
80 return allRequests; 108 return allRequests;
81 } 109 }
82 110
  111 +
83 } 112 }
1 -package com.yoho.search.recall.scene.cache; 1 +package com.yoho.search.recall.scene.beans;
2 2
3 import com.alibaba.fastjson.JSON; 3 import com.alibaba.fastjson.JSON;
4 import com.alibaba.fastjson.JSONObject; 4 import com.alibaba.fastjson.JSONObject;
@@ -6,7 +6,8 @@ import com.yoho.search.base.utils.ProductIndexEsField; @@ -6,7 +6,8 @@ import com.yoho.search.base.utils.ProductIndexEsField;
6 import com.yoho.search.core.es.model.SearchParam; 6 import com.yoho.search.core.es.model.SearchParam;
7 import com.yoho.search.core.es.model.SearchResult; 7 import com.yoho.search.core.es.model.SearchResult;
8 import com.yoho.search.recall.scene.cache.CacheRequestResponseComponent; 8 import com.yoho.search.recall.scene.cache.CacheRequestResponseComponent;
9 -import com.yoho.search.recall.scene.cache.CacheSknInfoRequestResponse; 9 +import com.yoho.search.recall.scene.models.RecallSknParams;
  10 +import com.yoho.search.recall.scene.models.RecallSknResult;
10 import com.yoho.search.recall.scene.models.SknInfoRequest; 11 import com.yoho.search.recall.scene.models.SknInfoRequest;
11 import com.yoho.search.service.base.SearchCommonService; 12 import com.yoho.search.service.base.SearchCommonService;
12 import com.yoho.search.service.base.index.ProductIndexBaseService; 13 import com.yoho.search.service.base.index.ProductIndexBaseService;
@@ -21,16 +22,12 @@ import java.util.List; @@ -21,16 +22,12 @@ import java.util.List;
21 import java.util.Map; 22 import java.util.Map;
22 23
23 @Component 24 @Component
24 -public class BacthSknInfoComponent { 25 +public class CacheSknInfoRequestResponseBean extends CacheRequestResponseComponent<SknInfoRequest,Map<String, Object>,CacheSknInfoRequestResponse>{
25 26
26 @Autowired 27 @Autowired
27 private SearchCommonService searchCommonService; 28 private SearchCommonService searchCommonService;
28 @Autowired 29 @Autowired
29 private ProductIndexBaseService productIndexBaseService; 30 private ProductIndexBaseService productIndexBaseService;
30 - @Autowired  
31 - private CacheRequestResponseComponent cacheRequestResponseComponent;  
32 -  
33 - private static final boolean useEhCache = true;  
34 31
35 /** 32 /**
36 * 按skn查询并按顺序返回 33 * 按skn查询并按顺序返回
@@ -56,32 +53,27 @@ public class BacthSknInfoComponent { @@ -56,32 +53,27 @@ public class BacthSknInfoComponent {
56 53
57 private List<CacheSknInfoRequestResponse> batchQuery(List<Integer> productSkns){ 54 private List<CacheSknInfoRequestResponse> batchQuery(List<Integer> productSkns){
58 //1、构建请求与返回结果 55 //1、构建请求与返回结果
59 - final List<CacheSknInfoRequestResponse> sknInfoCacheRequestRespons = new ArrayList<>(); 56 + final List<CacheSknInfoRequestResponse> requests = new ArrayList<>();
60 for (Integer productSkn : productSkns) { 57 for (Integer productSkn : productSkns) {
61 - sknInfoCacheRequestRespons.add(new CacheSknInfoRequestResponse(new SknInfoRequest(productSkn))); 58 + requests.add(new CacheSknInfoRequestResponse(new SknInfoRequest(productSkn)));
62 } 59 }
63 - //2、批量从缓存中获取  
64 - cacheRequestResponseComponent.batchFillResponseFromCache(sknInfoCacheRequestRespons,useEhCache);  
65 - //3、获取未命中缓存的请求  
66 - List<CacheSknInfoRequestResponse> missCacheRequests = cacheRequestResponseComponent.filterMissCacheRequests(sknInfoCacheRequestRespons);  
67 - //4、执行批量查询  
68 - Map<String,Map<String, Object>> queryResults = this.batchQueryMissCacheRequests(missCacheRequests);  
69 - //5、填充查询结果  
70 - cacheRequestResponseComponent.batchFillResponseWithQueryResults(sknInfoCacheRequestRespons,queryResults);  
71 - //6、将CacheRequestResponse中需要缓存的key加入缓存  
72 - cacheRequestResponseComponent.batchAddResponseToCache(sknInfoCacheRequestRespons,useEhCache);  
73 - return sknInfoCacheRequestRespons; 60 + //2、调父类方法
  61 + this.bacthFillResponseWithCache(requests,true);
  62 +
  63 + //3、返回结果
  64 + return requests;
74 } 65 }
75 66
76 - private Map<String,Map<String, Object>> batchQueryMissCacheRequests(List<CacheSknInfoRequestResponse> notCachedRequestResponse) { 67 + @Override
  68 + public Map<SknInfoRequest, Map<String, Object>> queryMissCacheRequestResults(List<CacheSknInfoRequestResponse> missCacheRequests) {
77 //1、合法性判断 69 //1、合法性判断
78 - Map<String,Map<String, Object>> results = new HashMap<>();  
79 - if(notCachedRequestResponse==null||notCachedRequestResponse.isEmpty()){ 70 + Map<SknInfoRequest,Map<String, Object>> results = new HashMap<>();
  71 + if(missCacheRequests==null||missCacheRequests.isEmpty()){
80 return results; 72 return results;
81 } 73 }
82 //2、获取skn 74 //2、获取skn
83 List<Integer> productSkns = new ArrayList<>(); 75 List<Integer> productSkns = new ArrayList<>();
84 - for (CacheSknInfoRequestResponse sknInfoCacheRequestResponse : notCachedRequestResponse) { 76 + for (CacheSknInfoRequestResponse sknInfoCacheRequestResponse : missCacheRequests) {
85 productSkns.add(sknInfoCacheRequestResponse.getRequest().getProductSkn()); 77 productSkns.add(sknInfoCacheRequestResponse.getRequest().getProductSkn());
86 } 78 }
87 //3、构建SearchParam 79 //3、构建SearchParam
@@ -98,11 +90,15 @@ public class BacthSknInfoComponent { @@ -98,11 +90,15 @@ public class BacthSknInfoComponent {
98 productTempMap.put(MapUtils.getIntValue(product,"product_skn",0),product); 90 productTempMap.put(MapUtils.getIntValue(product,"product_skn",0),product);
99 } 91 }
100 //5、构造最终结果 92 //5、构造最终结果
101 - for (CacheSknInfoRequestResponse requestResponse :notCachedRequestResponse ) {  
102 - results.put(requestResponse.getRequest().redisKeyBuilder().getKey(),productTempMap.get(requestResponse.getRequest().getProductSkn())); 93 + for (CacheSknInfoRequestResponse requestResponse :missCacheRequests ) {
  94 + results.put(requestResponse.getRequest(),productTempMap.get(requestResponse.getRequest().getProductSkn()));
103 } 95 }
104 return results; 96 return results;
105 } 97 }
106 98
107 99
  100 +
  101 +
  102 +
  103 +
108 } 104 }
1 -package com.yoho.search.recall.scene.beans;  
2 -  
3 -public class RecallSknComponent {  
4 -}  
1 package com.yoho.search.recall.scene.builder.response; 1 package com.yoho.search.recall.scene.builder.response;
2 2
3 -import com.yoho.search.recall.scene.cache.CacheRecallRequestResponse; 3 +import com.yoho.search.recall.scene.beans.CacheRecallRequestResponse;
4 import com.yoho.search.recall.scene.models.RecallRequest; 4 import com.yoho.search.recall.scene.models.RecallRequest;
5 import com.yoho.search.recall.scene.models.RecallResponse; 5 import com.yoho.search.recall.scene.models.RecallResponse;
6 import com.yoho.search.recall.scene.models.RecallResponseBatch; 6 import com.yoho.search.recall.scene.models.RecallResponseBatch;
@@ -5,6 +5,7 @@ import com.yoho.search.base.utils.CollectionUtils; @@ -5,6 +5,7 @@ import com.yoho.search.base.utils.CollectionUtils;
5 import com.yoho.search.base.utils.Transfer; 5 import com.yoho.search.base.utils.Transfer;
6 import com.yoho.search.common.cache.impls.EhCache; 6 import com.yoho.search.common.cache.impls.EhCache;
7 import com.yoho.search.core.redis.components.YohoSearchRedisComponent; 7 import com.yoho.search.core.redis.components.YohoSearchRedisComponent;
  8 +import com.yoho.search.recall.scene.beans.CacheSknInfoRequestResponse;
8 import org.apache.commons.lang.StringUtils; 9 import org.apache.commons.lang.StringUtils;
9 import org.slf4j.Logger; 10 import org.slf4j.Logger;
10 import org.slf4j.LoggerFactory; 11 import org.slf4j.LoggerFactory;
@@ -13,8 +14,7 @@ import org.springframework.stereotype.Component; @@ -13,8 +14,7 @@ import org.springframework.stereotype.Component;
13 14
14 import java.util.*; 15 import java.util.*;
15 16
16 -@Component  
17 -public class CacheRequestResponseComponent { 17 +public abstract class CacheRequestResponseComponent<K extends ICacheRequest, V,T extends CacheRequestResponse<K, V>> {
18 18
19 private static final Logger logger = LoggerFactory.getLogger(CacheRequestResponseComponent.class); 19 private static final Logger logger = LoggerFactory.getLogger(CacheRequestResponseComponent.class);
20 20
@@ -24,14 +24,35 @@ public class CacheRequestResponseComponent { @@ -24,14 +24,35 @@ public class CacheRequestResponseComponent {
24 private EhCache ehCache; 24 private EhCache ehCache;
25 25
26 /** 26 /**
27 - * 从缓存中获取response 27 + * 批量处理请求,以及添加缓存
  28 + *
  29 + * @param requests
  30 + * @param useEhCache
  31 + * @return
  32 + */
  33 + public void bacthFillResponseWithCache(final List<T> requests, boolean useEhCache) {
  34 + //1、批量从缓存中获取
  35 + this.batchFillResponseFromCache(requests, useEhCache);
  36 + //2、获取未命中缓存的请求
  37 + List<T> missCacheRequests = this.filterMissCacheRequests(requests);
  38 + //3、如果remainRequests为空,则说明全部命中了缓存,直接返回即可
  39 + if (missCacheRequests.isEmpty()) {
  40 + return ;
  41 + }
  42 + //4、处理请求
  43 + Map<K, V> requestResponseMap = this.queryMissCacheRequestResults(missCacheRequests);
  44 + //5、填充查询结果
  45 + this.batchFillResponseWithQueryResults(requests, requestResponseMap);
  46 + //6、将CacheRequestResponse中需要缓存的key加入缓存
  47 + this.batchAddResponseToCache(requests, useEhCache);
  48 + }
  49 +
  50 + /**
  51 + * 从缓存中批量填充response
28 * @param cacheRequestResponses 52 * @param cacheRequestResponses
29 * @param useEhCache 53 * @param useEhCache
30 - * @param <K>  
31 - * @param <V>  
32 - * @param <T>  
33 */ 54 */
34 - public <K extends ICacheRequest, V, T extends CacheRequestResponse<K, V>> void batchFillResponseFromCache(final List<T> cacheRequestResponses, boolean useEhCache) { 55 + private void batchFillResponseFromCache(final List<T> cacheRequestResponses, boolean useEhCache) {
35 try { 56 try {
36 Collection<RedisKeyBuilder> keys = new ArrayList<>(); 57 Collection<RedisKeyBuilder> keys = new ArrayList<>();
37 for (T requestResponse : cacheRequestResponses) { 58 for (T requestResponse : cacheRequestResponses) {
@@ -55,15 +76,12 @@ public class CacheRequestResponseComponent { @@ -55,15 +76,12 @@ public class CacheRequestResponseComponent {
55 /** 76 /**
56 * 过滤出未命中缓存的结果 77 * 过滤出未命中缓存的结果
57 * @param cacheRequestResponses 78 * @param cacheRequestResponses
58 - * @param <K>  
59 - * @param <V>  
60 - * @param <T>  
61 * @return 79 * @return
62 */ 80 */
63 - public <K extends ICacheRequest, V, T extends CacheRequestResponse<K, V>> List<T> filterMissCacheRequests(List<T> cacheRequestResponses){ 81 + private List<T> filterMissCacheRequests(List<T> cacheRequestResponses) {
64 List<T> notCachedRequests = new ArrayList<>(); 82 List<T> notCachedRequests = new ArrayList<>();
65 for (T requestResponse : cacheRequestResponses) { 83 for (T requestResponse : cacheRequestResponses) {
66 - if (requestResponse != null && requestResponse.getResponse()==null) { 84 + if (requestResponse != null && requestResponse.getResponse() == null) {
67 notCachedRequests.add(requestResponse); 85 notCachedRequests.add(requestResponse);
68 } 86 }
69 } 87 }
@@ -71,22 +89,33 @@ public class CacheRequestResponseComponent { @@ -71,22 +89,33 @@ public class CacheRequestResponseComponent {
71 } 89 }
72 90
73 /** 91 /**
74 - * 使用查询结果填充response 92 + * 处理未命中缓存的请求-子类实现
  93 + *
  94 + * @param missCacheRequests
  95 + * @return
  96 + */
  97 + public abstract Map<K, V> queryMissCacheRequestResults(List<T> missCacheRequests);
  98 +
  99 + /**
  100 + * 使用查询结果填充请求-转成String
75 * @param cacheRequestResponses 101 * @param cacheRequestResponses
76 * @param queryResults 102 * @param queryResults
77 - * @param <K>  
78 - * @param <V>  
79 - * @param <T>  
80 */ 103 */
81 - public <K extends ICacheRequest, V, T extends CacheRequestResponse<K, V>> void batchFillResponseWithQueryResults(List<T> cacheRequestResponses,Map<String,V> queryResults){ 104 + private void batchFillResponseWithQueryResults(List<T> cacheRequestResponses, Map<K, V> queryResults) {
  105 + //1、先转成map
  106 + Map<String, V> toCacheResults = new HashMap<>();
  107 + for (Map.Entry<K, V> entry : queryResults.entrySet()) {
  108 + toCacheResults.put(entry.getKey().redisKeyBuilder().getKey(), entry.getValue());
  109 + }
  110 + //2、填充结果
82 for (T sknInfoRequestResponse : cacheRequestResponses) { 111 for (T sknInfoRequestResponse : cacheRequestResponses) {
83 - if(sknInfoRequestResponse.getResponse()!=null){ 112 + if (sknInfoRequestResponse.getResponse() != null) {
84 continue; 113 continue;
85 } 114 }
86 RedisKeyBuilder redisKeyBuilder = sknInfoRequestResponse.getRequest().redisKeyBuilder(); 115 RedisKeyBuilder redisKeyBuilder = sknInfoRequestResponse.getRequest().redisKeyBuilder();
87 - V response = queryResults.get(redisKeyBuilder.getKey());  
88 - if(response!=null){  
89 - sknInfoRequestResponse.setResponse(response,true); 116 + V response = toCacheResults.get(redisKeyBuilder.getKey());
  117 + if (response != null) {
  118 + sknInfoRequestResponse.setResponse(response, true);
90 } 119 }
91 } 120 }
92 } 121 }
@@ -95,11 +124,8 @@ public class CacheRequestResponseComponent { @@ -95,11 +124,8 @@ public class CacheRequestResponseComponent {
95 * 将未缓存的response添加至缓存 124 * 将未缓存的response添加至缓存
96 * @param cacheRequestResponses 125 * @param cacheRequestResponses
97 * @param useEhCache 126 * @param useEhCache
98 - * @param <K>  
99 - * @param <V>  
100 - * @param <T>  
101 */ 127 */
102 - public <K extends ICacheRequest, V, T extends CacheRequestResponse<K, V>> void batchAddResponseToCache(List<T> cacheRequestResponses, boolean useEhCache) { 128 + private void batchAddResponseToCache(List<T> cacheRequestResponses, boolean useEhCache) {
103 //1、按缓存时间分组 129 //1、按缓存时间分组
104 Map<Integer, List<T>> groupMap = CollectionUtils.toListMap(cacheRequestResponses, new Transfer<T, Integer>() { 130 Map<Integer, List<T>> groupMap = CollectionUtils.toListMap(cacheRequestResponses, new Transfer<T, Integer>() {
105 @Override 131 @Override
@@ -113,16 +139,16 @@ public class CacheRequestResponseComponent { @@ -113,16 +139,16 @@ public class CacheRequestResponseComponent {
113 } 139 }
114 } 140 }
115 141
116 - private <K extends ICacheRequest, V, T extends CacheRequestResponse<K, V>> void batchAddResponseToCache(List<T> cacheRequestResponses, boolean useEhCache, int timeOutInSecond) { 142 + private void batchAddResponseToCache(List<T> cacheRequestResponses, boolean useEhCache, int timeOutInSecond) {
117 try { 143 try {
118 Map<RedisKeyBuilder, String> toCacheMap = new HashMap<>(); 144 Map<RedisKeyBuilder, String> toCacheMap = new HashMap<>();
119 for (T requestResponse : cacheRequestResponses) { 145 for (T requestResponse : cacheRequestResponses) {
120 - if (!requestResponse.isNeedRecache()){ 146 + if (!requestResponse.isNeedRecache()) {
121 continue; 147 continue;
122 } 148 }
123 RedisKeyBuilder redisKeyBuilder = requestResponse.getRequest().redisKeyBuilder(); 149 RedisKeyBuilder redisKeyBuilder = requestResponse.getRequest().redisKeyBuilder();
124 V response = requestResponse.getResponse(); 150 V response = requestResponse.getResponse();
125 - if(redisKeyBuilder==null || response==null){ 151 + if (redisKeyBuilder == null || response == null) {
126 continue; 152 continue;
127 } 153 }
128 String cacheValue = requestResponse.getFromResponseTransfer().transfer(response); 154 String cacheValue = requestResponse.getFromResponseTransfer().transfer(response);