基于函数式编程的调试工具

基于函数式编程的调试工具

需求

在项目开发过程中发现两个问题:

  1. 内部调试通常需要使用GM指令(比如一键满级满钱满技能等)。但是目前用的是在游戏内置的聊天框中输入文本的方式调用GM指令,体验不好而且效率不高。
  2. 每次联调过程中,当需要确认一些服务器消息时总是必须加入打印日志的相关代码,然后重新编译(即使是LuaJIT也需要花费不少时间)。

枯燥乏味的重复行为在无形中蚕食着开发人员的精力和耐心,它们是项目开发里的蚊蝇和蛆虫,解决上述问题迫在眉睫。刚好在前些时间了解了一些有关函数式编程的知识,本着实验的目的,先定几个小目标:

  1. 尽可能使用更加便捷的GUI提供用户交互,通过简单的点选操作就可完成执行GM指令以及信息查询等功能。
  2. 支持由用户自定义GUI,比如常见的多级菜单选项,或是点选按钮后执行的功能。
  3. 与现有项目代码尽可能保持低耦合,便于后期管理维护。

设计

基于函数式编程的调试工具GUI只是负责显示数据和交互;KEYS是GUI中显示的菜单选项,FUNC负责基于规则A执行逻辑(查询服务器消息内容、发送GM指令等),它们都是可配置的,分别由策划和程序维护;MANAGER则基于规则B从KEYS中提取文本给GUI显示,并根据用户选择的选项基于规则C提取数据,然后将其作为参数传递给FUNC。
能看到应用函数式编程的好处:

  1. 对于不同的对象和行为(比如不同类型的数据和不同签名的函数),能够基于自定义的范式对其进行统一的处理,逻辑上易于理解。上述提到的规则A、B、C可以抽象为三种函数(刚好Lua将function视为基础类型,代码写起来也更加方便)。
  2. 具体的逻辑被隐藏在统一的执行范式背后,用户可以实现除了执行GM指令和查询服务器消息之外的其他行为,而且由于Lua将函数也作为基础类型处理,现在这些行为都是可配置的。
  3. 函数内部一致性使得用户(这里指项目中的程序员)的调试工作能够进行地更加顺利。

实现

  1. MANAGER使用栈Stack管理GUI显示的KEYS多级菜单选项文本,以及点选菜单后存储的数据。
  2. 一些菜单选项需要自行定义规则才能获取到:
    1. 以Lua中的一个table存储这些规则,MANAGER只需读取table即可获取规则。
    2. table中以数字为key定义function,MANAGER基于当前在GUI中展开的菜单层级数,将其作为key值从该table中获取规则。比如刚打开调试工具界面时为第一级,即获取下标为1的规则。
    3. 如需要其它规则,在table中以字符串为key定义function,比如本工具就额外定义了canUnfold判断是否可继续展开下一级菜单。
      就像这样:
      基于函数式编程的调试工具
  3. FUNC的规则比较简单,filter筛选从MANAGER中取得的数据并将其作为参数返回,condition检查这些参数是否符合一定要求,func最后根据这些参数执行一定的逻辑。

参考资料

《Functional Programming For The Rest of Us》(中文翻译)