当前位置: 首页 > news >正文

成都锦江区网站建设公司潍坊 公司 网站

成都锦江区网站建设公司,潍坊 公司 网站,杭州设计网站的公司,网站建设预算申请如何写我前面写了一篇springboot优雅shutdown的文章,看起来一切很美好。 https://blog.csdn.net/chenshm/article/details/139640775 那是因为没有进行多线程测试。如果一个请求中包括阻塞线程(主线程)和非阻塞线程(异步线程&#xff09…

我前面写了一篇springboot优雅shutdown的文章,看起来一切很美好。
https://blog.csdn.net/chenshm/article/details/139640775
那是因为没有进行多线程测试。如果一个请求中包括阻塞线程(主线程)和非阻塞线程(异步线程),会是什么效果?接下来我们就测试一番。

1. 验证优雅shutdown的异步线程安全性

  • 确认graceful shutdown配置

graceful shutdown config
查看源码可以看到springboot graceful shutdown默认只会等待30s,我这里设置更长的时间只是方便测试,实际设置还是需要根据你业务api最长执行时间来配置。

graceful shutdown default timeout setting

  • 准备测试代码
@Slf4j
@RestController
@RequestMapping("/api")
public class DemoController {@GetMapping("/{userId}")public ResultVo<Object> getUserInfo(@PathVariable String userId) throws InterruptedException {log.info("userId:{}", userId);Runnable runnable = () -> {for (int i = 0; i < 60; i++) {log.info("async thread to update user login info to other services, service num: {}", i);try {Thread.sleep(1000);} catch (InterruptedException e) {throw new RuntimeException(e);}}};Thread thread = new Thread(runnable);thread.start();for (int i = 0; i < 30; i++) {log.info("querying user info for {}, waiting times: {}", userId, i);Thread.sleep(1000);}return ResultVo.ok();}
}

这里我设置非阻塞线程的循环是60次,大概60s完成,阻塞线程循环只有30次,大概30s完成。主要是为了测试我的阻塞线程完成后,graceful shutdown能不能保证我的异步线程安全。

  • 请求api
Administrator@USER-20230930SH MINGW64 /d/git/micro-service-logs-tracing
$ curl http://localhost:8080/api/sandwich
  • shutdown app(Ctrl+F2)
  • 查看日志
    shutdown日志

可以看到shutdown信号发出之后,两个线程都还在跑,但是阻塞线程(0-29)结束之后,异步线程也跟着终结了。它的循环应该是从0到59才算结束,但是只跑到30,所以异步线程是不安全的。

  • 验证主线程返回结果
    阻塞线程还是安全的,response正常返回了。
    api response correctly but the async thread not yet finished

其实这种测试方法并不局限于解决springboot的问题,其他微服务也是类似的。过去我看到一些朋友测试release的安全性,只是不断call health api,只要release 期间health api没有返回异常就当作ok了,其实这只能验证你的负载均衡服务的可靠性,你自己app的安全问题还是没有得到解决。
既然问题找到了,接下来我来解决它。

2. 确保优雅shutdown app时异步线程也安全

2.1 优化代码

前面的异步线程只是简单地写个野线程,并不规范,我先优化一下。

  • 把野线程放到线程池执行;
  • 利用mbean的PreDestroy来在servcie销毁前先等待异步线程完成;
  • 利用ExecutorService 的awaitTermination方法预判断异步线程的最长等待时间,等待异步线程完成,如果线程没有按时完成再强制结束。
@Slf4j
@Service
public class AsyncServiceImpl implements AsyncService {private final ExecutorService executorService;public AsyncServiceImpl() {this.executorService = Executors.newFixedThreadPool(10);}@Overridepublic void feedUserInfoToOtherServices(String userId) {executorService.execute(() -> {for (int i = 0; i < 35; i++) {log.info("async thread to update {} login info to other services, service num: {}", userId, i+1);try {Thread.sleep(1000);} catch (InterruptedException e) {throw new RuntimeException(e);}}});}@PreDestroypublic void tearDown() {if (null != executorService) {executorService.shutdown();try {if (!executorService.awaitTermination(50, TimeUnit.SECONDS)) {executorService.shutdownNow();}} catch (InterruptedException e) {log.info("PreDestroy executorService is interrupted", e);executorService.shutdownNow();}}}
}

api代码调整如下

@Slf4j
@RestController
@RequestMapping("/api")
public class DemoController {@ResourceAsyncService asyncService;@GetMapping("/{userId}")public ResultVo<Object> getUserInfo(@PathVariable String userId) throws InterruptedException {log.info("userId:{}", userId);asyncService.feedUserInfoToOtherServices(userId);for (int i = 0; i < 30; i++) {log.info("updating user info for {}, waiting times: {}", userId, i+1);Thread.sleep(1000);}return ResultVo.ok();}
}

2.2 验证shutdown过程异步线程的安全

从新代码看来,我们期待的结果是一个api请求,主线程循环从1到30,异步线程是从1到35,主线程先完成,异步线程会在AsyncServiceImpl servcie bean销毁前先等待异步线程完成。接下来是验证步骤。

  • 重启服务
  • call api
Administrator@USER-20230930SH MINGW64 /d/git/micro-service-logs-tracing
$ curl http://localhost:8080/api/sandwich
  • shutdown app(Ctrl + F2)
  • 查看日志
    异步线程安全退出日志

分析日志发现一切如代码所料,app graceful shutdown的时候,异步线程的安全性得到保障。
这个过程看起来非常完美,其实还不够完美,解决方案没最好,只有更好。请先关注我,容我研究一下,下期告诉你为什么。

http://www.yayakq.cn/news/378795/

相关文章:

  • 电子商务网站建设价格海宁市住房和城乡建设网站
  • 网站开发的私活网络营销平台排名
  • 可以做家教的网站有哪些购物商城排名
  • 网站建设漳州百度图片搜索
  • 帮别人做网站用织梦模板行吗大数据培训机构排名前十
  • ps网站建设教程做网站空间多大
  • 装修设计网站哪个好用免费制作手机网站
  • 电子商务网站域名网页设计基础课心得体会2000字
  • 企业网站开发怎么样完整网站开发
  • 青岛 网站科技公司怎样做jsp网站
  • 网站后台构建深圳市企业网站seo联系方式
  • 临沂罗庄做网站如何去建立和设计一个公司网站
  • 响应网站怎么做教学视频如何设计中文网站
  • 今天杭州新闻最新消息北京优化网站推广
  • oppo手机网站建设需求分析在线直播网站开发实战项目
  • 岳阳网站开发培训珠宝购物网站的建设
  • 漫画网站模板电话号码查询企业
  • 易语言可以做api网站对接吗163 com免费邮箱注册
  • 出售企业网站备案资料二十条优化措施全文
  • 沈阳定制网站方案学软件开发哪所学校好
  • 汽车电商网站建设上海品质网站建设
  • 做网站的实验总结沧州哪家做网站好
  • 手机移动端网站开发wordpress数据库写什么
  • 网站挂马检测流程图网页制作实训总结800字
  • 360免费建站网址是什么网络推广文案招聘
  • 做视频网站要什么软件有哪些湘潭做网站公司
  • 建设网站大概需要多少钱北京好的网站设计公司
  • 美乐乐网站源码北京网页设计公司招聘
  • 智能家居型网站开发做网站用的笔记本配置
  • 网站县区分站点建设wordpress设置图标