From a833d8d631eb124bb96df3e018303a57028cfcc7 Mon Sep 17 00:00:00 2001 From: cooper30 <100362205+remedy30@users.noreply.github.com> Date: Thu, 31 Jul 2025 09:24:18 +0800 Subject: [PATCH] feat:Modify the annotations --- CHANGELOG.md | 1 + .../callee/QuickstartCalleeController.java | 7 ++ .../callee/service/FaultToleranceService.java | 38 ++++++- .../demo/consumer/controller/SdkBaseTest.java | 105 +++++++++++++++++- 4 files changed, 144 insertions(+), 7 deletions(-) diff --git a/CHANGELOG.md b/CHANGELOG.md index 3af01953a..7db052512 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -18,3 +18,4 @@ - [feat:support fault injection.](https://github.com/Tencent/spring-cloud-tencent/pull/1707) - [feat: support config event and monitor address list.](https://github.com/Tencent/spring-cloud-tencent/pull/1708) - [fix:replace HttpClient with HttpURLConnection for JDK 8 compatibility.](https://github.com/Tencent/spring-cloud-tencent/pull/1709) +- [feat:Modify the annotations.](https://github.com/Tencent/spring-cloud-tencent/pull/1712) diff --git a/spring-cloud-tencent-examples/quickstart-example/quickstart-callee-service-a/src/main/java/com/tencent/cloud/quickstart/callee/QuickstartCalleeController.java b/spring-cloud-tencent-examples/quickstart-example/quickstart-callee-service-a/src/main/java/com/tencent/cloud/quickstart/callee/QuickstartCalleeController.java index 9ba76d18e..c8a1a785a 100644 --- a/spring-cloud-tencent-examples/quickstart-example/quickstart-callee-service-a/src/main/java/com/tencent/cloud/quickstart/callee/QuickstartCalleeController.java +++ b/spring-cloud-tencent-examples/quickstart-example/quickstart-callee-service-a/src/main/java/com/tencent/cloud/quickstart/callee/QuickstartCalleeController.java @@ -17,8 +17,10 @@ package com.tencent.cloud.quickstart.callee; +import java.io.IOException; import java.io.UnsupportedEncodingException; import java.net.URLDecoder; +import java.util.concurrent.TimeoutException; import com.tencent.cloud.common.constant.MetadataConstant; import com.tencent.cloud.quickstart.callee.config.DataSourceProperties; @@ -159,4 +161,9 @@ public class QuickstartCalleeController { public String faultToleranceForking() { return faultToleranceService.forking(); } + + @GetMapping("/faultTolerance/raisedException/{exceptionType}") + public String faultToleranceRaisedException(@PathVariable String exceptionType) throws IOException, TimeoutException { + return faultToleranceService.raisedException(exceptionType); + } } diff --git a/spring-cloud-tencent-examples/quickstart-example/quickstart-callee-service-a/src/main/java/com/tencent/cloud/quickstart/callee/service/FaultToleranceService.java b/spring-cloud-tencent-examples/quickstart-example/quickstart-callee-service-a/src/main/java/com/tencent/cloud/quickstart/callee/service/FaultToleranceService.java index 446d53318..abdd1d0fc 100644 --- a/spring-cloud-tencent-examples/quickstart-example/quickstart-callee-service-a/src/main/java/com/tencent/cloud/quickstart/callee/service/FaultToleranceService.java +++ b/spring-cloud-tencent-examples/quickstart-example/quickstart-callee-service-a/src/main/java/com/tencent/cloud/quickstart/callee/service/FaultToleranceService.java @@ -17,10 +17,14 @@ package com.tencent.cloud.quickstart.callee.service; +import java.io.IOException; +import java.util.concurrent.TimeoutException; import java.util.concurrent.atomic.AtomicInteger; import com.tencent.cloud.plugin.faulttolerance.annotation.FaultTolerance; import com.tencent.cloud.plugin.faulttolerance.model.FaultToleranceStrategy; +import org.slf4j.Logger; +import org.slf4j.LoggerFactory; import org.springframework.stereotype.Service; @@ -32,31 +36,59 @@ import org.springframework.stereotype.Service; @Service public class FaultToleranceService { + private static final Logger LOG = LoggerFactory.getLogger(FaultToleranceService.class); + private final AtomicInteger failOverCount = new AtomicInteger(0); private final AtomicInteger forkingCount = new AtomicInteger(0); @FaultTolerance(strategy = FaultToleranceStrategy.FAIL_FAST, fallbackMethod = "fallback") public String failFast() { + LOG.info("Test failFast"); throw new RuntimeException("NO"); } public String fallback() { - return "fallback"; + return "fallback success"; } @FaultTolerance(strategy = FaultToleranceStrategy.FAIL_OVER, maxAttempts = 3) public String failOver() { + LOG.info("Test failOver"); if (failOverCount.incrementAndGet() % 4 == 0) { - return "OK"; + return "failOver success,failOverCount=" + failOverCount.get(); } throw new RuntimeException("NO"); } @FaultTolerance(strategy = FaultToleranceStrategy.FORKING, parallelism = 4) public String forking() { + LOG.info("Test forking"); if (forkingCount.incrementAndGet() % 4 == 0) { - return "OK"; + return "forking success,forkingCount=" + forkingCount.get(); } throw new RuntimeException("NO"); } + + @FaultTolerance(strategy = FaultToleranceStrategy.FAIL_OVER, maxAttempts = 3, fallbackMethod = "fallback", + ignoreExceptions = {RuntimeException.class}, raisedExceptions = {Exception.class}) + public String raisedException(String exceptionType) throws IOException, RuntimeException, TimeoutException { + switch (exceptionType) { + case "RuntimeException": + LOG.info("Test failOver for raised RuntimeException"); + throw new RuntimeException("NO"); + case "TimeOutException": + LOG.info("Test failOver for raised TimeOutException"); + if (failOverCount.incrementAndGet() % 4 == 0) { + return "failOver success,failOverCount=" + failOverCount.get(); + } + throw new TimeoutException("NO"); + default: + LOG.info("Test failOver for raised otherException"); + if (failOverCount.incrementAndGet() % 4 == 0) { + return "failOver success,failOverCount=" + failOverCount.get(); + } + throw new IOException("NO"); + } + } + } diff --git a/spring-cloud-tencent-examples/tsf-example/consumer-demo/src/main/java/com/tencent/cloud/tsf/demo/consumer/controller/SdkBaseTest.java b/spring-cloud-tencent-examples/tsf-example/consumer-demo/src/main/java/com/tencent/cloud/tsf/demo/consumer/controller/SdkBaseTest.java index 1b68d6777..d53c2b438 100644 --- a/spring-cloud-tencent-examples/tsf-example/consumer-demo/src/main/java/com/tencent/cloud/tsf/demo/consumer/controller/SdkBaseTest.java +++ b/spring-cloud-tencent-examples/tsf-example/consumer-demo/src/main/java/com/tencent/cloud/tsf/demo/consumer/controller/SdkBaseTest.java @@ -17,11 +17,17 @@ package com.tencent.cloud.tsf.demo.consumer.controller; +import java.io.IOException; +import java.util.concurrent.TimeoutException; +import java.util.concurrent.atomic.AtomicInteger; + import com.tencent.polaris.api.utils.StringUtils; import org.slf4j.Logger; import org.slf4j.LoggerFactory; import org.springframework.beans.factory.annotation.Autowired; +import org.springframework.cloud.tsf.faulttolerance.annotation.TsfFaultTolerance; +import org.springframework.cloud.tsf.faulttolerance.model.TsfFaultToleranceStragety; import org.springframework.tsf.core.TsfContext; import org.springframework.web.bind.annotation.PathVariable; import org.springframework.web.bind.annotation.RequestMapping; @@ -38,11 +44,10 @@ public class SdkBaseTest { @Autowired private RestTemplate restTemplate; - // 调用一次provider接口 + private final AtomicInteger failOverCount = new AtomicInteger(0); + @RequestMapping(value = "/echo-once/{str}", method = RequestMethod.GET) - public String restOnceProvider(@PathVariable String str, - @RequestParam(required = false) String tagName, - @RequestParam(required = false) String tagValue) { + public String restOnceProvider(@PathVariable String str, @RequestParam(required = false) String tagName, @RequestParam(required = false) String tagValue) { if (!StringUtils.isEmpty(tagName)) { TsfContext.putTag(tagName, tagValue); } @@ -51,4 +56,96 @@ public class SdkBaseTest { LOG.info("end call echo-once, the result is : " + result); return result; } + + @TsfFaultTolerance(strategy = TsfFaultToleranceStragety.FAIL_FAST, fallbackMethod = "restProviderFailfast") + @RequestMapping(value = "/failfast/{str}", method = RequestMethod.GET) + public String failFast(@PathVariable String str) { + LOG.info("start call failfast:" + str); + String result = restTemplate.getForObject("http://provider-demo/error/" + str, String.class); + LOG.info("end call failfast-no-:" + str); + return result; + } + + public String restProviderFailfast(String str) { + String result = "failfast-recall:" + str; + LOG.info(result); + return result; + } + + + @TsfFaultTolerance(strategy = TsfFaultToleranceStragety.FAIL_FAST, fallbackMethod = "restProviderFallback") + @RequestMapping(value = "/fallback/{str}", method = RequestMethod.GET) + public String fallBack(@PathVariable String str) { + LOG.info("start call fallback:" + str); + String result = restTemplate.getForObject("http://provider-demo/error/" + str, String.class); + LOG.info("end call fallback-no:" + result); + return result; + } + + public String restProviderFallback(String str) { + String result = "fallback-recall:" + str; + LOG.info(result); + return result; + } + + // The call failed. Fault tolerance retry twice. A total of three calls + @TsfFaultTolerance(strategy = TsfFaultToleranceStragety.FAIL_OVER, maxAttempts = 2, fallbackMethod = "restProviderFailover") + @RequestMapping(value = "/failover/{str}", method = RequestMethod.GET) + public String failOver(@PathVariable String str) { + LOG.info("start call failover:" + str); + String result = restTemplate.getForObject("http://provider-demo/error/" + str, String.class); + LOG.info("end call failover-no:" + str); + return result; + } + + public String restProviderFailover(String str) { + String result = "failover-recall:" + str; + LOG.info(result); + return result; + } + + // Ignore the RuntimeException exception, do not trigger fault tolerance, and retry will fail + @TsfFaultTolerance(strategy = TsfFaultToleranceStragety.FAIL_OVER, maxAttempts = 2, ignoreExceptions = {RuntimeException.class}, fallbackMethod = "restProviderFailoverException") + @RequestMapping(value = "/failover-exception/{str}", method = RequestMethod.GET) + public String failOverException(@PathVariable String str) throws InterruptedException { + String result = ""; + LOG.info("start call failover-exception:" + str); + result = restTemplate.getForObject("http://provider-demo/error/" + str, String.class); + LOG.info("end call failover with exception:" + str); + return result; + } + + public String restProviderFailoverException(String str) { + String result = "failover-exception-recall:" + str; + LOG.info(result); + return result; + } + + + @TsfFaultTolerance(strategy = TsfFaultToleranceStragety.FAIL_OVER, maxAttempts = 2, ignoreExceptions = {RuntimeException.class}, + raisedExceptions = {Exception.class}, fallbackMethod = "restProviderFallback") + @RequestMapping(value = "/raisedException/{exceptionType}", method = RequestMethod.GET) + public String raisedException(@PathVariable String exceptionType) throws IOException, RuntimeException, TimeoutException { + String result = ""; +// LOG.info("start call raisedException:" + exceptionType); + switch (exceptionType) { + case "RuntimeException": + LOG.info("Test failOver for raised RuntimeException"); + throw new RuntimeException("NO"); + + case "TimeOutException": + LOG.info("Test failOver for raised TimeOutException"); + if (failOverCount.incrementAndGet() % 3 == 0) { + return "failOver success,failOverCount=" + failOverCount.get(); + } + throw new TimeoutException("NO"); + default: + LOG.info("Test failOver for raised otherException"); + if (failOverCount.incrementAndGet() % 3 == 0) { + return "failOver success,failOverCount=" + failOverCount.get(); + } + throw new IOException("NO"); + } + + } }