14-第14章-扩展点与插件机制

第14章:扩展点与插件机制

14.1 扩展点设计

14.1.1 系统扩展点

sfsEdgeStore 设计了多个扩展点,允许在不修改核心代码的情况下扩展功能:

扩展点 位置 说明
数据接收前 MQTT 消息处理器 消息到达后、存储前
数据存储前 数据库写入前 数据验证、转换
数据查询后 HTTP 响应前 查询结果转换、过滤
监控数据 监控模块 自定义监控指标
告警触发 告警模块 自定义告警规则

14.1.2 Hook 接口设计

go 复制代码
package hooks

type Hook interface {
    Name() string
    Priority() int
}

type PreMessageHook interface {
    Hook
    PreProcess(payload []byte) ([]byte, error)
}

type PreStoreHook interface {
    Hook
    PreStore(records []*map[string]interface{}) ([]*map[string]interface{}, error)
}

type PostQueryHook interface {
    Hook
    PostQuery(records record.Records) (record.Records, error)
}

type MonitorHook interface {
    Hook
    OnMetrics(metrics *monitor.Metrics) error
}

type AlertHook interface {
    Hook
    OnAlert(alert *alert.Alert) error
}

14.2 插件系统

14.2.1 插件加载器

go 复制代码
package plugin

import (
    "plugin"
    "sync"
)

type Plugin interface {
    Name() string
    Version() string
    Init() error
    Shutdown() error
}

type Manager struct {
    plugins map[string]Plugin
    mu      sync.RWMutex
}

func NewManager() *Manager {
    return &Manager{
        plugins: make(map[string]Plugin),
    }
}

func (m *Manager) LoadPlugin(path string) error {
    p, err := plugin.Open(path)
    if err != nil {
        return err
    }
    
    sym, err := p.Lookup("Plugin")
    if err != nil {
        return err
    }
    
    plugin, ok := sym.(Plugin)
    if !ok {
        return fmt.Errorf("unexpected type from module symbol")
    }
    
    if err := plugin.Init(); err != nil {
        return err
    }
    
    m.mu.Lock()
    m.plugins[plugin.Name()] = plugin
    m.mu.Unlock()
    
    return nil
}

func (m *Manager) GetPlugin(name string) (Plugin, bool) {
    m.mu.RLock()
    defer m.mu.RUnlock()
    p, ok := m.plugins[name]
    return p, ok
}

func (m *Manager) ShutdownAll() {
    m.mu.Lock()
    defer m.mu.Unlock()
    
    for name, p := range m.plugins {
        if err := p.Shutdown(); err != nil {
            log.Printf("Error shutting down plugin %s: %v", name, err)
        }
        delete(m.plugins, name)
    }
}

14.2.2 创建插件

go 复制代码
// 插件示例:myplugin.go
package main

import (
    "log"
    "sfsEdgeStore/plugin"
    "sfsEdgeStore/hooks"
)

type MyPlugin struct{}

func (p *MyPlugin) Name() string {
    return "my-plugin"
}

func (p *MyPlugin) Version() string {
    return "1.0.0"
}

func (p *MyPlugin) Init() error {
    log.Println("My plugin initialized")
    hooks.RegisterPreStoreHook(&MyPreStoreHook{})
    return nil
}

func (p *MyPlugin) Shutdown() error {
    log.Println("My plugin shutdown")
    return nil
}

type MyPreStoreHook struct{}

func (h *MyPreStoreHook) Name() string {
    return "my-pre-store"
}

func (h *MyPreStoreHook) Priority() int {
    return 100
}

func (h *MyPreStoreHook) PreStore(records []*map[string]interface{}) ([]*map[string]interface{}, error) {
    log.Printf("PreStore hook called with %d records", len(records))
    for _, record := range records {
        if processed, ok := (*record)["processed"]; !ok || !processed.(bool) {
            (*record)["processed"] = true
            (*record)["processed_at"] = time.Now().UnixNano()
        }
    }
    return records, nil
}

var Plugin MyPlugin

14.2.3 编译插件

bash 复制代码
# 编译为共享库
go build -buildmode=plugin -o myplugin.so myplugin.go

# 在主程序中加载
pluginManager := plugin.NewManager()
err := pluginManager.LoadPlugin("./myplugin.so")

14.3 实战练习

练习 14.1:Hook 开发

开发一个 PreMessageHook,对消息进行解密。

练习 14.2:插件开发

开发一个完整的插件,包含多个 Hook。

练习 14.3:热重载

实现插件的热重载功能。

14.4 本章小结

本章讲解了系统的扩展点和插件机制:

  • 系统扩展点设计
  • Hook 接口定义
  • 插件系统实现
  • 如何开发和加载插件

插件机制让系统具有极强的扩展性。


本书版本 :1.0.0
最后更新 :2026-03-08
sfsEdgeStore - 让边缘数据存储更简单!🚀
技术栈 - Go语言、sfsDb与EdgeX Foundry。纯golang工业物联网边缘计算技术栈
项目地址GitHub
GitCode 镜像GitCode

相关推荐
Rocktech_ruixun6 小时前
机器人本地跑LLM大模型对主板硬件有什么要求?瑞迅科技RK3588/3568方案选型解析
人工智能·科技·嵌入式硬件·机器人·边缘计算
Dola_Zou6 小时前
工厂智能排产软件算法保护与按产线计费实战
算法·自动化·软件工程·软件加密
tedcloud1237 小时前
Wand-Enhancer 怎么搭建?开源 Wand 客户端增强与远程控制工具介绍
大数据·服务器·人工智能·开源·音视频
紫_龙7 小时前
12软考备课基础阶段考点理论精讲数据库基础
软件工程
嘉琪coder7 小时前
我做了一个 Chrome 扩展,把 YouTube 播放列表批量变成 AI 可读的本地 Markdown
chrome·开源·浏览器
游戏开发爱好者87 小时前
网络连接排查指南,谁在电脑后台偷跑流量,哪些程序在联网
网络协议·计算机网络·网络安全·ios·adb·https·udp
ii_best9 小时前
安卓脚本/ios开发软件按键精灵实战:自动定位弹窗广告关闭按钮坐标的通用方案
android·ios·自动化
冬奇Lab10 小时前
一天一个开源项目(第214篇):AstronRPA —— 科大讯飞开源的企业级 RPA + AI Agent 自动化平台
人工智能·开源·资讯
Behaviour10 小时前
iPhone Duo 来了,苹果 Siri AI 接入定制 Gemini
人工智能·ios·语言模型·aigc·iphone
郝学胜-神的一滴11 小时前
C++11 工程级应用 09:告别无谓拷贝,解锁高性能移动语义
开发语言·数据结构·c++·vscode·软件工程·visual studio