1.责任链模式
先介绍基础概念:
用来处理相关事务责任的一条执行执行力链,链上的每个节点均有机会处理该请求事务,若某及诶单处理完了可以根据实际业务传递给下一个节点或者直接返回处理完毕
2.使用场景
即一个请求被多个对象所处理,具体是哪个对象在处理是运行时去动态决定的.
例如:
员工请假请求,需要多对象同意.
A经理同意–>转移到人事部门处理/审批完成了.
A经理资格不够(老子职位高)->B经理处理–>处理/转移到下一个
3.经典流程
经典流程来说,是Handler(处理者)内有下一个处理者的信息,且处理事件传递的是Request(请求).
open class Handler(
val leaveLimit: Float //能审批的时间
){
var next: Handler? = null
open fun handRequest(request: Request) {
if (request.leaveDay <= leaveLimit) {
println("${request.msg} -> 请假,$name 准了")
} else {
println("$name:超过${leaveLimit}天,让领导处理")
next?.handRequest(request)
}
}
}
fun main() {
val leader = Handler( 1f)
val manager = Handler( 30f)
//组链
leader.next = manager
leader.handRequest(Request(1f, "想休息了")) //脑热得隔离观察哈
println("-------------")
leader.handRequest(Request(14f, "出去旅游"))
println("-------------")
从上面可以看到,1天内由上头审批,14天内由经理审批.且组链,需要一步一步将对象进行next的赋值.这种方式,不够方便.
接下来我们学习一下Okhttp中的模式,在构建请求中就将链组好,让处理一步一步走下去
4.升级版流程
由上可知,我们的流程手动组链,请求构建不明朗
,用leader去处理了一个请求.主体在于leader,而不是请求.
所以我们用构造者模式去构建一个请求
,增加上责任链的处理方式,能让我们更加快乐的编码.
我们先定义两个接口
//请假的处理者
interface LeaveObject {
//处理请求函数
fun handleEvent(leaveRequest: LeaveRequest):Boolean
}
//请假请求,构造者模式
interface LeaveRequest {
val Name:String//请假人名字
val Duration:Int//需要请假的时间
fun Build():LeaveRequest
fun build()
fun AddChinaObject(chinaObject: LeaveObject):LeaveRequest
}
两个处理者的实现类,一个处理三天以下的,另一个在全部都可处理
//请假的处理者1
open class ChinaAchieve_1() :LeaveObject {
override fun handleEvent(leaveRequest: LeaveRequest):Boolean {
if(leaveRequest.Duration<3){
Log.d("TAG", "ChinaAchieve_1: 批准${leaveRequest.Name}请假,不用请求下一级了")
return true
}else{
Log.d("TAG", "ChinaAchieve_1: 批准不了,给上一级处理")
return false
}
}
}
//请假的处理者2
open class ChinaAchieve_2() :LeaveObject {
override fun handleEvent(leaveRequest: LeaveRequest):Boolean {
Log.d("TAG", "ChinaAchieve_2: 批准${leaveRequest.Name}请假")
return true
}
}
主要看我们的请假请求的实现类,
可以看到在对这个请求添加责任人的时候,用list保存起来。 build()将请求传入到处理者中
,此时若处理则整个事件处理完毕,若不处理则有请下一位受害者(皮一下).
open class LeaveRequestAchieve(override val Name: String, override val Duration: Int) :LeaveRequest{
val LeaveObjectList = ArrayList<LeaveObject>()
override fun Build():LeaveRequest {
//进行请求的初始化构建
return this
}
override fun build() {
var Finish:Boolean
for(d in LeaveObjectList){
Finish = d.handleEvent(this)
if (Finish) break
}
}
override fun AddChinaObject(chinaObject: LeaveObject): LeaveRequest {
LeaveObjectList.add(chinaObject)
return this
}
}
让我们来运行一下
main(){
LeaveRequestAchieve("Tim",1).Build().
AddChinaObject(ChinaAchieve_1()).
AddChinaObject(ChinaAchieve_2()).build()
LeaveRequestAchieve("Jix",4).Build().
AddChinaObject(ChinaAchieve_1()).
AddChinaObject(ChinaAchieve_2()).build()
}
可以看到,当Tim只请一天假,则ChinaAchieve_1已经处理了,也不用转移到下一个.若处理不了,则到第二个去处理
需要注意的是,这里添加责任链的先后顺序是有关系的
下一个问题来了,
若我们的责任链为 : 1->2->3->4->5->6
1处理完后,之后的处理者都不对该请求进行处理了.
我想1处理完之后去发送给处理者5 or 处理者6呢?
我们来看一看我们的豪华版流程
4.豪华版流程
这里多加一个功能
处理者处理后,可对该请求内可能的处理者进行分发
1->2->3->4->5->6
即1处理完后,可分发到5,或者5和6.但若请求没有5,6,则5,6都不会进行请求
稍微思考一下,上面的将所有处理者进行遍历的方法已经不适用于我们这里的需求了…所以,我们的组链方式在请求中进行组.我们只需要定义处理者的上下级关系即可.
定义两个接口,增加了可能要去通知的下一个受害者,以及本身组链的next
interface ChinaObject_Updata {
//下一位受害者
var chinaObjectNext:ChinaObject_Updata?
//成功之后要去通知的下一个受害者
var ChinaObjectList: MutableList<ChinaObject_Updata>
//处理请求函数
fun handleEvent(leaveRequest_updata: LeaveRequest_Updata,list:MutableList<ChinaObject_Updata>)
}
//请假请求_升级
interface LeaveRequest_Updata {
val Name:String
val Duration:Int
fun Build():LeaveRequest_Updata
fun build()
fun AddChinaObject(chinaObject_updata: ChinaObject_Updata):LeaveRequest_Updata
}
实现我们的请求接口。
链头:责任链的头部(梦开始的地方)
链列表:责任链的全部处理者
暂存链头:用来组链的
open class ChinaAchieve_Updata(override val Name: String, override val Duration: Int) :LeaveRequest_Updata {
var FirstChina:ChinaObject_Updata ?=null
var Now:ChinaObject_Updata ?=null
val LeaveObjectList = ArrayList<ChinaObject_Updata>()
override fun Build(): LeaveRequest_Updata {
return this
}
override fun build() {
FirstChina?.handleEvent(this,LeaveObjectList)
}
override fun AddChinaObject(chinaObject_updata: ChinaObject_Updata): LeaveRequest_Updata {
//组链
if(Now ==null){
Now = chinaObject_updata
}else{
Now?.chinaObjectNext=chinaObject_updata
Now = chinaObject_updata
}
if(FirstChina==null){FirstChina= chinaObject_updata}
LeaveObjectList.add(chinaObject_updata)
return this
}
}
实现多个处理者接口,当然你自己可以将它根据业务封装的好一些,这里就不多写了。 也让自己看的清楚一些.
我们具体看处理者1:当拿到整条责任链,且自己处理过后,则把属于自己的责任给删除(推锅了,宝贝).之后看是否属于应该自己处理,以及处理之后是否需要分发给下一个处理人.
例如,1->2->3->4->5->6
处理人1应该处理该 请求 ,处理过后将跳过处理2,3,将请求继续发送到5,让5继续处理.
open class ChinaObject_UpdataFinal(
override var chinaObjectNext: ChinaObject_Updata?,
) :ChinaObject_Updata{
override var ChinaObjectList: MutableList<ChinaObject_Updata> = ArrayList()
override fun handleEvent(
leaveRequest_updata: LeaveRequest_Updata,
list: MutableList<ChinaObject_Updata>
) {
Log.d("TAG", "ChinaObject_UpdataFinal: 最终处理Final 一个无人处理的东西")
}
}
open class ChinaObject_Updata1() :ChinaObject_Updata{
override var ChinaObjectList: MutableList<ChinaObject_Updata> = ArrayList()//要发送的下一位受害者列表
override var chinaObjectNext: ChinaObject_Updata? = ChinaObject_UpdataFinal(null)//默认下一个为final
override fun handleEvent(leaveRequest: LeaveRequest_Updata,list:MutableList<ChinaObject_Updata>) {
list.remove(this)//自己处理过了,remove自己
if(leaveRequest.Duration==1){
//处理了
Log.d("TAG", "ChinaAchieve_1: 批准${leaveRequest.Name}请假")
//处理完,判断是否要给更高级的领导
// 可能这个请求内添加的责任人,不需要向更高级的处理了(处理请求中不包括这个的更高处理)
if (list.containsAll( ChinaObjectList ) ){
for(d in ChinaObjectList){
Log.d("TAG", "ChinaAchieve_1: 继续请求下一级了")
d.handleEvent(leaveRequest,list)
}
}
}else{
chinaObjectNext?.handleEvent(leaveRequest,list)
}
}
}
open class ChinaObject_Updata2() :ChinaObject_Updata{
override var ChinaObjectList: MutableList<ChinaObject_Updata> = ArrayList()//要发送的下一位受害者列表
override var chinaObjectNext: ChinaObject_Updata? = ChinaObject_UpdataFinal(null)//默认下一个为final
override fun handleEvent(leaveRequest: LeaveRequest_Updata,list:MutableList<ChinaObject_Updata>) {
list.remove(this)//自己处理过了,remove自己
if(leaveRequest.Duration==2){
//处理了
Log.d("TAG", "ChinaObject_Updata2: 批准${leaveRequest.Name}请假")
//处理完,判断是否要给更高级的领导
// 可能这个请求内添加的责任人,不需要向更高级的处理了(处理请求中不包括这个的更高处理)
if (list.containsAll( ChinaObjectList ) ){
for(d in ChinaObjectList){
Log.d("TAG", "ChinaObject_Updata2: 继续请求下一级了")
d.handleEvent(leaveRequest,list)
}
}
}else{
chinaObjectNext?.handleEvent(leaveRequest,list)
}
}
}
open class ChinaObject_Updata3() :ChinaObject_Updata{
override var ChinaObjectList: MutableList<ChinaObject_Updata> = ArrayList()//要发送的下一位受害者列表
override var chinaObjectNext: ChinaObject_Updata? = ChinaObject_UpdataFinal(null)//默认下一个为final
override fun handleEvent(leaveRequest: LeaveRequest_Updata,list:MutableList<ChinaObject_Updata>) {
list.remove(this)//自己处理过了,remove自己
if(leaveRequest.Duration==3){
//处理了
Log.d("TAG", "ChinaObject_Updata3: 批准${leaveRequest.Name}请假")
//处理完,判断是否要给更高级的领导
// 可能这个请求内添加的责任人,不需要向更高级的处理了(处理请求中不包括这个的更高处理)
if (list.containsAll( ChinaObjectList ) ){
for(d in ChinaObjectList){
Log.d("TAG", "ChinaObject_Updata3: 继续请求下一级了")
d.handleEvent(leaveRequest,list)
}
}
}else{
chinaObjectNext?.handleEvent(leaveRequest,list)
}
}
}
open class ChinaObject_Updata4() :ChinaObject_Updata{
override var ChinaObjectList: MutableList<ChinaObject_Updata> = ArrayList()//要发送的下一位受害者列表
override var chinaObjectNext: ChinaObject_Updata? = ChinaObject_UpdataFinal(null)//默认下一个为final
override fun handleEvent(leaveRequest: LeaveRequest_Updata,list:MutableList<ChinaObject_Updata>) {
list.remove(this)//自己处理过了,remove自己
if(leaveRequest.Duration==4){
//处理了
Log.d("TAG", "ChinaObject_Updata4: 批准${leaveRequest.Name}请假")
//无值返回,可以开启异步再去向下一个受害者继续处理节点.
//处理完,判断是否要给更高级的领导
// 可能这个请求内添加的责任人,不需要向更高级的处理了(处理请求中不包括这个的更高处理)
if (list.containsAll( ChinaObjectList ) ){
for(d in ChinaObjectList){
Log.d("TAG", "ChinaObject_Updata4: 继续请求下一级了")
d.handleEvent(leaveRequest,list)
}
}
}else{
chinaObjectNext?.handleEvent(leaveRequest,list)
}
}
}
open class ChinaObject_Updata5() :ChinaObject_Updata{
override var ChinaObjectList: MutableList<ChinaObject_Updata> = ArrayList()//要发送的下一位受害者列表
override var chinaObjectNext: ChinaObject_Updata? = ChinaObject_UpdataFinal(null)//默认下一个为final
override fun handleEvent(leaveRequest: LeaveRequest_Updata,list:MutableList<ChinaObject_Updata>) {
list.remove(this)//自己处理过了,remove自己
if(leaveRequest.Name.equals("Tim") ){
//处理了
Log.d("TAG", "ChinaObject_Updata5: 转移到人事部门处理.")
//处理完,判断是否要给更高级的领导
// 可能这个请求内添加的责任人,不需要向更高级的处理了(处理请求中不包括这个的更高处理)
if (list.containsAll( ChinaObjectList ) ){
for(d in ChinaObjectList){
Log.d("TAG", "ChinaObject_Updata5: 继续请求下一级了")
d.handleEvent(leaveRequest,list)
}
}
}
else{
//下一位人事处理
chinaObjectNext?.handleEvent(leaveRequest,list)
}
}
}
让我们来调用一下
main(){
val p = ChinaObject_Updata1()
val pp = ChinaObject_Updata5()
val gg = ArrayList<ChinaObject_Updata>()
gg.add(pp)
p.ChinaObjectList = gg
ChinaAchieve_Updata("Tim",1).Build().
AddChinaObject(p).
AddChinaObject(ChinaObject_Updata2()).
AddChinaObject(ChinaObject_Updata3()).
AddChinaObject(ChinaObject_Updata4()).build()
ChinaAchieve_Updata("Tim",1).Build().
AddChinaObject(p).
AddChinaObject(ChinaObject_Updata2()).
AddChinaObject(ChinaObject_Updata3()).
AddChinaObject(ChinaObject_Updata4()).
AddChinaObject(pp).build()
}
Result:
好了,一个请求,在没有责任人5之前是不会进行转发的.如果有,且处理人1需要责任转发的时候,则会进行转发.
好了, 一个基本的责任链模式已经写好了,如果喜欢请点个赞~