Chuanwise
本帖最后由 Chuanwise 于 2021-2-25 21:46 编辑

- CustomCommands · 自定义指令 -

有谁会喜欢经常依次输入一串格式固定的指令呢?
在一些 RPG 服务器上,你可能不希望经常依次输入
  1. /sudo 玩家名 cell create 公寓编号
  2. /sudo 玩家名 cell sethome 公寓编号
  3. /sudo 玩家名 cell setprice 1800 公寓编号
  4. /sudo 玩家名 cell addoor 公寓编号
  5. /sudo 玩家名 cell settrental 1 公寓编号
  6. /sudo 玩家名 cell addsign 公寓编号
复制代码
这些冗长的一系列指令。

虽然 ChestCommands(菜单)、木牌指令这类插件可以一次性执行多个指令,但编辑修改起来也较为麻烦。

本插件允许你将这些指令按照自己希望的方式打包成一个指令

只需要输入一句:
/ccsr <任何你自定义的喜欢的格式>
就可以自动执行上面一串指令。



本插件 CustomCommands 插件也叫 CCS(CustomCommandS)或 Custom-Commands 等。
它允许自己设置一些指令的格式,以简化输入。
开源地址https://github.com/Chuanwise/CustomCommands
编写插件不容易,给个 Star 好不好 (☆▽☆)
下载地址:

基本概念
指令组
使用 CCS(本插件) 设计的指令都具有指令名。CCS 允许多个指令具有相同的名字和不同的参数格式。
例如,你的服务器叫 Taixue。你为该服务器设计了一组指令,他们的格式分别是:
  1. /ccsc taixue register <password> <email>
  2. /ccsc taixue login <password> <Verification-code>
  3. /ccsc taixue ...
复制代码
这些指令都以 /ccsc taixue 开头,却具有不同的参数格式,对应不同的功能。在 CCS 中,因为他们都以 /ccsr taixue 开头,所以上述指令同属于指令组 taixue,它们是 taixue 的不同指令分支。由此可见,指令组的构成单元是指令分支

指令分支
指令分支是指令组的构成单元。每一个指令分支,都对应一种参数格式,和匹配成功后要执行的指令。查看后文有关指令查找的描述,你会对指令分支有更深刻的理解。

指令匹配的方式
执行使用 CCS 设计的指令的语句一般是:/ccsr <group-name> <arguments>。CCS 首先查找名为 <group-name> 的指令组,在该指令组下的所有分支中寻找能与当前参数匹配的一种分支。若能确定唯一的匹配当前参数的分支,则执行该指令。

演示效果
设计目标
如果你希望输入 /ccsr test something {arg1} {arg2} tail {arg3} 后自动执行 say {arg1} {arg2} 和 say {arg3},同时希望输入 /ccsr test something {arg1} 后自动执行 say {arg1},那么 commands.yml 应该是:
  1. commands:
  2.   # test 指令组下有两个分支:branch1 和 branch2
  3.   test:
  4.     branch1:
  5.       format: 'something {arg1} {arg2} tail {arg3}'
  6.       result: 'a string will be send to command sender after all parsed commands executed.'
  7.       actions:
  8.         - 'say {arg1} {arg2}'
  9.         - 'say {arg3}'
  10.     branch2:
  11.       format: 'something {arg1}'
  12.       actions:
  13.         - 'say {arg1}'
  14.     # 其他分支信息
  15.     # ...
  16.   # 其他指令组信息
  17.   # ...
复制代码
这个文件的写法非常简单,下文有详细的介绍。

功能演示
(演示的时候忘记截图了所以有的时间不一样)
下文的实验是在 1.16.5 服务器的控制台上进行的,第一行的 > 后的内容是刚才输入的指令。

错误的指令组名
输入了错误的指令组名(只定义了 test 指令组,所以只可能存在 /ccsr test 开头的指令),将会输出:
  1. >ccsr qwq
  2. [15:31:34] [Server thread/INFO]: [Custom-Commands] 未定义指令组 qwq
复制代码

指令组名正确但无任何可匹配分支
输入正确的指令组名但没有任何分支可以匹配输入格式,将会输出所有该用户可用的分支格式:
  1. >ccsr test
  2. [18:27:57] [Server thread/INFO]: [Custom-Commands] 未在指令组 test 中找到能与当前参数列表匹配的指令
  3. [18:27:57] [Server thread/INFO]: [Custom-Commands] 当前在指令组 test 中加载的指令有:
  4. [18:27:57] [Server thread/INFO]: [Custom-Commands] /ccsr test something {arg1} {arg2} tail {arg3}
  5. [18:27:57] [Server thread/INFO]: [Custom-Commands] /ccsr test something {arg1} {arg2} {arg3} {arg4}
复制代码

匹配某一分支成功
输入匹配第一种分支 /ccsr test something {arg1} {arg2} tail {arg3},则自动执行该分支下的指令: say {arg1} {arg2} 和 say {arg3},并显示 a string will be send to command sender after all parsed commands executed. 信息(这行文字是可以自定义的):
  1. >ccsr test something qwq orz tail qwqw!
  2. [11:24:32] [Server thread/INFO]: [Server] qwq orz
  3. [11:24:32] [Server thread/INFO]: [Server] qwqw!
  4. [11:24:32] [Server thread/INFO]: [Custom-Commands] a string will be send to command sender after all parsed commands executed
复制代码
用 /ccs debug 打开调试模式后,输出相关解析信息:
  1. [11:24:56] [Server thread/INFO]: [Custom-Commands] DEBUG >> variable-value list:
  2. [11:24:56] [Server thread/INFO]: [Custom-Commands] DEBUG >>   > arg3:    qwqw!
  3. [11:24:56] [Server thread/INFO]: [Custom-Commands] DEBUG >>   > arg2:    orz
  4. [11:24:56] [Server thread/INFO]: [Custom-Commands] DEBUG >>   > arg1:    qwq
  5. [11:24:56] [Server thread/INFO]: [Custom-Commands] DEBUG >> parsed commands:
  6. [11:24:56] [Server thread/INFO]: [Custom-Commands] DEBUG >>   > say qwq orz
  7. [11:24:56] [Server thread/INFO]: [Custom-Commands] DEBUG >>   > say qwqw!
  8. [11:24:56] [Server thread/INFO]: [Server] qwq orz
  9. [11:24:56] [Server thread/INFO]: [Server] qwqw!
  10. [11:24:56] [Server thread/INFO]: [Custom-Commands] a string will be send to command sender after all parsed commands executed.
复制代码
可见变量 {arg1} {arg2} {arg3} 的值符合预期。
输入匹配另一种分支的指令后,可以成功匹配到对应分支:
  1. >ccsr test something qwq
  2. [11:22:31] [Server thread/INFO]: [Custom-Commands] DEBUG >> variable-value list:
  3. [11:22:31] [Server thread/INFO]: [Custom-Commands] DEBUG >>     > arg1:    qwq
  4. [11:22:31] [Server thread/INFO]: [Custom-Commands] DEBUG >> parsed commands:
  5. [11:22:31] [Server thread/INFO]: [Custom-Commands] DEBUG >>     > say qwq
  6. [11:22:31] [Server thread/INFO]: [Server] qwq
  7. [11:22:31] [Server thread/INFO]: [Custom-Commands] 成功执行 test 组中的 branch2 指令
复制代码

同时能被多个分支匹配
如果修改设置,使得多种分支能够同时被匹配,则会输出错误。这是当时的配置文件 commands.yml:
  1. commands:
  2.   # ...
  3.   test:
  4.     branch1:
  5.       format: 'something {arg1} {arg2} tail {arg3}'
  6.       result: 'a string will be send to command sender after all parsed commands executed.'
  7.       actions:
  8.         - 'say {arg1} {arg2}'
  9.         - 'say {arg3}'
  10.     branch2:
  11.       format: 'something {arg1} {arg2} {arg3} {arg4}'
  12.       actions:
  13.         - 'say {arg1}'
  14.   # ...
复制代码
此时 /ccsr test something a b tail d 可以被两个分支匹配:
  1. >ccsr test something a b tail d
  2. [11:42:38] [Server thread/INFO]: [Custom-Commands] 有 2 个指令与之匹配,请修改设置以消除歧义。
  3. [11:42:38] [Server thread/INFO]: [Custom-Commands] /ccsr test something {arg1} {arg2} tail {arg3}
  4. [11:42:38] [Server thread/INFO]: [Custom-Commands] /ccsr test something {arg1} {arg2} {arg3} {arg4}
  5. ```
复制代码
可见插件发现了这个问题。

前置插件
当前最新版本(CustomCommands 2.0)暂无。
高版本可能会需要 PlaceholderAPI。

插件指令
所有格式是 /ccs <config | run> <remain-arguments> 的指令都可以被简化为 /ccs<c | r> <remain-arguments>,例如 /ccs config 可以简化为 /ccsc。CCSC 也就是 CustomCommandS Config,CCSR 是 CustomCommandS Run

/ccs reload 重载所有设置
/ccs version 显示插件名、版本号等信息
/ccs debug 开关调试模式
/ccsc list 显示所有已加载的指令组
/ccsc add <group-name> 新增加一个组
/ccsc group <group-name> 查看有关指令组`<group-name>`的信息
/ccsc remove <group-name> 删除指令组`<group-name>`
/ccsc group <group-name> add <command-name> 在指令组中添加分支`<command-name>`
/ccsc group <group-name> remove <command-name> 删除整个指令组`<command-name>`
/ccsc group <group-name> rename <new-name> 重命名指令组为`<new-name>`。该组分支下的所有 `usage` 都会被重置
/ccsc group <group-name> command <command-name> 查看分支`<command-name>`的信息
/ccsc group <group-name> command <command-name> rename <new-name> 重命名分支`<command-name>`为`<new-name>`
/ccsc group <group-name> command <command-name> identify <identify> 设置执行 `actions` 中的指令的身份为 `<identify>`
/ccsc group <group-name> command <command-name> format <format> 设置该分支的解析格式为 `<format>`,可以包含空格或为空。其 `usage` 会被自动重置
/ccsc group <group-name> command <command-name> actions add <command> 在该分支的 `actions` 结尾追加新的指令 `<command>`,可以包含空格或为空
/ccsc group <group-name> command <command-name> actions clear 清空 `actions`
/ccsc group <group-name> command <command-name> actions remove <command> 删除 `actions` 中的第一个出现的指令 `<command>`
/ccsc group <group-name> command <command-name> actions set <command> 设置 `actions` 为指令 `<command>`
/ccsc group <group-name> command <command-name> actions edit <index> <command> 修改 `actions` 中的第 `<index>` 条指令为 `<command>`(`index` 从 `1` 开始)
/ccsc group <group-name> command <command-name> result <string> 修改返回信息 `result` 为 `<string>`,可以包含空格或为空
/ccsc group <group-name> command <command-name> usage <usage> 修改 `usage` 为 `<usage>`,可以包含空格或为空
/ccsc group <group-name> command <command-name> permissions add <permission> 在该分支的必须权限中增加新的权限节点 `<permission>`
/ccsc group <group-name> command <command-name> permissions clear 清除该分支的必须权限。
/ccsc group <group-name> command <command-name> permissions remove <permission> 删除该分支的必须权限中的权限节点 `<permission>`
/ccsc group <group-name> command <command-name> permissions set <permission> 设置必须权限为一条 `<permission>`
/ccsc group <group-name> command <command-name> permissions edit <index> <command> 修改必须权限中的第 `<index>` 个节点为 `<command>`(`index` 从 `1` 开始)
/ccsc group <group-name> command <command-name> permissions default 将必须权限设置为默认值,即一条 `ccs.run.<group-name>.<command-name>`
/ccsc val <variable-name> 查找 `config.yml` 中的设置项 `<variable-name>`,并显示其值
/ccsc val <variable-name> <set-to> 设置 `config.yml` 中的设置项 `<variable-name>` 的值为 `<set-to>`
/ccsr <command-name> [arguments-list] 执行在 `commands.yml` 内定义的指令 `<command-name> `


配置文件
config.yml
默认的 config.yml 的内容是:

  1. config:      
  2.   # zhcn 是中文, en 就英文
  3.   lang: zhcn

  4.   # 开关 debug 模式
  5.   debug: false

  6.   # 最大迭代次数
  7.   max-iterations: 10
复制代码


max-iterations(最大迭代次数)
将变量替换为其值的最大次数
对于变量 {remain},如果它的内容是 head {remain},在这个例子中:
最后执行的指令格式:/say {remain}
输入格式:/.. head {remain}
将会执行的指令:/say head head head ... head {remain}
因为变量 {remain} 的值是 "head {remain}",所以还可以不断展开。
显然,变量 max-iterations 控制了变量的值中仍存在变量的情况下,最大的迭代次数。

commands.yml
默认的 commands.yml 的内容是:
  1. commands:
  2.   # (必填)
  3.   # <指令组名>:
  4.   group-name:
  5.     # (必填)
  6.     # 分支名
  7.     branch-name:
  8.       # (必填)
  9.       format: '{user_name} {group_name}'

  10.       # (必填)
  11.       actions:
  12.       - 'pex user {user_name} group set {group_name}'
  13.       - 'broadcast {user_name} is a member of {group_name}.'

  14.       # identify: 'console'

  15.       # usage: '格式错误时显示给指令发送者的内容'

  16.       # result: '成功执行后显示给指令发送者的内容'

  17.       # permissions:
  18.       #   - permissions.node
  19.       #   - 其他执行此分支的指令必备的权限节点

复制代码
format(解析规则)
解析输入的指令的规则。
变量定义普通字符串组成。
你可以在 format 中定义变量,就像 {variable_name}。大括号之间的内容就是变量名。一个合乎规则的变量名必须仅由英文字母、数字和下划线组成,并且不以数字开头。
format 中还可以存在普通字符串,以便于区分指令分支。例如上面文件中的 give

变量 {remain} 是一个很特殊的变量。如果在 format 中使用,它必须出现在末尾。
在解析的时候,如果遇到 {remain} ,指令剩余的所有内容都会存入这个变量中,所以它的内容可能包含空格,也可能为空。

actions(执行指令)
在输入了正确的 /ccsr 指令后将会执行的命令,可以是多条不同的指令,每一句中可以使用 format 中定义的变量,他们会在执行时被解析成正确的内容。
如果这当中出现了没有在 format 中定义的变量,它们会保持原样,也就是 {变量名}。

警告
CCS 允许你在 actions 中写入 /ccsr 指令,以便嵌套执行一些命令。如果设计的不好,这可能会导致循环。例如下面的情况:
  1. commands:
  2.   # ...
  3.   death-loop:
  4.     # 分支名可以随便起。
  5.     this:
  6.       format: '{remain}'
  7.       actions:
  8.         - 'ccsr death-loop {remain}'
复制代码
这意味着如果输入 /ccsr death-loop <任何剩余内容>,将会执行 /ccsr death-loop <刚才的那些剩余内容>。
实际上就是只要输入了这个指令,便会不断无限循环执行这个指令。
我(插件作者)亲测,这会导致服务器后台输出大量错误信息随后崩服。为了保护你的服务器,在设计 actions 时,必须在添加 /ccsr 时仔细考虑。

usage(选填)
默认值:/ccsr <指令组名> <分支名> <解析规则>。
在上面的 pex-group-set 命令中,usage 的值是 /ccsr pex-group-set {user_name} {group_name}。

这是描述该指令用法的字符串,他将在使用指令的人输入了一种无法被当前指令组中任何一种指令分支匹配,或能同时被多个分支匹配时显示。

identify(选填)
默认值: auto。
执行 actions 那些指令时的身份,可以是 auto 也可以是 console。
auto 就是以当前输入 /ccsr 指令的身份执行 actions,console 就是以控制台身份执行 actions。

这个设置项允许你仅使用 console 时可以通过权限 ccs.run.<指令组名>.<分支名> 跳过这一串指令的权限检测。当然,如果大家支持 CCS,在未来还可能更新支持 bypass 模式(以玩家身份无视权限执行)。

permissions(选填)
默认值: [ccs.run.<group-name>.<branch-name>]。
匹配当前指令组所需的权限,可以是多条。

如果你希望拥有不同权限的玩家在输入相同的指令格式时当做不同的指令分支解析,使用 permissions 加以区分是一种很好的办法。当检测到当前指令格式可以匹配多种指令分支,CCS 会首先尝试筛除玩家不具有权限的那些分支,如果筛除后仅剩下一种分支,CCS 会执行该指令。

result(选填)
默认值:成功执行 <group-name> 组中的 <branch-name> 指令(可以在 lang 文件中修改)。
指令匹配成功并执行结束后,发送给指令发送者的信息。


配置文件示例
config.yml
  1. config:      
  2.   # zhcn 是中文, en 是英文
  3.   lang: zhcn

  4.   # 开关 debug 模式
  5.   debug: false

  6.   # 最大迭代次数
  7.   max-iterations: 10
复制代码

commands.yml
  1. commands:
  2.   # 有关权限设置的所有指令
  3.   pex:
  4.     # set 分支
  5.     set:
  6.       # 匹配 set 分支的格式
  7.       format: 'set {group_name} {user_name}'
  8.       # 匹配成功后执行的指令
  9.       actions:
  10.         - 'pex user {user_name} group set {group_name}'
  11.         - 'bc {user_name} is a member of {group_name}.'
  12.       identify: console

  13.     # 给用户在某一世界中的建筑权限分支
  14.     give-world-builder:
  15.       format: 'give {user_name} {world_name}'
  16.       actions:
  17.         - 'pex user {user_name} add multiverse.access.{world_name}'
  18.         - 'pex user {user_name} group add p-world-builder {world_name}'
  19.         - 'pex reload'
  20.       result: '成功给了 {user_name} 在世界 {world_name} 中的建造权限。'
  21.       identify: console

  22.     # 移除用户在某一世界中的建筑权限分支
  23.     remove-world-builder:
  24.       format: 'remove {user_name} {world_name}'
  25.       actions:
  26.         - 'pex user {user_name} remove multiverse.access.{world_name}'
  27.         - 'pex user {user_name} group remove p-world-builder {world_name}'
  28.         - 'pex reload'
  29.       result: '成功移除 {user_name} 在世界 {world_name} 中的建造权限。'
  30.       identify: console

  31.   # 和经济相关的指令组
  32.   eco:
  33.     give:
  34.       format: '{user_name} {money_number}'
  35.       actions:
  36.         - 'eco give {user_name} {money_number}'
  37.     # ...
复制代码
按以上设置后,便可通过指令 /ccsr pex set <group-name> <user-name> 匹配 pex.set 分支,用 /ccsr pex give <user-name> <world-name> 匹配 pex.give 分支,并执行对应分支内的指令。

权限节点
  • ccs.*: 所有 CCS 权限。
  • ccs.version: 查看插件名、版本等信息的权限。
  • ccs.debug: 开关调试模式的权限。
  • ccs.reload: 重载 CCS 插件的权限。
  • ccs.run.<指令组名>.<指令分支名>: 使用某一特定指令组某一分支的权限。
  • ccs.config.val.set: 设置一个项目的权限
  • ccs.config.val.look: 查看一个项目的值的权限

联系方式
QQ 群:  1028582500
作者: Chuanwise
邮箱: [email protected]
明城京联合太学,保留所有权利。
Taixue, All rights reserved.

画大饼
欢迎提交 issue 反馈你希望增加的功能。
点击这个页面的绿色按钮 New issue 反馈。

已经开发完成的功能
下面枚举的功能将在下一个版本更新时发布。
  • 在 actions 中使用类似 @sleep 100 的指令让 CCS 等待一会儿再执行下一个指令的特殊语句。
正在开发的功能
  • 使用正则表达式检查变量名。
  • 通过指令编辑 commands.yml。

可能要增加的功能
下面枚举的功能我有相关想法,但是不知道实际使用性如何,需要大家的反馈才会决定是否要开发。

  • 允许直接使用 /<指令组名> <分支名> [参数列表] 的形式执行指令,无需使用 /ccsr。
  • 不能在 format 解析获得的默认变量。例如 {user_name},{world_name}。

更新日志
2.0
发布于 2021年2月22日
  • 完善了消息提示系统,使用了一些颜色让插件输出更加赏心悦目。
  • 完成了 zhcn.yml 汉化提示包。
  • 从原本的单一指令系统,升级为指令分组,按格式匹配的系统。增加了自定义指令的自由度。
  • 优化了之前代码中的一些不合理的部分。
1.0
发布于 2021年2月19日。

鸣谢
  • Favourite:引导我入门了最基础的 `Minecraft` 服务器技术
  • Eric
  • One47
  • Coloryr


2021.12 数据,可能有更多内容- CustomCommands · 自定义指令 -
有谁会喜欢经常依次输入一串格式固定的指令呢?在一些 RPG 服务器上,你可能不希望经常依次输入

代码:

  1. /sudo 玩家名 cell create 公寓编号
  2. /sudo 玩家名 cell sethome 公寓编号
  3. /sudo 玩家名 cell setprice 1800 公寓编号
  4. /sudo 玩家名 cell addoor 公寓编号
  5. /sudo 玩家名 cell settrental 1 公寓编号
  6. /sudo 玩家名 cell addsign 公寓编号
这些冗长的一系列指令。
虽然 ChestCommands(菜单)、木牌指令这类插件可以一次性执行多个指令,但编辑修改起来也较为麻烦。
本插件允许你将这些指令按照自己希望的方式打包成一个指令
只需要输入一句:/ccsr &lt;任何你自定义的喜欢的格式&gt;就可以自动执行上面一串指令。



本插件 CustomCommands 插件也叫 CCS(CustomCommandS)或 Custom-Commands 等。
它允许自己设置一些指令的格式,以简化输入。开源地址https://github.com/Chuanwise/CustomCommands编写插件不容易,给个 Star 好不好 (☆▽☆)下载地址:https://github.com/Chuanwise/CustomCommands/releases/download/2.0/Custom-Commands-2.0.jar
基本概念指令组使用 CCS(本插件) 设计的指令都具有指令名。CCS 允许多个指令具有相同的名字和不同的参数格式。例如,你的服务器叫 Taixue。你为该服务器设计了一组指令,他们的格式分别是:

代码:

  1. /ccsc taixue register <password> <email>
  2. /ccsc taixue login <password> <Verification-code>
  3. /ccsc taixue ...
这些指令都以 /ccsc taixue 开头,却具有不同的参数格式,对应不同的功能。在 CCS 中,因为他们都以 /ccsr taixue 开头,所以上述指令同属于指令组 taixue,它们是 taixue 的不同指令分支。由此可见,指令组的构成单元是指令分支
指令分支
指令分支是指令组的构成单元。每一个指令分支,都对应一种参数格式,和匹配成功后要执行的指令。查看后文有关指令查找的描述,你会对指令分支有更深刻的理解。


指令匹配的方式
执行使用 CCS 设计的指令的语句一般是:/ccsr &lt;group-name&gt; &lt;arguments&gt;。CCS 首先查找名为 &lt;group-name&gt; 的指令组,在该指令组下的所有分支中寻找能与当前参数匹配的一种分支。若能确定唯一的匹配当前参数的分支,则执行该指令。


演示效果设计目标如果你希望输入 /ccsr test something {arg1} {arg2} tail {arg3} 后自动执行 say {arg1} {arg2} 和 say {arg3},同时希望输入 /ccsr test something {arg1} 后自动执行 say {arg1},那么 commands.yml 应该是:

代码:

  1. commands:
  2. # test 指令组下有两个分支:branch1 和 branch2
  3. test:
  4.     branch1:
  5.    format: 'something {arg1} {arg2} tail {arg3}'
  6.    result: 'a string will be send to command sender after all parsed commands executed.'
  7.    actions:
  8.   - 'say {arg1} {arg2}'
  9.   - 'say {arg3}'
  10.     branch2:
  11.    format: 'something {arg1}'
  12.    actions:
  13.   - 'say {arg1}'
  14.     # 其他分支信息
  15.     # ...
  16. # 其他指令组信息
  17. # ...
这个文件的写法非常简单,下文有详细的介绍。
功能演示
(演示的时候忘记截图了所以有的时间不一样)下文的实验是在 1.16.5 服务器的控制台上进行的,第一行的 &gt; 后的内容是刚才输入的指令。
错误的指令组名输入了错误的指令组名(只定义了 test 指令组,所以只可能存在 /ccsr test 开头的指令),将会输出:

代码:

  1. >ccsr qwq
  2. [15:31:34] [Server thread/INFO]: [Custom-Commands] 未定义指令组 qwq

指令组名正确但无任何可匹配分支输入正确的指令组名但没有任何分支可以匹配输入格式,将会输出所有该用户可用的分支格式:

代码:

  1. >ccsr test
  2. [18:27:57] [Server thread/INFO]: [Custom-Commands] 未在指令组 test 中找到能与当前参数列表匹配的指令
  3. [18:27:57] [Server thread/INFO]: [Custom-Commands] 当前在指令组 test 中加载的指令有:
  4. [18:27:57] [Server thread/INFO]: [Custom-Commands] /ccsr test something {arg1} {arg2} tail {arg3}
  5. [18:27:57] [Server thread/INFO]: [Custom-Commands] /ccsr test something {arg1} {arg2} {arg3} {arg4}

匹配某一分支成功输入匹配第一种分支 /ccsr test something {arg1} {arg2} tail {arg3},则自动执行该分支下的指令: say {arg1} {arg2} 和 say {arg3},并显示 a string will be send to command sender after all parsed commands executed. 信息(这行文字是可以自定义的):

代码:

  1. >ccsr test something qwq orz tail qwqw!
  2. [11:24:32] [Server thread/INFO]: [Server] qwq orz
  3. [11:24:32] [Server thread/INFO]: [Server] qwqw!
  4. [11:24:32] [Server thread/INFO]: [Custom-Commands] a string will be send to command sender after all parsed commands executed
用 /ccs debug 打开调试模式后,输出相关解析信息:

代码:

  1. [11:24:56] [Server thread/INFO]: [Custom-Commands] DEBUG >> variable-value list:
  2. [11:24:56] [Server thread/INFO]: [Custom-Commands] DEBUG >>   > arg3:    qwqw!
  3. [11:24:56] [Server thread/INFO]: [Custom-Commands] DEBUG >>   > arg2:    orz
  4. [11:24:56] [Server thread/INFO]: [Custom-Commands] DEBUG >>   > arg1:    qwq
  5. [11:24:56] [Server thread/INFO]: [Custom-Commands] DEBUG >> parsed commands:
  6. [11:24:56] [Server thread/INFO]: [Custom-Commands] DEBUG >>   > say qwq orz
  7. [11:24:56] [Server thread/INFO]: [Custom-Commands] DEBUG >>   > say qwqw!
  8. [11:24:56] [Server thread/INFO]: [Server] qwq orz
  9. [11:24:56] [Server thread/INFO]: [Server] qwqw!
  10. [11:24:56] [Server thread/INFO]: [Custom-Commands] a string will be send to command sender after all parsed commands executed.
可见变量 {arg1} {arg2} {arg3} 的值符合预期。输入匹配另一种分支的指令后,可以成功匹配到对应分支:

代码:

  1. >ccsr test something qwq
  2. [11:22:31] [Server thread/INFO]: [Custom-Commands] DEBUG >> variable-value list:
  3. [11:22:31] [Server thread/INFO]: [Custom-Commands] DEBUG >>  > arg1:    qwq
  4. [11:22:31] [Server thread/INFO]: [Custom-Commands] DEBUG >> parsed commands:
  5. [11:22:31] [Server thread/INFO]: [Custom-Commands] DEBUG >>  > say qwq
  6. [11:22:31] [Server thread/INFO]: [Server] qwq
  7. [11:22:31] [Server thread/INFO]: [Custom-Commands] 成功执行 test 组中的 branch2 指令

同时能被多个分支匹配如果修改设置,使得多种分支能够同时被匹配,则会输出错误。这是当时的配置文件 commands.yml:

代码:

  1. commands:
  2. # ...
  3. test:
  4.     branch1:
  5.    format: 'something {arg1} {arg2} tail {arg3}'
  6.    result: 'a string will be send to command sender after all parsed commands executed.'
  7.    actions:
  8.   - 'say {arg1} {arg2}'
  9.   - 'say {arg3}'
  10.     branch2:
  11.    format: 'something {arg1} {arg2} {arg3} {arg4}'
  12.    actions:
  13.   - 'say {arg1}'
  14. # ...
此时 /ccsr test something a b tail d 可以被两个分支匹配:

代码:

  1. >ccsr test something a b tail d
  2. [11:42:38] [Server thread/INFO]: [Custom-Commands] 有 2 个指令与之匹配,请修改设置以消除歧义。
  3. [11:42:38] [Server thread/INFO]: [Custom-Commands] /ccsr test something {arg1} {arg2} tail {arg3}
  4. [11:42:38] [Server thread/INFO]: [Custom-Commands] /ccsr test something {arg1} {arg2} {arg3} {arg4}
  5. ```
可见插件发现了这个问题。
前置插件
当前最新版本(CustomCommands 2.0)暂无。
高版本可能会需要 PlaceholderAPI。


插件指令
所有格式是 /ccs &lt;config | run&gt; &lt;remain-arguments&gt; 的指令都可以被简化为 /ccs&lt;c | r&gt; &lt;remain-arguments&gt;,例如 /ccs config 可以简化为 /ccsc。CCSC 也就是 CustomCommandS Config,CCSR 是 CustomCommandS Run
/ccs reload
重载所有设置
/ccs version
显示插件名、版本号等信息
/ccs debug
开关调试模式
/ccsc list
显示所有已加载的指令组
/ccsc add &lt;group-name&gt;
新增加一个组
/ccsc group &lt;group-name&gt;
查看有关指令组`&lt;group-name&gt;`的信息
/ccsc remove &lt;group-name&gt;
删除指令组`&lt;group-name&gt;`
/ccsc group &lt;group-name&gt; add &lt;command-name&gt;
在指令组中添加分支`&lt;command-name&gt;`
/ccsc group &lt;group-name&gt; remove &lt;command-name&gt;
删除整个指令组`&lt;command-name&gt;`
/ccsc group &lt;group-name&gt; rename &lt;new-name&gt;
重命名指令组为`&lt;new-name&gt;`。该组分支下的所有 `usage` 都会被重置
/ccsc group &lt;group-name&gt; command &lt;command-name&gt;
查看分支`&lt;command-name&gt;`的信息
/ccsc group &lt;group-name&gt; command &lt;command-name&gt; rename &lt;new-name&gt;
重命名分支`&lt;command-name&gt;`为`&lt;new-name&gt;`
/ccsc group &lt;group-name&gt; command &lt;command-name&gt; identify &lt;identify&gt;
设置执行 `actions` 中的指令的身份为 `&lt;identify&gt;`
/ccsc group &lt;group-name&gt; command &lt;command-name&gt; format &lt;format&gt;
设置该分支的解析格式为 `&lt;format&gt;`,可以包含空格或为空。其 `usage` 会被自动重置
/ccsc group &lt;group-name&gt; command &lt;command-name&gt; actions add &lt;command&gt;
在该分支的 `actions` 结尾追加新的指令 `&lt;command&gt;`,可以包含空格或为空
/ccsc group &lt;group-name&gt; command &lt;command-name&gt; actions clear
清空 `actions`
/ccsc group &lt;group-name&gt; command &lt;command-name&gt; actions remove &lt;command&gt;
删除 `actions` 中的第一个出现的指令 `&lt;command&gt;`
/ccsc group &lt;group-name&gt; command &lt;command-name&gt; actions set &lt;command&gt;
设置 `actions` 为指令 `&lt;command&gt;`
/ccsc group &lt;group-name&gt; command &lt;command-name&gt; actions edit &lt;index&gt; &lt;command&gt;
修改 `actions` 中的第 `&lt;index&gt;` 条指令为 `&lt;command&gt;`(`index` 从 `1` 开始)
/ccsc group &lt;group-name&gt; command &lt;command-name&gt; result &lt;string&gt;
修改返回信息 `result` 为 `&lt;string&gt;`,可以包含空格或为空
/ccsc group &lt;group-name&gt; command &lt;command-name&gt; usage &lt;usage&gt;
修改 `usage` 为 `&lt;usage&gt;`,可以包含空格或为空
/ccsc group &lt;group-name&gt; command &lt;command-name&gt; permissions add &lt;permission&gt;
在该分支的必须权限中增加新的权限节点 `&lt;permission&gt;`
/ccsc group &lt;group-name&gt; command &lt;command-name&gt; permissions clear
清除该分支的必须权限。
/ccsc group &lt;group-name&gt; command &lt;command-name&gt; permissions remove &lt;permission&gt;
删除该分支的必须权限中的权限节点 `&lt;permission&gt;`
/ccsc group &lt;group-name&gt; command &lt;command-name&gt; permissions set &lt;permission&gt;
设置必须权限为一条 `&lt;permission&gt;`
/ccsc group &lt;group-name&gt; command &lt;command-name&gt; permissions edit &lt;index&gt; &lt;command&gt;
修改必须权限中的第 `&lt;index&gt;` 个节点为 `&lt;command&gt;`(`index` 从 `1` 开始)
/ccsc group &lt;group-name&gt; command &lt;command-name&gt; permissions default
将必须权限设置为默认值,即一条 `ccs.run.&lt;group-name&gt;.&lt;command-name&gt;`
/ccsc val &lt;variable-name&gt;
查找 `config.yml` 中的设置项 `&lt;variable-name&gt;`,并显示其值
/ccsc val &lt;variable-name&gt; &lt;set-to&gt;
设置 `config.yml` 中的设置项 `&lt;variable-name&gt;` 的值为 `&lt;set-to&gt;`
/ccsr &lt;command-name&gt; [arguments-list]
执行在 `commands.yml` 内定义的指令 `&lt;command-name&gt; `



配置文件
config.yml
默认的 config.yml 的内容是:

代码:

  1. config:   
  2. # zhcn 是中文, en 就英文
  3. lang: zhcn

  4. # 开关 debug 模式
  5. debug: false

  6. # 最大迭代次数
  7. max-iterations: 10



max-iterations(最大迭代次数)将变量替换为其值的最大次数对于变量 {remain},如果它的内容是 head {remain},在这个例子中:最后执行的指令格式:/say {remain}输入格式:/.. head {remain}将会执行的指令:/say head head head ... head {remain}因为变量 {remain} 的值是 &quot;head {remain}&quot;,所以还可以不断展开。显然,变量 max-iterations 控制了变量的值中仍存在变量的情况下,最大的迭代次数。
commands.yml默认的 commands.yml 的内容是:

代码:

  1. commands:
  2. # (必填)
  3. # <指令组名>:
  4. group-name:
  5.     # (必填)
  6.     # 分支名
  7.     branch-name:
  8.    # (必填)
  9.    format: '{user_name} {group_name}'

  10.    # (必填)
  11.    actions:
  12.    - 'pex user {user_name} group set {group_name}'
  13.    - 'broadcast {user_name} is a member of {group_name}.'

  14.    # identify: 'console'

  15.    # usage: '格式错误时显示给指令发送者的内容'

  16.    # result: '成功执行后显示给指令发送者的内容'

  17.    # permissions:
  18.    #   - permissions.node
  19.    #   - 其他执行此分支的指令必备的权限节点

format(解析规则)
解析输入的指令的规则。
变量定义普通字符串组成。
你可以在 format 中定义变量,就像 {variable_name}。大括号之间的内容就是变量名。一个合乎规则的变量名必须仅由英文字母、数字和下划线组成,并且不以数字开头。
format 中还可以存在普通字符串,以便于区分指令分支。例如上面文件中的 give


变量 {remain} 是一个很特殊的变量。如果在 format 中使用,它必须出现在末尾。
在解析的时候,如果遇到 {remain} ,指令剩余的所有内容都会存入这个变量中,所以它的内容可能包含空格,也可能为空。


actions(执行指令)
在输入了正确的 /ccsr 指令后将会执行的命令,可以是多条不同的指令,每一句中可以使用 format 中定义的变量,他们会在执行时被解析成正确的内容。
如果这当中出现了没有在 format 中定义的变量,它们会保持原样,也就是 {变量名}。


警告
CCS 允许你在 actions 中写入 /ccsr 指令,以便嵌套执行一些命令。如果设计的不好,这可能会导致循环。例如下面的情况:

代码:

  1. commands:
  2. # ...
  3. death-loop:
  4.     # 分支名可以随便起。
  5.     this:
  6.    format: '{remain}'
  7.    actions:
  8.   - 'ccsr death-loop {remain}'
这意味着如果输入 /ccsr death-loop &lt;任何剩余内容&gt;,将会执行 /ccsr death-loop &lt;刚才的那些剩余内容&gt;。实际上就是只要输入了这个指令,便会不断无限循环执行这个指令。我(插件作者)亲测,这会导致服务器后台输出大量错误信息随后崩服。为了保护你的服务器,在设计 actions 时,必须在添加 /ccsr 时仔细考虑。


usage(选填)
默认值:/ccsr &lt;指令组名&gt; &lt;分支名&gt; &lt;解析规则&gt;。
在上面的 pex-group-set 命令中,usage 的值是 /ccsr pex-group-set {user_name} {group_name}。


这是描述该指令用法的字符串,他将在使用指令的人输入了一种无法被当前指令组中任何一种指令分支匹配,或能同时被多个分支匹配时显示。


identify(选填)
默认值: auto。
执行 actions 那些指令时的身份,可以是 auto 也可以是 console。
auto 就是以当前输入 /ccsr 指令的身份执行 actions,console 就是以控制台身份执行 actions。


这个设置项允许你仅使用 console 时可以通过权限 ccs.run.&lt;指令组名&gt;.&lt;分支名&gt; 跳过这一串指令的权限检测。当然,如果大家支持 CCS,在未来还可能更新支持 bypass 模式(以玩家身份无视权限执行)。


permissions(选填)
默认值: [ccs.run.&lt;group-name&gt;.&lt;branch-name&gt;]。
匹配当前指令组所需的权限,可以是多条。


如果你希望拥有不同权限的玩家在输入相同的指令格式时当做不同的指令分支解析,使用 permissions 加以区分是一种很好的办法。当检测到当前指令格式可以匹配多种指令分支,CCS 会首先尝试筛除玩家不具有权限的那些分支,如果筛除后仅剩下一种分支,CCS 会执行该指令。


result(选填)
默认值:成功执行 &lt;group-name&gt; 组中的 &lt;branch-name&gt; 指令(可以在 lang 文件中修改)。
指令匹配成功并执行结束后,发送给指令发送者的信息。


配置文件示例
config.yml

代码:

  1. config:   
  2. # zhcn 是中文, en 是英文
  3. lang: zhcn

  4. # 开关 debug 模式
  5. debug: false

  6. # 最大迭代次数
  7. max-iterations: 10

commands.yml

代码:

  1. commands:
  2. # 有关权限设置的所有指令
  3. pex:
  4.     # set 分支
  5.     set:
  6.    # 匹配 set 分支的格式
  7.    format: 'set {group_name} {user_name}'
  8.    # 匹配成功后执行的指令
  9.    actions:
  10.   - 'pex user {user_name} group set {group_name}'
  11.   - 'bc {user_name} is a member of {group_name}.'
  12.    identify: console

  13.     # 给用户在某一世界中的建筑权限分支
  14.     give-world-builder:
  15.    format: 'give {user_name} {world_name}'
  16.    actions:
  17.   - 'pex user {user_name} add multiverse.access.{world_name}'
  18.   - 'pex user {user_name} group add p-world-builder {world_name}'
  19.   - 'pex reload'
  20.    result: '成功给了 {user_name} 在世界 {world_name} 中的建造权限。'
  21.    identify: console

  22.     # 移除用户在某一世界中的建筑权限分支
  23.     remove-world-builder:
  24.    format: 'remove {user_name} {world_name}'
  25.    actions:
  26.   - 'pex user {user_name} remove multiverse.access.{world_name}'
  27.   - 'pex user {user_name} group remove p-world-builder {world_name}'
  28.   - 'pex reload'
  29.    result: '成功移除 {user_name} 在世界 {world_name} 中的建造权限。'
  30.    identify: console

  31. # 和经济相关的指令组
  32. eco:
  33.     give:
  34.    format: '{user_name} {money_number}'
  35.    actions:
  36.   - 'eco give {user_name} {money_number}'
  37.     # ...
按以上设置后,便可通过指令 /ccsr pex set &lt;group-name&gt; &lt;user-name&gt; 匹配 pex.set 分支,用 /ccsr pex give &lt;user-name&gt; &lt;world-name&gt; 匹配 pex.give 分支,并执行对应分支内的指令。

权限节点
  • ccs.*: 所有 CCS 权限。
  • ccs.version: 查看插件名、版本等信息的权限。
  • ccs.debug: 开关调试模式的权限。
  • ccs.reload: 重载 CCS 插件的权限。
  • ccs.run.&lt;指令组名&gt;.&lt;指令分支名&gt;: 使用某一特定指令组某一分支的权限。
  • ccs.config.val.set: 设置一个项目的权限
  • ccs.config.val.look: 查看一个项目的值的权限

联系方式
QQ 群:1028582500
作者: Chuanwise
邮箱: [email protected]
明城京联合太学,保留所有权利。
Taixue, All rights reserved.


画大饼
欢迎提交 issue 反馈你希望增加的功能。
点击这个页面的绿色按钮 New issue 反馈。
已经开发完成的功能
下面枚举的功能将在下一个版本更新时发布。
  • 在 actions 中使用类似 @sleep 100 的指令让 CCS 等待一会儿再执行下一个指令的特殊语句。
正在开发的功能
  • 使用正则表达式检查变量名。
  • 通过指令编辑 commands.yml。

可能要增加的功能
下面枚举的功能我有相关想法,但是不知道实际使用性如何,需要大家的反馈才会决定是否要开发。
  • 允许直接使用 /&lt;指令组名&gt; &lt;分支名&gt; [参数列表] 的形式执行指令,无需使用 /ccsr。
  • 不能在 format 解析获得的默认变量。例如 {user_name},{world_name}。

更新日志
2.0
发布于 2021年2月22日
  • 完善了消息提示系统,使用了一些颜色让插件输出更加赏心悦目。
  • 完成了 zhcn.yml 汉化提示包。
  • 从原本的单一指令系统,升级为指令分组,按格式匹配的系统。增加了自定义指令的自由度。
  • 优化了之前代码中的一些不合理的部分。
1.0
发布于 2021年2月19日。


鸣谢
  • Favourite:引导我入门了最基础的 `Minecraft` 服务器技术
  • Eric
  • One47
  • Coloryr


Chuanwise
捞一捞 (๑•̀ㅂ•́)و✧

Animalworld
catserver似乎并不支持

164ebr
不会用 实力劝退

天基无情
很实用的插件,感谢分享

Yless
允许直接使用 /<指令组名> <分支名> [参数列表] 的形式执行指令,无需使用 /ccsr。
这个功能有打算更新吗 因为用/ccsr 组名 的确长了一些

叫我笨熊吖-
挺不错的一个插件 服务器刚好需要

临惜123
感谢分享

战域天
二位夫人 人格如果任由他和家人格瓦斯