在设计程序的许多应用场景中我们会遇到大体分为三个阶段的任务流。

第一、入口

一个或多个入口,等待阻塞的、或者主动请求方式的。

==============================

比如任务流需要接受来自于 HTTP 和 FTP 的应用请求,后续还有可能增加别的方式的接受请求。

第二、处理

多个入口可以对应一个处理程序,也可以对应多个处理程序。

==================================

比如 HTTP 和 FTP 的多个入口程序需要对应一个和多个处理逻辑,同样也面临着增加处理程序的扩展性问题。

第三、出口

多个处理程序或者一个处理程序对应多个出口或者一个出口。

==================================

比如报警方式有邮件报警、微信报警等等,后续还有可能增加短信报警等等。

事实上可以把绝大部分需求可以抽象成上述思维。

那么对于这类问题我们采取的扩展性要求是,拓展功能时改动少量原有代码或者干脆不改动原有代码。在不考虑软件重构层面,当新入职员工接手上位大哥的代码时,我想最头疼的就是增加需求,因为你不知道更改代码会带来什么隐藏 BUG。

我们总是理想可以用"插件化"的思想来适应需求,写好框架,然后分门别类,每一个抽象出来的角色是一个大的容器,然后每次向这个容器中插一个个的插件,来一个需求,做一个插件插进去。来两个需求,做两个插件插一双进去。

更"过分"的要求是插进去插件必须有一个按钮来控制是不是启用该插件,理由就是拔插一次插件太耗时了(对应代码中的注释 N 多行)。

总之一切的一切我们想要的效果就是每一个插件独立工作,互不相应,增加可拓展性。这样带来的弊端就是可能有一部分的冗余代码,但是这样也比交接出去工作让人家天天在背后黑你要强的多吧。

那首先我们先用 golang 来造出一个需求容器。

package need

import (
"fmt"
) var (
Plugins map[string]Need
) func init() {
Plugins = make(map[string]Need)
} type Need interface {
Flag() bool // 必须告诉容器是否启动
Start() //必须有启动方法
} func Start() {
for name, plugin := range Plugins {
if plugin.Flag() {
go plugin.Start()
fmt.Printf("启动插件%s\n", name)
} else {
fmt.Printf("不启动插件%s\n", name)
}
}
} //每个插件在初始化时必须注册
func Register(name string, plugin Need) {
Plugins[name] = plugin
}

  

这个需求容器对插入自己的插件有要求!

  1. 必须告诉容器插件本身是不是正常的
  2. 必须提供你插件本身的工作内容
  3. 必须与容器进行连接

如果缺少 1,那么就无法实现插件生病就放病假。

如果缺少 2,你说你不说你是干啥的容器怎么敢收你,万一是贩毒的咋办~

如果缺少 3,得与容器签订合同,绑定劳动关系。

按照上述要求,我们来实现一个插件一号。

package node

import (
"fmt"
"go_dev/plugin/need"
) func init() {
p1 := plugin1{}
need.Register("plugin1", p1)
} type plugin1 struct {
} func (p plugin1) Flag() bool {
return true
} func (p plugin1) Start() {
fmt.Println("我是插件一号")
}

  

现在是容器也有了,插件也有了,但是没电跑不起来啊。。。,我们现在再用 golang 给他提供个电源。

package main

import (
"go_dev/plugin/need"
_ "go_dev/plugin/node"
) func main() {
need.Start()
}

  

go interface衍生的插件化处理的更多相关文章

  1. Android架构设计之插件化、组件化

    如今移动app市场已经是百花齐放,其中有不乏有很多大型公司.巨型公司都是通过app创业发展起来的:app类型更加丰富,有电子商务.有视频.有社交.有工具等等,基本上涵盖了各行各业每个角落,为了更加具有 ...

  2. Winform开发框架之插件化应用框架实现

    支持插件化应用的开发框架能给程序带来无穷的生命力,也是目前很多系统.程序追求的重要方向之一,插件化的模块,在遵循一定的接口标准的基础上,可以实现快速集成,也就是所谓的热插拔操作,可以无限对已经开发好系 ...

  3. 如何写一个c++插件化系统

    1.为什么需要插件化系统 “编程就是构建一个一个自己的小积木, 然后用自己的小积木搭建大系统”. 但是程序还是会比积木要复杂, 我们的系统必须要保证小积木能搭建出大的系统(必须能被组合),有必须能使各 ...

  4. iOS插件化研究之中的一个——JavaScriptCore

    原文:p=191">http://chentoo.com/?p=191 一.前言 一样的开篇问题,为什么要研究这个?iOS为什么要插件化?为什么要借助其它语言比方html5 js甚至脚 ...

  5. Android插件化开发---执行未安装apk中的Service

    欢迎各位增加我的Android开发群[257053751​] 假设你还不知道什么叫插件化开发.那么你应该先读一读之前写的这篇博客:Android插件化开发,初入殿堂 上一篇博客主要从总体角度分析了一下 ...

  6. 小白也能看懂插件化DroidPlugin原理(一)-- 动态代理

    前言:插件化在Android开发中的优点不言而喻,也有很多文章介绍插件化的优势,所以在此不再赘述.前一阵子在项目中用到 DroidPlugin 插件框架 ,近期准备投入生产环境时出现了一些小问题,所以 ...

  7. 小白也能看懂的插件化DroidPlugin原理(二)-- 反射机制和Hook入门

    前言:在上一篇博文<小白也能看懂的插件化DroidPlugin原理(一)-- 动态代理>中详细介绍了 DroidPlugin 原理中涉及到的动态代理模式,看完上篇博文后你就会发现原来动态代 ...

  8. Android动态加载技术(插件化技术)

    No1: 插件化技术的好处: 1)减轻应用的内存和CPU占用 2)实现热插拔,即在不发布新版本的情况下更新某些模块 No2: 插件化方案必须要解决三个基础性问题:资源访问.Activity生命周期的管 ...

  9. Android插件化的兼容性(中):Android P的适配

    Android系统的每次版本升级,都会对原有代码进行重构,这就为插件化带来了麻烦. Android P对插件化的影响,主要体现在两方面,一是它重构了H类中Activity相关的逻辑,另一个是它重构了I ...

随机推荐

  1. yii DAO操作总结

    数据库代码: /* Navicat MySQL Data Transfer Source Server         : lonxom Source Server Version : 50524 S ...

  2. Python中的字符编码

    一.文本编辑器存取文件的原理: #1.打开编辑器就打开了启动了一个进程,是在内存中的,所以,用编辑器编写的内容也都是存放与内存中的,断电后数据丢失 #2.要想永久保存,需要点击保存按钮:编辑器把内存的 ...

  3. 浅说——状压DP

    第一次没认真听,没听懂.(有点难) 第二次才搞懂,主要位运算太烦了!!! 位运算基础知识: 名称 符号 规则 按位与 & 全一则一,否则为零 按位或 | 有一则一,否则为零 按位取反 ~ 是零 ...

  4. ZOJ 3981:Balloon Robot(思维+递推)

    题目链接 题意 有n支队在m个位置上做题,有一个机器人位置1到位置m再到位置1循环走派发气球,当队伍a在时间b做完了一道题目的时候,假如机器人走到队伍a的位置的时间为c,那么这个队伍的不开心值就是c- ...

  5. POJ 3680:Intervals(最小费用最大流)***

    http://poj.org/problem?id=3680 题意:给出n个区间[Li,Ri],每个区间有一个权值wi,要使得每个点都不被超过k个区间覆盖(最多能被k个区间覆盖),如果选取了第i个区间 ...

  6. HDU 4819:Mosaic(线段树套线段树)

    http://acm.hdu.edu.cn/showproblem.php?pid=4819 题意:给出一个矩阵,然后q个询问,每个询问有a,b,c,代表(a,b)这个点上下左右c/2的矩形区域内的( ...

  7. 玩转SpringBoot之MyBatisplus自动化构建工具

    使用MyBatisplus自动化构建项目 为什么要用这个? 方便 因为之前那种方式让我用起来不爽了:mybatis逆向工程(MyBatis Generator) 能紧密的贴合mybatis,并且MyB ...

  8. c++ 广度优先搜索(宽搜)

    c++ bfs基本应用 Knight Moves 题目描述 贝茜和她的表妹在玩一个简化版的国际象棋.棋盘如图所示: 贝茜和表妹各有一颗棋子.棋子每次移一步,且棋子只能往如图所示的八个方向移动.比赛的规 ...

  9. 解决Tomcat catalina.out 不断膨胀,导致磁盘占用过大的问题

    到服务器上看了一下任务中心的日志情况,膨胀的很快,必须采取措施限制其增长速度. 我们采用Cronlog组件对此进行日志切分,官网http://cronolog.org/一直未能打开,只能从其它地方寻找 ...

  10. Zeppelin 0.6.2使用Spark的yarn-client模式

    Zeppelin版本0.6.2 1. Export SPARK_HOME In conf/zeppelin-env.sh, export SPARK_HOME environment variable ...