通过Dapr实现一个简单的基于.net的微服务电商系统(四)——一步一步教你如何撸Dapr之订阅发布
之前的章节我们介绍了如何通过dapr发起一个服务调用,相信看过前几章的小伙伴已经对dapr有一个基本的了解了,今天我们来聊一聊dapr的另外一个功能——订阅发布
目录:
一、通过Dapr实现一个简单的基于.net的微服务电商系统
二、通过Dapr实现一个简单的基于.net的微服务电商系统(二)——通讯框架讲解
三、通过Dapr实现一个简单的基于.net的微服务电商系统(三)——一步一步教你如何撸Dapr
四、通过Dapr实现一个简单的基于.net的微服务电商系统(四)——一步一步教你如何撸Dapr之订阅发布
附录:(如果你觉得对你有用,请给个star)
一、电商Demo地址
惯例我们还是再老生常谈一下什么是订阅发布,订阅发布是根据设计模式之观察者模式发展出来的一种软件系统设计思想,它的核心是指“多个对象间存在一对多的依赖关系,当一个对象的状态发生改变时,所有依赖于它的对象都得到通知并被自动更新”。假设一个系统有ABC三个模块其中BC依赖于A,当A进行改变后需要A主动调用BC进行相应改变,而观察者模式则将A的控制权剥离,A改变之后只是发送一个事件给消息总线“我改变了”,BC通过预先订阅该主题而获取到A的状态变化,再进行自身的状态变更。

强耦合调用模式

通过消息中间件订阅发布模式
聪明的同学应该发现了,通过订阅发布其实我们是将以往强耦合的ABC通过巧妙的控制权转移的方式进行了解耦,由之前的BC依赖于A改为了BC依赖于消息组件,通过消息组件接受到A的消息后进行分发,这样设计系统的目的当然有好有坏,好处是这会大大提高A的吞吐量,假设以往操作ABC总耗时300ms平均单个操作耗时100ms,通过解耦后A耗时100ms后就可以马上返回线程。那坏处是什么呢,由于对BC进行了解耦往往状态的一致性就得不到保障了。当ABC处于同一个粗粒度的原子操作里(比如数据库事务操作、比如lock锁),我们很容易控制ABC的强一致性,ABC有一个操作失败可以很轻松的进行回滚而不用影响我们持久化设备的数据一致。另外由于需要依赖第三方中间件,整个系统的健壮性是会有一定影响的。另外还需要考虑订阅方消费失败、异常后如何处理。关于这部分内容这里我们就不展开了,如果大家确实感兴趣,推荐大家看看国内开源作者@杨晓东写的.netcore分布式一致性解决方案CAP,地址:https://github.com/dotnetcore/cap
OK,老生常谈的部分唠完,咱今天就来唠唠在Dapr中如何实现订阅发布的。通过上面的部分大家应该知道如果要实现一个进程间的订阅发布系统,我们需要准备很多东西,其中一个是事件总线,事件总线的作用是让事件发布者可以通过该模块进行事件发布。第二个需要选型一个消息组件,第三需要订阅器对订阅特定类型组件的技术支持。由于每一种组件其协议和接口实现方式都不同,在传统的订阅发布设计中我们往往需要对某种特定类型的消息组件在基础设施层进行相应的SDK集成,通过为业务层提供事件总线接口和订阅接口来进行技术解耦。就算做到了业务系统中不耦合技术实现,往往我们也很难替换消息组件。而Dapr在这方面为开发者集成了相当一部分的主流订阅发布组件(通过该支持列表可预览支持)。同时在业务层面是完全基于http+谓词的形式来实现订阅发布的。这就大大降低了引入SDK产生的成本。
订阅发布的API如下:
POST http://localhost:<daprPort>/v1.0/publish/<pubsubname>/<topic>[?<metadata>]
GET http://localhost:<appPort>/dapr/subscribe
稍微说一下这两个接口的含义,第一个接口告诉sidecar,我们将会调用某个已申明的类型为pubsub的component发送我们的事件到特定的topic
第二个接口是告诉sidecar我们当前这个服务会订阅哪些topic,我们提供的订阅器入口地址是什么,我们只接受哪一个component发布的数据
也就是说和服务调用一样,我们只需要一个weapi+httpclient就可以实现一个订阅发布模式而,其他的一切都交给dapr好了。
现在我们来看看如何实现它,首先我们还是需要选一个特定的订阅发布组件,这里我就选择redis,通过redis5.0新增的stream来做订阅发布。搭建redis这里不赘述,搭建好之后,我们需要创建一个dapr的特定CRD Component来申明引用该组件,其申明yaml文件如下
apiVersion: dapr.io/v1alpha1
kind: Component
metadata:
name: pubsub
spec:
type: pubsub.redis
version: v1
metadata:
- name: redisHost
value: redis.infrastructure.svc.cluster.local:6379
其中的type是由Dapr预定义的,可以参考这里,不要随意改变。metadata是对组件的一组描述包括其地址、账号密码等等,由于是演示这里我就直接使用k8s创建了一个无密码的redis pod并暴露其6379端口到svc。当我们创建好并通过kubectl apply -f x.yaml后,可以在dashboard的Componsents页面观察是否已经创建成功

基础设施准备完毕,接下来就是打开我们的项目看看如何实现订阅发布了。首先我们还是要把上一章的解决方案打开,上一章不是通过client发起一个对service的调用吗,今天我们反着来演示,我们在client创建一个订阅器,当clientsample调用servicesample时让servicesample发布一个事件,由该订阅器订阅并打印出文本到控制台。
首先我们在clientsample创建一个订阅器,订阅器类必须继承ieventhandle接口,其订阅方法体必须添加EventHandlerFunc注解并申明需要订阅的主题(topic),订阅器接收参数必须以EventHandleRequest<T>的方式接收,否则反序列化器可能会收不到请求。最后ack必须以DefaultEventHandlerResponse.Default的方式返回,否则事件总线会认为本次订阅器消费失败,会重复推送。

需要在我们的hostbuilder里注册这个对象到ioc容器:

接着我们在RPC接口项目创建事件Data HelloEventData,其中之包含一个演示用的words字段(图略)。
接下来我们在上一章的HelloServiceImpl中注入一个事件总线,并发送事件:

一切就绪,我们重新按照上一章的内容打包并部署,然后开启postman和控制台日志观看结果,可以看到我们的clientsample发起一个服务调用后,我们的serversample回调并发送了事件,而clientsample成功订阅到了该事件并消费掉了。

今天的分享到此为止,demo只是对dapr订阅发布最基础功能的演示,真正到生产环境还需要客服诸多问题来提高系统健壮,系统建设是一个长期持续的过程。欢迎大家评论区留言讨论~ 下期我们将讲一下dapr里如何做状态管理以及actor模型
通过Dapr实现一个简单的基于.net的微服务电商系统(四)——一步一步教你如何撸Dapr之订阅发布的更多相关文章
- 通过Dapr实现一个简单的基于.net的微服务电商系统
本来想在Dpar 1.0GA时发布这篇文章,由于其他事情耽搁了放到现在.时下微服务和云原生技术如何如荼,微软也不甘示弱的和阿里一起适时推出了Dapr(https://dapr.io/),园子里关于da ...
- 通过Dapr实现一个简单的基于.net的微服务电商系统(二)——通讯框架讲解
首先感谢张队@geffzhang公众号转发了上一篇文章,希望广大.neter多多推广dapr,让云原生更快更好的在.net这片土地上落地生根. 目录:一.通过Dapr实现一个简单的基于.net的微服务 ...
- 通过Dapr实现一个简单的基于.net的微服务电商系统(三)——一步一步教你如何撸Dapr
目录:一.通过Dapr实现一个简单的基于.net的微服务电商系统 二.通过Dapr实现一个简单的基于.net的微服务电商系统(二)--通讯框架讲解 三.通过Dapr实现一个简单的基于.net的微服务电 ...
- 通过Dapr实现一个简单的基于.net的微服务电商系统(五)——一步一步教你如何撸Dapr之状态管理
状态管理和上一章的订阅发布都算是Dapr相较于其他服务网格框架来讲提供的比较特异性的内容,今天我们来讲讲状态管理. 目录:一.通过Dapr实现一个简单的基于.net的微服务电商系统 二.通过Dapr实 ...
- 通过Dapr实现一个简单的基于.net的微服务电商系统(六)——一步一步教你如何撸Dapr之Actor服务
我个人认为Actor应该是Dapr里比较重头的部分也是Dapr一直在讲的所谓"stateful applications"真正具体的一个实现(个人认为),上一章讲到有状态服务可能很 ...
- 通过Dapr实现一个简单的基于.net的微服务电商系统(七)——一步一步教你如何撸Dapr之服务限流
在一般的互联网应用中限流是一个比较常见的场景,也有很多常见的方式可以实现对应用的限流比如通过令牌桶通过滑动窗口等等方式都可以实现,也可以在整个请求流程中进行限流比如客户端限流就是在客户端通过随机数直接 ...
- 通过Dapr实现一个简单的基于.net的微服务电商系统(八)——一步一步教你如何撸Dapr之链路追踪
Dapr提供了一些开箱即用的分布式链路追踪解决方案,今天我们来讲一讲如何通过dapr的configuration来实现非侵入式链路追踪的 目录:一.通过Dapr实现一个简单的基于.net的微服务电商系 ...
- 通过Dapr实现一个简单的基于.net的微服务电商系统(九)——一步一步教你如何撸Dapr之OAuth2授权
Oauth2授权,熟悉微信开发的同学对这个东西应该不陌生吧.当我们的应用系统需要集成第三方授权时一般都会做oauth集成,今天就来看看在Dapr的语境下我们如何仅通过配置无需修改应用程序的方式让第三方 ...
- 通过Dapr实现一个简单的基于.net的微服务电商系统(十)——一步一步教你如何撸Dapr之绑定
如果说Actor是dapr有状态服务的内部体现的话,那绑定应该是dapr对serverless这部分的体现了.我们可以通过绑定极大的扩展应用的能力,甚至未来会成为serverless的基础.最开始接触 ...
随机推荐
- django学习-21.优化表数据的标题展示
目录结构 1.前言 2.表数据的标题默认展示的数据格式是[模型类名 object(主键名)]的相关信息 3.优化表数据的标题展示的数据格式是[改成我们想要展示的数据格式]的相关完整操作步骤 3.1.第 ...
- 将项目加载到tomcat中的时候报错:Tomcat version 6.0 only supports J2EE 1.2, 1.3, 1.4, and Java EE 5 Web modules
转自:http://jingwang0523.blog.163.com/blog/static/9090710320113294551497/ 最近在用eclipse做项目,新建项目时什么都贪新,用最 ...
- 代码安全性和健壮性:如何在if和assert中做选择?
道哥的第 023 篇原创 目录 一.前言 二.assert 断言 assert 是一个宏,不是一个函数 三.if VS assert 1. 使用 if 语句来检查 2. 使用 assert 断言来检查 ...
- linux 安装软件步骤
1,下载wget http://www.erlang.org/download/otp_src_R16B02.tar.gz2,解压 tar -zxvf otp_src_R16B02.tar.gz3,编 ...
- 【HTB系列】 靶机Swagshop的渗透测试详解
出品|MS08067实验室(www.ms08067.com) 本文作者:是大方子(Ms08067实验室核心成员) 总结与反思 使用vi提权 magento漏洞的利用 magescan 工具的使用 靶机 ...
- WPF 应用 - 在 web 中启动 exe
以下 F:/Debug/xx.exe 为客户端路径. 1. Web 调用 1.1 IE 内核的浏览器调用方式 js 函数调用如下: var a=new ActiveXObject("Wscr ...
- web实现时钟效果
纯原生开发时钟效果,话不多说直接上代码. HTML标签部分 <div class="cricles"> <div class="poin ...
- mybatis&plus系列------Mysql的JSON字段的读取和转换
mybatis&plus系列------Mysql的JSON字段的读取和转换 一. 背景 在平常的开发中,我们可能会有这样的需求: 业务数据在存储的时候,并不是以mysql中的varchar丶 ...
- nginx使用-1(源码安装nginx)
Nginx概述 Nginx (engine x) 是一个高性能的HTTP和反向代理web服务器,同时也提供了IMAP/POP3/SMTP服务.Nginx是由伊戈尔·赛索耶夫为俄罗斯访问量第二的Ramb ...
- 微信小程序--简约风博客小程序(基于云开发 - 全开源)
微信小程序--简约风博客小程序(基于云开发 - 全开源) 项目启动纯属突发奇想,想看看博客小程序,例如wehalo博客小程序,但是感觉自建平台还要浪费自己的服务器算力,还没有访问量,省省吧. 本着白嫖 ...