diff --git a/client/src/main/java/cn/icanci/loopstack/ras/client/aop/RpcCallAop.java b/client/src/main/java/cn/icanci/loopstack/ras/client/aop/RpcCallAop.java index 9f372746c13ea6ca826323bc88ba9d3e0a3d2c0f..b0347ad2631ac2d656e6deb3784e70b40acb28a8 100644 --- a/client/src/main/java/cn/icanci/loopstack/ras/client/aop/RpcCallAop.java +++ b/client/src/main/java/cn/icanci/loopstack/ras/client/aop/RpcCallAop.java @@ -1,5 +1,7 @@ package cn.icanci.loopstack.ras.client.aop; +import cn.icanci.loopstack.ras.client.cache.loadbalancing.LoadBalancingSupport; + import org.aspectj.lang.ProceedingJoinPoint; import org.aspectj.lang.annotation.Around; import org.aspectj.lang.annotation.Aspect; @@ -7,8 +9,7 @@ import org.aspectj.lang.annotation.Pointcut; import org.springframework.stereotype.Component; /** - * AOP拦截 - * TODO 拦截执行时间和相关请求参数,记录到缓存 + * AOP拦截 - 拦截执行时间和相关请求参数,记录到缓存 * * @author icanci * @since 1.0 Created in 2023/01/16 19:56 @@ -17,7 +18,7 @@ import org.springframework.stereotype.Component; @Component public class RpcCallAop { - @Pointcut("execution(public * cn.icanci.loopstack.ras.client.facade.RpcCallFacade.call(..))") + @Pointcut("execution(public * cn.icanci.loopstack.ras.client.facade.RpcCallFacade.reallyCall(..))") private void callAop() { } @@ -28,7 +29,8 @@ public class RpcCallAop { long startTime = System.currentTimeMillis(); Object returnVal = pjp.proceed(); long endTime = System.currentTimeMillis(); - // TODO 记录执行时间、执行的内容 + // 刷新数据 + LoadBalancingSupport.refreshCallSpeedInfo(args, (endTime - startTime)); return returnVal; } } diff --git a/client/src/main/java/cn/icanci/loopstack/ras/client/cache/loadbalancing/ConsistencyHashLoadBalancing.java b/client/src/main/java/cn/icanci/loopstack/ras/client/cache/loadbalancing/ConsistencyHashLoadBalancing.java index f01ae3e4d6f20889ba3d55ee3208c66d1ba0a250..208a18a25662f419af0848a74a6e0676f345eb1f 100644 --- a/client/src/main/java/cn/icanci/loopstack/ras/client/cache/loadbalancing/ConsistencyHashLoadBalancing.java +++ b/client/src/main/java/cn/icanci/loopstack/ras/client/cache/loadbalancing/ConsistencyHashLoadBalancing.java @@ -6,7 +6,7 @@ import cn.icanci.loopstack.ras.common.enums.LoadBalanceTypeEnum; import org.springframework.stereotype.Service; /** - * 一致性hash负载均衡 + * 一致性哈希 * * @author icanci * @since 1.0 Created in 2023/01/30 19:34 diff --git a/client/src/main/java/cn/icanci/loopstack/ras/client/cache/loadbalancing/FastestCallSpeedLoadBalancing.java b/client/src/main/java/cn/icanci/loopstack/ras/client/cache/loadbalancing/FastestCallSpeedLoadBalancing.java index f3f37a3b7a2e2a592a9dfd6a0be3b24a75be8d85..b09b31b87ce2a826d24f78d6693d4e31b3a315ee 100644 --- a/client/src/main/java/cn/icanci/loopstack/ras/client/cache/loadbalancing/FastestCallSpeedLoadBalancing.java +++ b/client/src/main/java/cn/icanci/loopstack/ras/client/cache/loadbalancing/FastestCallSpeedLoadBalancing.java @@ -1,30 +1,74 @@ package cn.icanci.loopstack.ras.client.cache.loadbalancing; +import cn.icanci.loopstack.ras.client.cache.loadbalancing.model.FastestCallSpeedLoadBalancingHolder; import cn.icanci.loopstack.ras.client.cache.loadbalancing.model.LoadBalancingHolder; +import cn.icanci.loopstack.ras.client.cache.model.ApplicationValue; +import cn.icanci.loopstack.ras.client.cache.model.ClientApplicationValue; import cn.icanci.loopstack.ras.common.enums.LoadBalanceTypeEnum; +import java.util.Map; +import java.util.Set; +import java.util.concurrent.ConcurrentHashMap; + +import org.apache.commons.collections4.CollectionUtils; import org.springframework.stereotype.Service; /** + * 调用速度最快 + * * @author icanci * @since 1.0 Created in 2023/01/30 19:36 */ @Service @LoadBalancingBean(LoadBalanceTypeEnum.FASTEST_CALL_SPEED) public class FastestCallSpeedLoadBalancing extends LoadBalancingCache implements LoadBalancing { + /** + * 数据缓存结果模型 + */ + private static Map HOLDER = new ConcurrentHashMap<>(); @Override public void init() { + // 1.根据路由表,找到所有的指定路由方式 + if (isLbAppEmpty()) { + return; + } + Set applicationValues = filterLbType(LoadBalanceTypeEnum.FIRST); + if (CollectionUtils.isEmpty(applicationValues)) { + return; + } + Map tempMap = new ConcurrentHashMap<>(); + // 2.遍历应用表,构建缓存 + for (ClientApplicationValue applicationValue : applicationValues) { + String appId = applicationValue.getAppId(); + Set apps = applicationValue.getApplicationValues(); + tempMap.put(appId, new FastestCallSpeedLoadBalancingHolder(apps)); + } + // 3.替换 + HOLDER = tempMap; } @Override public void refresh() { - + init(); } @Override protected LoadBalancingHolder getHolder(String appId) { - return null; + return HOLDER.get(appId); + } + + /** + * 缓存构建刷新 + * + * @param appId appId + * @param ip ip + * @param port port + * @param runtime runtime + */ + public void refresh(String appId, String ip, int port, long runtime) { + FastestCallSpeedLoadBalancingHolder holder = HOLDER.get(appId); + holder.refresh(ip, port, runtime); } } diff --git a/client/src/main/java/cn/icanci/loopstack/ras/client/cache/loadbalancing/FirstLoadBalancing.java b/client/src/main/java/cn/icanci/loopstack/ras/client/cache/loadbalancing/FirstLoadBalancing.java index 334dc037a3090505bf31cae7c60516d34c06a136..2c3028ca9c318a6308adf1f8f1dd6d3d54efed3d 100644 --- a/client/src/main/java/cn/icanci/loopstack/ras/client/cache/loadbalancing/FirstLoadBalancing.java +++ b/client/src/main/java/cn/icanci/loopstack/ras/client/cache/loadbalancing/FirstLoadBalancing.java @@ -14,7 +14,7 @@ import org.apache.commons.collections4.CollectionUtils; import org.springframework.stereotype.Service; /** - * 负载均衡算法实现 + * 第一个 * * @author icanci * @since 1.0 Created in 2023/01/23 10:23 diff --git a/client/src/main/java/cn/icanci/loopstack/ras/client/cache/loadbalancing/InOrderLoadBalancing.java b/client/src/main/java/cn/icanci/loopstack/ras/client/cache/loadbalancing/InOrderLoadBalancing.java index 59e4005899260d025b55c2c78f1c9945fa773da1..5b289cd297c8b6f09732a94c4d5ee37e32b7b533 100644 --- a/client/src/main/java/cn/icanci/loopstack/ras/client/cache/loadbalancing/InOrderLoadBalancing.java +++ b/client/src/main/java/cn/icanci/loopstack/ras/client/cache/loadbalancing/InOrderLoadBalancing.java @@ -14,7 +14,7 @@ import org.apache.commons.collections4.CollectionUtils; import org.springframework.stereotype.Service; /** - * 负载均衡算法实现 + * 按顺序 * * @author icanci * @since 1.0 Created in 2023/01/23 10:23 diff --git a/client/src/main/java/cn/icanci/loopstack/ras/client/cache/loadbalancing/LastLoadBalancing.java b/client/src/main/java/cn/icanci/loopstack/ras/client/cache/loadbalancing/LastLoadBalancing.java index 7c2c7ba6c8bc67fdb787c0e624432ab310262631..76a511af834d3e4d881acdfb745e0d5854975b71 100644 --- a/client/src/main/java/cn/icanci/loopstack/ras/client/cache/loadbalancing/LastLoadBalancing.java +++ b/client/src/main/java/cn/icanci/loopstack/ras/client/cache/loadbalancing/LastLoadBalancing.java @@ -14,7 +14,7 @@ import org.apache.commons.collections4.CollectionUtils; import org.springframework.stereotype.Service; /** - * 负载均衡算法实现 + * 最后一个 * * @author icanci * @since 1.0 Created in 2023/01/23 10:23 diff --git a/client/src/main/java/cn/icanci/loopstack/ras/client/cache/loadbalancing/LeastFrequentlyUsedLoadBalancing.java b/client/src/main/java/cn/icanci/loopstack/ras/client/cache/loadbalancing/LeastFrequentlyUsedLoadBalancing.java index 981c5bfa8156519c7ac7a1a8dc7831dbedba4a3a..4cef718f5ae78fcb53627f7ebeaa52aca339be20 100644 --- a/client/src/main/java/cn/icanci/loopstack/ras/client/cache/loadbalancing/LeastFrequentlyUsedLoadBalancing.java +++ b/client/src/main/java/cn/icanci/loopstack/ras/client/cache/loadbalancing/LeastFrequentlyUsedLoadBalancing.java @@ -1,11 +1,13 @@ package cn.icanci.loopstack.ras.client.cache.loadbalancing; -import org.springframework.stereotype.Service; - import cn.icanci.loopstack.ras.client.cache.loadbalancing.model.LoadBalancingHolder; import cn.icanci.loopstack.ras.common.enums.LoadBalanceTypeEnum; +import org.springframework.stereotype.Service; + /** + * 最不经常使用 + * * @author icanci * @since 1.0 Created in 2023/01/30 19:36 */ @@ -25,6 +27,6 @@ public class LeastFrequentlyUsedLoadBalancing extends LoadBalancingCache impleme @Override protected LoadBalancingHolder getHolder(String appId) { - return HOLDER.get(appId); + return null; } } diff --git a/client/src/main/java/cn/icanci/loopstack/ras/client/cache/loadbalancing/LeastRecentlyUsedLoadBalancing.java b/client/src/main/java/cn/icanci/loopstack/ras/client/cache/loadbalancing/LeastRecentlyUsedLoadBalancing.java index 53365202d25aee183d5c183eaa51cd4085b36fa7..5b45a5473af260bf3b4a32d3d659e23cb3d64ec8 100644 --- a/client/src/main/java/cn/icanci/loopstack/ras/client/cache/loadbalancing/LeastRecentlyUsedLoadBalancing.java +++ b/client/src/main/java/cn/icanci/loopstack/ras/client/cache/loadbalancing/LeastRecentlyUsedLoadBalancing.java @@ -1,11 +1,13 @@ package cn.icanci.loopstack.ras.client.cache.loadbalancing; -import org.springframework.stereotype.Service; - import cn.icanci.loopstack.ras.client.cache.loadbalancing.model.LoadBalancingHolder; import cn.icanci.loopstack.ras.common.enums.LoadBalanceTypeEnum; +import org.springframework.stereotype.Service; + /** + * 最近最久未使用 + * * @author icanci * @since 1.0 Created in 2023/01/30 19:36 */ @@ -25,6 +27,6 @@ public class LeastRecentlyUsedLoadBalancing extends LoadBalancingCache implement @Override protected LoadBalancingHolder getHolder(String appId) { - return HOLDER.get(appId); + return null; } } diff --git a/client/src/main/java/cn/icanci/loopstack/ras/client/cache/loadbalancing/LoadBalancingSupport.java b/client/src/main/java/cn/icanci/loopstack/ras/client/cache/loadbalancing/LoadBalancingSupport.java index 3d6352d2872c4dc1e85a7303ecb16855e318a3fa..ecf7a567d13fd7f4446e7d0f5cba649d5effc3eb 100644 --- a/client/src/main/java/cn/icanci/loopstack/ras/client/cache/loadbalancing/LoadBalancingSupport.java +++ b/client/src/main/java/cn/icanci/loopstack/ras/client/cache/loadbalancing/LoadBalancingSupport.java @@ -4,15 +4,22 @@ import cn.icanci.loopstack.ras.client.cache.MetaCacheHolder; import cn.icanci.loopstack.ras.client.cache.model.ApplicationValue; import cn.icanci.loopstack.ras.client.cache.model.ClientApplicationValue; import cn.icanci.loopstack.ras.common.enums.LoadBalanceTypeEnum; +import io.netty.util.internal.ThrowableUtil; +import java.io.IOException; +import java.net.InetAddress; +import java.net.URL; import java.util.Collection; import java.util.Map; import java.util.Optional; +import org.slf4j.Logger; +import org.slf4j.LoggerFactory; import org.springframework.aop.support.AopUtils; import org.springframework.beans.BeansException; import org.springframework.context.ApplicationContext; +import com.alibaba.fastjson.JSON; import com.google.common.collect.Maps; /** @@ -24,6 +31,8 @@ import com.google.common.collect.Maps; */ public final class LoadBalancingSupport extends MetaCacheHolder { + private static final Logger logger = LoggerFactory.getLogger(LoadBalancingSupport.class); + /** 执行存储单元 */ private static final Map LB_REPOSITORY = Maps.newHashMap(); @@ -76,4 +85,66 @@ public final class LoadBalancingSupport extends MetaCacheHolder { LB_REPOSITORY.put(loadBalancingBean.value(), loadBalancing); } } + + /** + * 数据刷新 + * + * @param args 方法参数 + * String appId, String url, Object request, Map headers, Method method, int readTimeOut, int retry, Class clazz + * + * @param rt 执行调用的耗时 + */ + public static void refreshCallSpeedInfo(Object[] args, long rt) { + try { + // 获取 appid + String appId = String.valueOf(args[0]); + String url = String.valueOf(args[1]); + // REQUEST_FORMAT + ClientApplicationValue clientApplicationValue = CLIENT_APPLICATION_MAP.get(appId); + if (clientApplicationValue == null) { + return; + } + // 解析 ip 和 port + String ip = parseIp(url); + int port = parsePort(url); + + LoadBalanceTypeEnum loadBalanceType = clientApplicationValue.getLoadBalanceType(); + LoadBalancing loadBalancing = LB_REPOSITORY.get(loadBalanceType); + // 只处理 FastestCallSpeedLoadBalancing 类型 + if (loadBalancing instanceof FastestCallSpeedLoadBalancing) { + FastestCallSpeedLoadBalancing fastestCallSpeedLoadBalancing = (FastestCallSpeedLoadBalancing) loadBalancing; + fastestCallSpeedLoadBalancing.refresh(appId, ip, port, rt); + } + } catch (Throwable ex) { + logger.error("[LoadBalancingSupport][refreshCallSpeedInfo] args:{},rt:{}rt, error:{}", JSON.toJSONString(args), rt, ThrowableUtil.stackTraceToString(ex)); + } + } + + /** + * 获取端口号 + * + * @param href 网址 + * @return port + */ + public static int parsePort(String href) throws IOException { + URL url = new URL(href); + int port = url.getPort(); + if (port < 0) { + port = url.getDefaultPort(); + } + return port; + } + + /** + * 根据域名解析IP地址 + * + * @param href href + * @return getHostAddress + */ + public static String parseIp(String href) throws IOException { + URL url = new URL(href); + String host = url.getHost(); + InetAddress inetAddress = InetAddress.getByName(host); + return inetAddress.getHostAddress(); + } } diff --git a/client/src/main/java/cn/icanci/loopstack/ras/client/cache/loadbalancing/RandomLoadBalancing.java b/client/src/main/java/cn/icanci/loopstack/ras/client/cache/loadbalancing/RandomLoadBalancing.java index 23cf0e393802880b2be3c87c8a8d098ff0601546..39744e31fcb224696fbd04c4d5d9651576e7164d 100644 --- a/client/src/main/java/cn/icanci/loopstack/ras/client/cache/loadbalancing/RandomLoadBalancing.java +++ b/client/src/main/java/cn/icanci/loopstack/ras/client/cache/loadbalancing/RandomLoadBalancing.java @@ -14,7 +14,7 @@ import org.apache.commons.collections4.CollectionUtils; import org.springframework.stereotype.Service; /** - * 负载均衡算法实现 + * 随机 * * @author icanci * @since 1.0 Created in 2023/01/23 10:23 diff --git a/client/src/main/java/cn/icanci/loopstack/ras/client/cache/loadbalancing/model/FastestCallSpeedLoadBalancingHolder.java b/client/src/main/java/cn/icanci/loopstack/ras/client/cache/loadbalancing/model/FastestCallSpeedLoadBalancingHolder.java new file mode 100644 index 0000000000000000000000000000000000000000..d43505faabb49d91dda740b6a99c40bee5244de0 --- /dev/null +++ b/client/src/main/java/cn/icanci/loopstack/ras/client/cache/loadbalancing/model/FastestCallSpeedLoadBalancingHolder.java @@ -0,0 +1,183 @@ +package cn.icanci.loopstack.ras.client.cache.loadbalancing.model; + +import cn.icanci.loopstack.ras.client.cache.model.ApplicationValue; + +import java.util.*; +import java.util.concurrent.atomic.AtomicInteger; + +import org.apache.commons.lang3.StringUtils; + +import com.google.common.collect.Lists; + +/** + * @author icanci + * @since 1.0 Created in 2023/02/04 21:00 + */ +public class FastestCallSpeedLoadBalancingHolder extends LoadBalancingHolder { + /** + * 应用列表 + */ + private final Set applicationHolder; + + /** + * 缓存队列的最大长度 + * 同一个App调用次数超过1千次,则清零 + */ + private AtomicInteger maxQueueSize = new AtomicInteger(1000); + + public FastestCallSpeedLoadBalancingHolder(Set applications) { + // 初始化 + applicationHolder = new TreeSet<>(new Comparator() { + @Override + public int compare(InnerFastestCallSpeedLoadBalancingHolder o1, InnerFastestCallSpeedLoadBalancingHolder o2) { + return (int) (o1.getAverageCallRuntime() - o2.getAverageCallRuntime()); + } + }); + init(applications); + // 设置下一个 + setNext(); + } + + /** + * 初始化操作 + * + * @param applications applications + */ + private void init(Set applications) { + for (ApplicationValue application : applications) { + applicationHolder.add(new InnerFastestCallSpeedLoadBalancingHolder(application)); + } + } + + /** + * 设置下一个需要加载的数据 + */ + @Override + public void setNext() { + Optional speedOptional = applicationHolder.stream() + .filter(appHolder -> appHolder.getApplicationValue().getOnline() == 0 && appHolder.getApplicationValue().getIsDelete() == 0).findFirst(); + if (speedOptional.isPresent()) { + this.next = speedOptional.get().getApplicationValue(); + maxQueueSize.decrementAndGet(); + } else { + speedOptional = applicationHolder.stream().filter(appHolder -> appHolder.getApplicationValue().getOnline() == 0).findFirst(); + if (speedOptional.isPresent()) { + this.next = speedOptional.get().getApplicationValue(); + maxQueueSize.decrementAndGet(); + } else { + speedOptional = applicationHolder.stream().filter(appHolder -> appHolder.getApplicationValue().getOnline() == 1).findFirst(); + if (speedOptional.isPresent()) { + this.next = speedOptional.get().getApplicationValue(); + maxQueueSize.decrementAndGet(); + } + } + } + + tryFixQueueSize(); + } + + /** + * 尝试处理次数 + */ + private void tryFixQueueSize() { + if (maxQueueSize.get() <= 0) { + maxQueueSize = new AtomicInteger(1000); + } + } + + /** + * refresh + * + * @param ip ip + * @param port port + * @param runtime runtime + */ + public void refresh(String ip, int port, long runtime) { + if (runtime < 0) { + return; + } + Optional target = applicationHolder.stream() + .filter(appHolder -> StringUtils.equals(appHolder.getApplicationValue().getAddress(), ip) && appHolder.getApplicationValue().getPort() == port).findFirst(); + if (!target.isPresent()) { + return; + } + InnerFastestCallSpeedLoadBalancingHolder holder = target.get(); + ApplicationValue applicationValue = holder.getApplicationValue(); + long averageCallRuntime = holder.getAverageCallRuntime(); + List callRuntimeQueue = holder.getCallRuntimeQueue(); + callRuntimeQueue.add(runtime); + double average = callRuntimeQueue.stream().mapToDouble(Long::longValue).average().orElse(0D); + InnerFastestCallSpeedLoadBalancingHolder temp = new InnerFastestCallSpeedLoadBalancingHolder(applicationValue, (long) average, callRuntimeQueue); + applicationHolder.removeIf(appHolder -> StringUtils.equals(appHolder.getApplicationValue().getAddress(), ip) && appHolder.getApplicationValue().getPort() == port); + applicationHolder.add(temp); + } + + /** + * 内部对象 + */ + public static class InnerFastestCallSpeedLoadBalancingHolder { + /** + * app 信息 + */ + private final ApplicationValue applicationValue; + /** + * 执行平均时间 + */ + private long averageCallRuntime = 0L; + /** + * 执行耗时队列 + */ + private List callRuntimeQueue = Lists.newArrayList(); + + /** + * 初始化构造函数 + * - + * @param applicationValue applicationValue + */ + public InnerFastestCallSpeedLoadBalancingHolder(ApplicationValue applicationValue) { + this.applicationValue = applicationValue; + } + + public InnerFastestCallSpeedLoadBalancingHolder(ApplicationValue applicationValue, long averageCallRuntime, List callRuntimeQueue) { + this.applicationValue = applicationValue; + this.averageCallRuntime = averageCallRuntime; + this.callRuntimeQueue = callRuntimeQueue; + } + + public ApplicationValue getApplicationValue() { + return applicationValue; + } + + public long getAverageCallRuntime() { + return averageCallRuntime; + } + + public void setAverageCallRuntime(long averageCallRuntime) { + this.averageCallRuntime = averageCallRuntime; + } + + public List getCallRuntimeQueue() { + return callRuntimeQueue; + } + + public void setCallRuntimeQueue(List callRuntimeQueue) { + this.callRuntimeQueue = callRuntimeQueue; + } + + @Override + public boolean equals(Object o) { + if (this == o) + return true; + if (o == null || getClass() != o.getClass()) + return false; + InnerFastestCallSpeedLoadBalancingHolder that = (InnerFastestCallSpeedLoadBalancingHolder) o; + return Objects.equals(applicationValue, that.applicationValue); + } + + @Override + public int hashCode() { + return Objects.hash(applicationValue); + } + } + +} diff --git a/client/src/main/java/cn/icanci/loopstack/ras/client/cache/loadbalancing/model/InOrderBalancingHolder.java b/client/src/main/java/cn/icanci/loopstack/ras/client/cache/loadbalancing/model/InOrderBalancingHolder.java index ca67e61978412a2a064b2307f51b05189c22281c..656cafb3666b64dfe29038b5a8263b3acf4a4d73 100644 --- a/client/src/main/java/cn/icanci/loopstack/ras/client/cache/loadbalancing/model/InOrderBalancingHolder.java +++ b/client/src/main/java/cn/icanci/loopstack/ras/client/cache/loadbalancing/model/InOrderBalancingHolder.java @@ -60,7 +60,7 @@ public class InOrderBalancingHolder extends LoadBalancingHolder { * @param size 当前执行的大小 */ private void fixInOrderIndex(int size) { - if (inOrderAtomicInteger.get() == size) { + if (inOrderAtomicInteger.get() == size - 1) { inOrderAtomicInteger = new AtomicInteger(0); } } diff --git a/client/src/main/java/cn/icanci/loopstack/ras/client/cache/loadbalancing/model/LoadBalancingHolder.java b/client/src/main/java/cn/icanci/loopstack/ras/client/cache/loadbalancing/model/LoadBalancingHolder.java index 13d4e5c94555d891223d77fca29d6cf7768fd2fa..f17db6cdd870f61b348529e52ac45db0f717aaf1 100644 --- a/client/src/main/java/cn/icanci/loopstack/ras/client/cache/loadbalancing/model/LoadBalancingHolder.java +++ b/client/src/main/java/cn/icanci/loopstack/ras/client/cache/loadbalancing/model/LoadBalancingHolder.java @@ -33,4 +33,5 @@ public abstract class LoadBalancingHolder { // 返回当前的 return tmpNext; } + } diff --git a/client/src/main/java/cn/icanci/loopstack/ras/client/facade/RpcCallFacade.java b/client/src/main/java/cn/icanci/loopstack/ras/client/facade/RpcCallFacade.java index 8a686bc6e1cabae92b267ceaa374521bb1c537f9..e95abc778ef14db5ccfc90094740e670e483e777 100644 --- a/client/src/main/java/cn/icanci/loopstack/ras/client/facade/RpcCallFacade.java +++ b/client/src/main/java/cn/icanci/loopstack/ras/client/facade/RpcCallFacade.java @@ -3,8 +3,8 @@ package cn.icanci.loopstack.ras.client.facade; import cn.hutool.http.Method; import cn.icanci.loopstack.api.client.Client; import cn.icanci.loopstack.api.client.http.HttpClientImpl; -import cn.icanci.loopstack.ras.client.exception.RpcCallException; import cn.icanci.loopstack.ras.client.cache.holder.RasRepositoryHolder; +import cn.icanci.loopstack.ras.client.exception.RpcCallException; import java.util.Map; import java.util.concurrent.TimeUnit; @@ -120,10 +120,26 @@ public class RpcCallFacade { * @return 返回请求返回数据 */ public T call(String appId, String relativePath, Object request, Map headers, Method method, int readTimeOut, int retry, Class clazz) { - // 构建请求参数 - Client.RpcRequest rpcRequest = new Client.RpcRequest(resolvingRequestUrl(appId, relativePath), request, headers == null ? DEFAULT_HEADERS : headers, method, readTimeOut, - TimeUnit.SECONDS, retry); + return reallyCall(appId, resolvingRequestUrl(appId, relativePath), request, headers == null ? DEFAULT_HEADERS : headers, method, readTimeOut, retry, clazz); + } + /** + * 请求调用 + * + * @param appId appId AOP 使用 + * @param url url + * @param request 请求 + * @param headers 请求头 + * @param method 请求方法 + * @param readTimeOut 请求超时时间(单位 秒) + * @param retry 重试次数 + * @param clazz 请求返回类型 + * @param 请求返回泛型 + * @return 返回请求返回数据 + */ + public T reallyCall(String appId, String url, Object request, Map headers, Method method, int readTimeOut, int retry, Class clazz) { + // 构建请求参数 + Client.RpcRequest rpcRequest = new Client.RpcRequest(url, request, headers, method, readTimeOut, TimeUnit.SECONDS, retry); // 调用 return CLIENT.call(rpcRequest, clazz); } diff --git a/client/src/test/java/cn/icanci/loopstack/ras/client/cache/loadbalancing/test/TreeSetTest.java b/client/src/test/java/cn/icanci/loopstack/ras/client/cache/loadbalancing/test/TreeSetTest.java new file mode 100644 index 0000000000000000000000000000000000000000..9106a6c2becb9e45b1b42853075ad871facaa591 --- /dev/null +++ b/client/src/test/java/cn/icanci/loopstack/ras/client/cache/loadbalancing/test/TreeSetTest.java @@ -0,0 +1,77 @@ +package cn.icanci.loopstack.ras.client.cache.loadbalancing.test; + +import java.util.*; + +import org.junit.Test; + +/** + * @author icanci + * @since 1.0 Created in 2023/02/04 21:35 + */ +public class TreeSetTest { + @Test + public void test1() { + TreeSet tests = new TreeSet<>(new Comparator() { + @Override + public int compare(Test1 o1, Test1 o2) { + return o1.index - o2.index; + } + }); + tests.add(new Test1(111)); + tests.add(new Test1(222)); + tests.add(new Test1(333)); + System.out.println(tests); + Test1 first = tests.first(); + Test1 test1 = new Test1(999); + tests.remove(first); + tests.add(test1); + System.out.println(tests); + } + + @Test + public void test2() { + List callRuntimeQueue = new ArrayList<>(); + callRuntimeQueue.add(111L); + callRuntimeQueue.add(222L); + callRuntimeQueue.add(333L); + double average = callRuntimeQueue.stream().mapToDouble(Long::longValue).average().orElse(0D); + System.out.println((long) average); + } + + public static class Test1 { + private int index; + + public Test1(int index) { + this.index = index; + } + + public int getIndex() { + + return index; + } + + public void setIndex(int index) { + this.index = index; + } + + @Override + public boolean equals(Object o) { + if (this == o) + return true; + if (o == null || getClass() != o.getClass()) + return false; + Test1 test = (Test1) o; + return index == test.index; + } + + @Override + public int hashCode() { + return Objects.hash(index); + } + + @Override + public String toString() { + return new StringJoiner(",").add("index=" + index).toString(); + } + } +} diff --git a/client/src/test/java/cn/icanci/loopstack/ras/client/cache/loadbalancing/test/UrlTest.java b/client/src/test/java/cn/icanci/loopstack/ras/client/cache/loadbalancing/test/UrlTest.java new file mode 100644 index 0000000000000000000000000000000000000000..26bf88ddc9b50b415ece6e73ec07d46dfbe0bb78 --- /dev/null +++ b/client/src/test/java/cn/icanci/loopstack/ras/client/cache/loadbalancing/test/UrlTest.java @@ -0,0 +1,61 @@ +package cn.icanci.loopstack.ras.client.cache.loadbalancing.test; + +import java.io.IOException; +import java.net.InetAddress; +import java.net.URI; +import java.net.URL; + +import org.junit.Test; + +/** + * @author icanci + * @since 1.0 Created in 2023/02/04 21:35 + */ +public class UrlTest { + @Test + public void test1() throws IOException { + String host1 = "https://blog.csdn.net/qq_43566496/article/details/84938575"; + System.out.println(parseIp(host1)); + System.out.println(parsePort(host1)); + + + String host2 = "http://127.0.0.1:8080/qq_43566496/article/details/84938575"; + System.out.println(parseIp(host2)); + System.out.println(parsePort(host2)); + + URI uri = URI.create("http://127.0.0.1:8080/qq_43566496/article/details/84938575"); + String host = uri.getHost(); + int port = uri.getPort(); + System.out.println(host); + System.out.println(port); + } + + /** + * 获取端口号 + * + * @param href 网址 + * @return port + */ + public int parsePort(String href) throws IOException { + URL url = new URL(href); + int port = url.getPort(); + if (port < 0) { + port = url.getDefaultPort(); + } + return port; + } + + /** + * 根据域名解析IP地址 + * + * @param href href + * @return getHostAddress + * @throws IOException + */ + public String parseIp(String href) throws IOException { + URL url = new URL(href); + String host = url.getHost(); + InetAddress inetAddress = InetAddress.getByName(host); + return inetAddress.getHostAddress(); + } +} diff --git a/server/src/main/java/cn/icanci/loopstack/ras/server/Test.java b/server/src/main/java/cn/icanci/loopstack/ras/server/Test.java new file mode 100644 index 0000000000000000000000000000000000000000..a4a877cdec162b5733ba485ace85ab3d5d89196d --- /dev/null +++ b/server/src/main/java/cn/icanci/loopstack/ras/server/Test.java @@ -0,0 +1,8 @@ +package cn.icanci.loopstack.ras.server; + +/** + * @author icanci + * @since 1.0 Created in 2023/02/04 21:38 + */ +public class Test { +}