Skip to content

插件机制

概述

什么是插件

所谓插件,就是被框定在一个范围内,具备一定“生命周期”的功能组件。

java 插件

java的插件实现方式有很多种,常见的有:

  1. 代理模式
  2. JDBC架构
  3. Spring的Bean机制、SpringBootStarter等
  4. Maven插件
  5. IDE插件: idea、eclipse等
  6. 微服务
  7. 业务插件

本篇重点讨论 业务插件 的实现机制

设计思路

业务插件分类两类:

  1. 模块插件
  2. 应用插件

模块插件

模块插件——针对单个业务模块,抽取生命周期的插件。
例如:HR系统中,考勤模块,有自研组件,有 钉钉插件/企业微信插件/飞书插件。
主要在技术层实现。

应用插件

应用插件——整体业务体系的打包。
例如:微信的各个小程序,微信的各家公众号,360中的各种应用。
主要在业务层实现。

模块插件

我写了一套测试代码开源
下载地址: https://gitee.com/fly2world_admin/plugin-demo.git
实现思路如下:

  1. 新建插件工程 plugin
java
/**
 * 考勤插件接口
 */
public interface ClockInPlugin {

    // 安装
    void install();

    // 数据转化
    void turnData();

    // 批量导入考勤数据
    void importData();

    // 卸载
    void destory();

}
  1. 微信实现 + 钉钉实现
java
/**
 * 企业微信考勤
 */
public class WeixinClockInPluginImpl implements ClockInPlugin {

    @Override
    public void install() {
        System.out.println("企业微信-考勤安装初始化...");
    }

    @Override
    public void turnData() {
        System.out.println("企业微信-考勤数据转化");
    }

    @Override
    public void importData() {
        System.out.println("企业微信-考勤数据月度导入");
    }

    @Override
    public void destory() {
        System.out.println("企业微信-考勤卸载");
    }
}
java
/**
 * 钉钉考勤
 */
public class DingDingClockInPluginImpl implements ClockInPlugin {

    @Override
    public void install() {
        System.out.println("钉钉-考勤安装初始化...");
    }

    @Override
    public void turnData() {
        System.out.println("钉钉-考勤数据转化");
    }

    @Override
    public void importData() {
        System.out.println("钉钉-考勤数据月度导入");
    }

    @Override
    public void destory() {
        System.out.println("钉钉-考勤卸载");
    }
}
  1. 业务系统引入 业务自身实现考勤
java
/**
 * 业务系统自身实现考勤
 */
public class ClockInPluginImpl implements ClockInPlugin {

    @Override
    public void install() {
        System.out.println("本系统考勤安装初始化...");
    }

    @Override
    public void turnData() {
        System.out.println("本系统考勤数据转化");
    }

    @Override
    public void importData() {
        System.out.println("本系统考勤数据月度导入");
    }

    @Override
    public void destory() {
        System.out.println("本系统考勤卸载");
    }
}

定义考勤类型:

java
/**
 * 考勤类型
 */
public enum ClockType {
    sytem,// 系统考勤
    dingding,// 钉钉考勤
    weixin,// 企微考勤
}
java
/**
 * 考勤业务使用插件
 */
public class ClockInService {

    /**
     * 考勤执行
     */
    public void clickIn(ClockType clockType) {

        // 初始化插件
        ClockInPlugin clockInPlugin = switch (clockType) {
            case sytem -> new ClockInPluginImpl();
            case dingding -> new DingDingClockInPluginImpl();
            case weixin -> new WeixinClockInPluginImpl();
        };

        clockInPlugin.install();
        clockInPlugin.turnData();
        clockInPlugin.importData();
        clockInPlugin.destory();
    }
}

小结

以上紧紧是静态代理的一种实现,可以使用动态代理实现更强大的插件机制。
具体代码见gitee:
https://gitee.com/fly2world_admin/plugin-demo-proxy.git

java
package top.mybatisx.plugin_proxy;

import top.mybatisx.plugin_proxy.plugin.ClockInPlugin;
import top.mybatisx.plugin_proxy.plugin.ClockType;
import top.mybatisx.plugin_proxy.service.ClockInService;

import java.lang.reflect.Proxy;

/**
 * 业务使用插件
 */
public class Main {

    public static void main(String[] args) {
        // 调用考勤
        ClockType clockType = ClockType.dingding;

        // 构造动态代理
        ClockInPlugin clockInPlugin = (ClockInPlugin) Proxy.newProxyInstance(ClockInPlugin.class.getClassLoader(), new Class[]{ClockInPlugin.class}, new ClockInService(clockType));

        // 调用纯接口,更加纯粹
        clockInPlugin.install();
        clockInPlugin.turnData();
        clockInPlugin.importData();
        clockInPlugin.destory();
    }
}

应用插件

应用插件更多体现的是业务的独立性。

  1. 具备生命周期;
  2. 具备完整的业务体系;
  3. 通过Auth2.0等机制调用宿主信息,例如sso等;
  4. 微前端解决方案。 (https://qiankun.umijs.org/zh)

实现机制,后续文章来写。