我的编程空间,编程开发者的网络收藏夹
学习永远不晚

MySQL插件调用

短信预约 -IT技能 免费直播动态提醒
省份

北京

  • 北京
  • 上海
  • 天津
  • 重庆
  • 河北
  • 山东
  • 辽宁
  • 黑龙江
  • 吉林
  • 甘肃
  • 青海
  • 河南
  • 江苏
  • 湖北
  • 湖南
  • 江西
  • 浙江
  • 广东
  • 云南
  • 福建
  • 海南
  • 山西
  • 四川
  • 陕西
  • 贵州
  • 安徽
  • 广西
  • 内蒙
  • 西藏
  • 新疆
  • 宁夏
  • 兵团
手机号立即预约

请填写图片验证码后获取短信验证码

看不清楚,换张图片

免费获取短信验证码

MySQL插件调用


简单记录以备学习,如果有误请指出。


一、核心类

  • Observer_info:观察者 rpl_handler.h


class Observer_info {  //插件观察者public:  void *observer; //这个void指针是具体的观察者,使用指针函数实现多态
  st_plugin_int *plugin_int;  plugin_ref plugin  Observer_info(void *ob, st_plugin_int *p);
};
  • 实际观察者
    及void* 指向的对象,其中全部都是函数指针,这里通过函数指针指向了具体的函数,实现了插件的功能。其中的函数指针指向的实际函数就是需要用户自己实现的。


Trans_observer 结构体
Server_state_observer 结构体
Binlog_transmit_observer 结构体
Binlog_relay_IO_observer 结构体

实际上看具体实现的时候,搜索这些结构的名字,插件中如果实现会定义实际的函数名。如MGR中如下:


Trans_observer trans_observer = {  sizeof(Trans_observer),
  group_replication_trans_before_dml,
  group_replication_trans_before_commit,
  group_replication_trans_before_rollback,
  group_replication_trans_after_commit,
  group_replication_trans_after_rollback,
};
  • Delegate:委托者基类
    其中包含


  Observer_info_list observer_info_list; //观察者链表,也就是Observer_info的一个链表
  mysql_rwlock_t lock;//读写锁
  MEM_ROOT memroot;//内存空间
  bool inited;//是否初始化

并且实现了一些通用的函数,比如增加和删除插件

  • 具体的委托者继承自Delegate


Trans_delegate :事物相关 typedef Trans_observer Observer; 
Server_state_delegate :服务器相关 typedef Server_state_observer Observer;
Binlog_transmit_delegate  :传输相关 typedef Binlog_transmit_observer Observer;
Binlog_relay_IO_delegate  :slave 相关typedef Binlog_relay_IO_observer Observer;

二、注册函数

举例rpl_handler.cc中


int register_trans_observer(Trans_observer *observer, void *p){  return transaction_delegate->add_observer(observer, (st_plugin_int *)p);
}

observer已经初始化完成,注册即可。这里加入到了观察者队列。一旦加入这个链表则,在实际使用的时候就会遍历整个链表执行相应的函数。

三、重要的宏

  • RUN_HOOK 宏
    定义如下:


#define RUN_HOOK(group, hook, args)             \
  (group ##_delegate->is_empty() ?              \
   0 : group ##_delegate->hook args)#define NO_HOOK(group) (group ##_delegate->is_empty())

这个宏会在MySQL中代码的相应合适的位置进行调用,进入插件定义的逻辑。

  • FOREACH_OBSERVER 宏
    定义如下:


#define FOREACH_OBSERVER(r, f, thd, args)                               \
                                                                      \
  Prealloced_array<plugin_ref, 8> plugins(PSI_NOT_INSTRUMENTED);        \ //定义一个插件数组
  read_lock();                                                          \
  Observer_info_iterator iter= observer_info_iter();                    \ //迭代器
  Observer_info *info= iter++;                                          \ //
  for (; info; info= iter++)                                            \
  {                                                                     \
    plugin_ref plugin=                                                  \
      my_plugin_lock(0, &info->plugin);                                 \    if (!plugin)                                                        \
    {                                                                   \         \
      r= 0;                                                             \      break;                                                            \
    }                                                                   \
    plugins.push_back(plugin);                                          \    if (((Observer *)info->observer)->f                                 \
        && ((Observer *)info->observer)->f args)                        \
    {                                                                   \
      r= 1;                                                             \
      sql_print_error("Run function '" #f "' in plugin '%s' failed",    \
                      info->plugin_int->name.str);                      \      break;                                                            \
    }                                                                   \
  }                                                                     \

实际上可以看到是在遍历相应的实际委托者的链表observer_info_list,执行相应的回表函数。

四、一个实际的列子


RUN_HOOK(transaction,
                 before_commit,
                 (thd, all,
                  thd_get_cache_mngr(thd)->get_binlog_cache_log(true),
                  thd_get_cache_mngr(thd)->get_binlog_cache_log(false),
                  max<my_off_t>(max_binlog_cache_size,
                                max_binlog_stmt_cache_size))

根据RUN_HOOK定义 group ##_delegate->hook args 转换为:


transaction_delegate->before_commit(thd, all,
                  thd_get_cache_mngr(thd)->get_binlog_cache_log(true),
                  thd_get_cache_mngr(thd)->get_binlog_cache_log(false),
                  max<my_off_t>(max_binlog_cache_size,
                                max_binlog_stmt_cache_size)

此处的transaction_delegate是一个已经初始化的并且已经有插件注册的Trans_delegate类的全局对象。因为Trans_delegate继承来自Delegate,而在Trans_delegate中实现了before_commit的逻辑。其中包含的宏调用


FOREACH_OBSERVER(ret, before_commit, thd, (&param)); //这里会执行回调函数宏定义:(#define FOREACH_OBSERVER(r, f, thd, args)  )

做回调,实际上他会遍历整个transaction_delegate中的观察者,这些观察者就是每一个插件实现的特定的GROUP的功能,所以FOREACH_OBSERVER宏的这一句


((Observer *)info->observer)->f args

就装换为了(Trans_observer *)info->observer)->before_commit(&param) 其中info是一个Observer_info对象其中包含了一个VOID指针observer,可以转换为需要的类型,而Trans_observer是一个结构体其中全部都是函数指针before_commit是一个函数指针指向了group_replication_trans_before_commit,整个回调过程完成。

五、一张调用图

调用图如下:


MySQL插件调用

RUN_HOOK.png

作者微信:


MySQL插件调用

微信.jpg


免责声明:

① 本站未注明“稿件来源”的信息均来自网络整理。其文字、图片和音视频稿件的所属权归原作者所有。本站收集整理出于非商业性的教育和科研之目的,并不意味着本站赞同其观点或证实其内容的真实性。仅作为临时的测试数据,供内部测试之用。本站并未授权任何人以任何方式主动获取本站任何信息。

② 本站未注明“稿件来源”的临时测试数据将在测试完成后最终做删除处理。有问题或投稿请发送至: 邮箱/279061341@qq.com QQ/279061341

MySQL插件调用

下载Word文档到电脑,方便收藏和打印~

下载Word文档

猜你喜欢

Python 调用MySQL插入含有变量

注意 占位符和双引号
2023-01-31

Intellij IDEA中怎么调试maven插件

今天小编给大家分享一下Intellij IDEA中怎么调试maven插件的相关知识点,内容详细,逻辑清晰,相信大部分人都还太了解这方面的知识,所以分享这篇文章给大家参考一下,希望大家阅读完这篇文章后有所收获,下面我们一起来了解一下吧。Int
2023-07-05

MySQL查询重写插件的使用

查询重写插件 从MySQL 5.7.6开始,MySQL Server支持查询重写插件,可以在服务器执行之前检查并可能修改服务器接收的语句。 以下是官方文档介绍: 预解析重写插件具有以下特点: 1.该插件允许在服务器处理之前重写到达服务器
2022-05-24

MySQL Clone Plugin(克隆插件,适用8.0.17+)

MySQL Clone Plugin(克隆插件,8.0.17+) 一. 克隆插件是什么? 允许从本地或远程MySQL服务器实例拷贝数据 可对InnoDB的schemas,tables,tablespaces,数据字典元数据进行物理快照 支持replic
MySQL Clone Plugin(克隆插件,适用8.0.17+)
2018-06-07

VS Code里如何使用Debugger for Unity插件调试

这篇文章主要介绍“VS Code里如何使用Debugger for Unity插件调试”,在日常操作中,相信很多人在VS Code里如何使用Debugger for Unity插件调试问题上存在疑惑,小编查阅了各式资料,整理出简单好用的操作
2023-07-05

Intellij IDEA 中调试 maven 插件的步骤

这篇文章主要介绍了Intellij IDEA 中调试 maven 插件,本文分步骤给大家讲解的非常详细,对大家的学习或工作具有一定的参考借鉴价值,需要的朋友可以参考下
2023-03-20

编程热搜

目录