mirror of
https://github.com/PHIDIAS0303/ExpCluster.git
synced 2025-12-27 03:25:23 +09:00
Improvements for ExpCommands
This commit is contained in:
@@ -9,13 +9,14 @@ The default permission authorities controlled by the flags: admin_only, system_o
|
|||||||
]]
|
]]
|
||||||
|
|
||||||
local Storage = require("modules/exp_util/storage")
|
local Storage = require("modules/exp_util/storage")
|
||||||
local Commands = require("modules/exp_commands")
|
|
||||||
|
local Commands = require("modules/exp_commands") --- @class Commands
|
||||||
local add, allow, deny = Commands.add_permission_authority, Commands.status.success, Commands.status.unauthorised
|
local add, allow, deny = Commands.add_permission_authority, Commands.status.success, Commands.status.unauthorised
|
||||||
|
|
||||||
local authorities = {}
|
local authorities = {}
|
||||||
|
|
||||||
local system_players = {}
|
local system_players = {} --- @type table<string, boolean>
|
||||||
local disabled_commands = {}
|
local disabled_commands = {} --- @type table<string, boolean>
|
||||||
Storage.register({
|
Storage.register({
|
||||||
system_players,
|
system_players,
|
||||||
disabled_commands,
|
disabled_commands,
|
||||||
@@ -100,7 +101,7 @@ authorities.system_only =
|
|||||||
|
|
||||||
--- If Commands.disable was called then no one can use the command
|
--- If Commands.disable was called then no one can use the command
|
||||||
authorities.disabled =
|
authorities.disabled =
|
||||||
add(function(_player, command)
|
add(function(player, command)
|
||||||
if disabled_commands[command.name] then
|
if disabled_commands[command.name] then
|
||||||
return deny{ "exp-commands-authorities.disabled" }
|
return deny{ "exp-commands-authorities.disabled" }
|
||||||
else
|
else
|
||||||
|
|||||||
@@ -1,6 +1,5 @@
|
|||||||
--[[-- Command Module - Help
|
--[[-- Commands - Help
|
||||||
Game command to list and search all registered commands in a nice format
|
Game command to list and search all registered commands in a nice format
|
||||||
@commands _system-ipc
|
|
||||||
|
|
||||||
--- Get all messages related to banning a player
|
--- Get all messages related to banning a player
|
||||||
/commands ban
|
/commands ban
|
||||||
@@ -13,13 +12,16 @@ local Commands = require("modules/exp_commands")
|
|||||||
|
|
||||||
local PAGE_SIZE = 5
|
local PAGE_SIZE = 5
|
||||||
|
|
||||||
local search_cache = {}
|
--- @alias ResultsPage LocalisedString[]
|
||||||
|
--- @class HelpCacheEntry: { keyword: string, pages: ResultsPage[], found: number }
|
||||||
|
|
||||||
|
local search_cache = {} --- @type table<number, HelpCacheEntry>
|
||||||
Storage.register(search_cache, function(tbl)
|
Storage.register(search_cache, function(tbl)
|
||||||
search_cache = tbl
|
search_cache = tbl
|
||||||
end)
|
end)
|
||||||
|
|
||||||
--- Format commands into a strings across multiple pages
|
--- Format commands into a strings across multiple pages
|
||||||
--- @param commands { [string]: Commands.Command } The commands to split into pages
|
--- @param commands table<string, Commands.Command> The commands to split into pages
|
||||||
--- @param page_size number The number of requests to show per page
|
--- @param page_size number The number of requests to show per page
|
||||||
--- @return LocalisedString[][], number
|
--- @return LocalisedString[][], number
|
||||||
local function format_as_pages(commands, page_size)
|
local function format_as_pages(commands, page_size)
|
||||||
|
|||||||
@@ -1,6 +1,5 @@
|
|||||||
--[[-- Command Module - IPC
|
--[[-- Commands - IPC
|
||||||
System command which sends an object to the clustorio api, should be used for debugging / echo commands
|
System command which sends an object to the clustorio api, should be used for debugging / echo commands
|
||||||
@commands _system-ipc
|
|
||||||
|
|
||||||
--- Send a message on your custom channel, message is a json string
|
--- Send a message on your custom channel, message is a json string
|
||||||
/_ipc myChannel { "myProperty": "foo", "playerName": "Cooldude2606" }
|
/_ipc myChannel { "myProperty": "foo", "playerName": "Cooldude2606" }
|
||||||
|
|||||||
@@ -1,6 +1,5 @@
|
|||||||
--[[-- Command Module - Rcon
|
--[[-- Commands - Rcon
|
||||||
System command which runs arbitrary code within a custom (not sandboxed) environment
|
System command which runs arbitrary code within a custom (not sandboxed) environment
|
||||||
@commands _system-rcon
|
|
||||||
|
|
||||||
--- Get the names of all online players, using rcon
|
--- Get the names of all online players, using rcon
|
||||||
/_system-rcon local names = {}; for index, player in pairs(game.connected_player) do names[index] = player.name end; return names;
|
/_system-rcon local names = {}; for index, player in pairs(game.connected_player) do names[index] = player.name end; return names;
|
||||||
@@ -12,53 +11,60 @@ System command which runs arbitrary code within a custom (not sandboxed) environ
|
|||||||
local ExpUtil = require("modules/exp_util")
|
local ExpUtil = require("modules/exp_util")
|
||||||
local Async = require("modules/exp_util/async")
|
local Async = require("modules/exp_util/async")
|
||||||
local Storage = require("modules/exp_util/storage")
|
local Storage = require("modules/exp_util/storage")
|
||||||
local Commands = require("modules/exp_commands")
|
|
||||||
local Clustorio = require("modules/clusterio/api")
|
local Clustorio = require("modules/clusterio/api")
|
||||||
|
|
||||||
local rcon_env = {}
|
local Commands = require("modules/exp_commands") --- @class Commands
|
||||||
local rcon_statics = {}
|
|
||||||
local rcon_callbacks = {}
|
local rcon_env = {} --- @type table<string, any>
|
||||||
setmetatable(rcon_statics, { __index = _G })
|
local rcon_static = {} --- @type table<string, any>
|
||||||
setmetatable(rcon_env, { __index = rcon_statics })
|
local rcon_dynamic = {} --- @type table<string, ExpCommand.RconDynamic>
|
||||||
|
setmetatable(rcon_static, { __index = _G })
|
||||||
|
setmetatable(rcon_env, { __index = rcon_static })
|
||||||
|
|
||||||
--- Some common static values which can be added now
|
--- Some common static values which can be added now
|
||||||
--- @diagnostic disable: name-style-check
|
--- @diagnostic disable: name-style-check
|
||||||
rcon_statics.Async = Async
|
rcon_static.Async = Async
|
||||||
rcon_statics.ExpUtil = ExpUtil
|
rcon_static.ExpUtil = ExpUtil
|
||||||
rcon_statics.Commands = Commands
|
rcon_static.Commands = Commands
|
||||||
rcon_statics.Clustorio = Clustorio
|
rcon_static.Clustorio = Clustorio
|
||||||
rcon_statics.print = Commands.print
|
rcon_static.print = Commands.print
|
||||||
rcon_statics.ipc = Clustorio.send_json
|
rcon_static.ipc = Clustorio.send_json
|
||||||
--- @diagnostic enable: name-style-check
|
--- @diagnostic enable: name-style-check
|
||||||
|
|
||||||
--- Some common callback values which are useful when a player uses the command
|
--- Some common callback values which are useful when a player uses the command
|
||||||
function rcon_callbacks.player(player) return player end
|
--- @alias ExpCommand.RconDynamic fun(player: LuaPlayer?): any
|
||||||
|
|
||||||
function rcon_callbacks.surface(player) return player and player.surface end
|
function rcon_dynamic.player(player) return player end
|
||||||
|
|
||||||
function rcon_callbacks.force(player) return player and player.force end
|
function rcon_dynamic.surface(player) return player and player.surface end
|
||||||
|
|
||||||
function rcon_callbacks.position(player) return player and player.position end
|
function rcon_dynamic.force(player) return player and player.force end
|
||||||
|
|
||||||
function rcon_callbacks.entity(player) return player and player.selected end
|
function rcon_dynamic.position(player) return player and player.position end
|
||||||
|
|
||||||
function rcon_callbacks.tile(player) return player and player.surface.get_tile(player.position) end
|
function rcon_dynamic.entity(player) return player and player.selected end
|
||||||
|
|
||||||
|
function rcon_dynamic.tile(player) return player and player.surface.get_tile(player.position.x, player.position.y) end
|
||||||
|
|
||||||
--- The rcon env is saved between command runs to prevent desyncs
|
--- The rcon env is saved between command runs to prevent desyncs
|
||||||
Storage.register(rcon_env, function(tbl)
|
Storage.register(rcon_env, function(tbl)
|
||||||
rcon_env = setmetatable(tbl, { __index = rcon_statics })
|
rcon_env = setmetatable(tbl, { __index = rcon_static })
|
||||||
end)
|
end)
|
||||||
|
|
||||||
--- Static values can be added to the rcon env which are not stored in global such as modules
|
--- Static values can be added to the rcon env which are not stored in global such as modules
|
||||||
|
--- @param name string Name of the value as it will appear in the rcon environment
|
||||||
|
--- @param value any Value it is have
|
||||||
function Commands.add_rcon_static(name, value)
|
function Commands.add_rcon_static(name, value)
|
||||||
ExpUtil.assert_not_runtime()
|
ExpUtil.assert_not_runtime()
|
||||||
rcon_statics[name] = value
|
rcon_static[name] = value
|
||||||
end
|
end
|
||||||
|
|
||||||
--- Callback values can be added to the rcon env, these are called on each invocation and should return one value
|
--- Callback values can be added to the rcon env, these are called on each invocation and should return one value
|
||||||
function Commands.add_rcon_callback(name, callback)
|
--- @param name string Name of the value as it will appear in the rcon environment
|
||||||
|
--- @param callback ExpCommand.RconDynamic Callback called to get the current value
|
||||||
|
function Commands.add_rcon_dynamic(name, callback)
|
||||||
ExpUtil.assert_not_runtime()
|
ExpUtil.assert_not_runtime()
|
||||||
rcon_callbacks[name] = callback
|
rcon_dynamic[name] = callback
|
||||||
end
|
end
|
||||||
|
|
||||||
Commands.new("_rcon", { "exp-commands_rcon.description" })
|
Commands.new("_rcon", { "exp-commands_rcon.description" })
|
||||||
@@ -70,7 +76,7 @@ Commands.new("_rcon", { "exp-commands_rcon.description" })
|
|||||||
|
|
||||||
-- Construct the environment the command will run within
|
-- Construct the environment the command will run within
|
||||||
local env = setmetatable({}, { __index = rcon_env, __newindex = rcon_env })
|
local env = setmetatable({}, { __index = rcon_env, __newindex = rcon_env })
|
||||||
for name, callback in pairs(rcon_callbacks) do
|
for name, callback in pairs(rcon_dynamic) do
|
||||||
local _, rtn = pcall(callback, player.index > 0 and player or nil)
|
local _, rtn = pcall(callback, player.index > 0 and player or nil)
|
||||||
rawset(env, name, rtn)
|
rawset(env, name, rtn)
|
||||||
end
|
end
|
||||||
|
|||||||
@@ -1,6 +1,5 @@
|
|||||||
--[[-- Command Module - Sudo
|
--[[-- Commands - Sudo
|
||||||
System command to execute a command as another player using their permissions (except for permissions group actions)
|
System command to execute a command as another player using their permissions (except for permissions group actions)
|
||||||
@commands _system-sudo
|
|
||||||
|
|
||||||
--- Run the example command as another player
|
--- Run the example command as another player
|
||||||
-- As Cooldude2606: /repeat 5
|
-- As Cooldude2606: /repeat 5
|
||||||
|
|||||||
@@ -25,10 +25,9 @@ local Commands = require("modules/exp_commands")
|
|||||||
local add, parse = Commands.add_data_type, Commands.parse_input
|
local add, parse = Commands.add_data_type, Commands.parse_input
|
||||||
local valid, invalid = Commands.status.success, Commands.status.invalid_input
|
local valid, invalid = Commands.status.success, Commands.status.invalid_input
|
||||||
|
|
||||||
local types = {}
|
local types = {} --- @class Commands._types
|
||||||
|
|
||||||
--- A boolean value where true is one of: yes, y, true, 1
|
--- A boolean value where true is one of: yes, y, true, 1
|
||||||
--- @type Commands.InputParser
|
|
||||||
types.boolean =
|
types.boolean =
|
||||||
add("boolean", function(input)
|
add("boolean", function(input)
|
||||||
input = input:lower()
|
input = input:lower()
|
||||||
@@ -43,14 +42,12 @@ types.boolean =
|
|||||||
end)
|
end)
|
||||||
|
|
||||||
--- A string, validation does nothing but it is a requirement
|
--- A string, validation does nothing but it is a requirement
|
||||||
--- @type Commands.InputParser
|
|
||||||
types.string =
|
types.string =
|
||||||
add("string", function(input)
|
add("string", function(input)
|
||||||
return valid(input)
|
return valid(input)
|
||||||
end)
|
end)
|
||||||
|
|
||||||
--- A string from a set of options, takes one argument which is an array of options
|
--- A string from a set of options, takes one argument which is an array of options
|
||||||
--- @type Commands.InputParserFactory
|
|
||||||
types.enum =
|
types.enum =
|
||||||
add("enum", function(options)
|
add("enum", function(options)
|
||||||
--- @cast options string[]
|
--- @cast options string[]
|
||||||
@@ -65,10 +62,9 @@ types.enum =
|
|||||||
end)
|
end)
|
||||||
|
|
||||||
--- A string which is the key of a table, takes one argument which is an map of string keys to values
|
--- A string which is the key of a table, takes one argument which is an map of string keys to values
|
||||||
--- @type Commands.InputParserFactory
|
|
||||||
types.key_of =
|
types.key_of =
|
||||||
add("key_of", function(map)
|
add("key_of", function(map)
|
||||||
--- @cast map { [string]: any }
|
--- @cast map table<string, any>
|
||||||
return function(input)
|
return function(input)
|
||||||
local option = auto_complete(map, input, true)
|
local option = auto_complete(map, input, true)
|
||||||
if option == nil then
|
if option == nil then
|
||||||
@@ -80,7 +76,6 @@ types.key_of =
|
|||||||
end)
|
end)
|
||||||
|
|
||||||
--- A string with a maximum length, takes one argument which is the maximum length of a string
|
--- A string with a maximum length, takes one argument which is the maximum length of a string
|
||||||
--- @type Commands.InputParserFactory
|
|
||||||
types.string_max_length =
|
types.string_max_length =
|
||||||
add("string_max_length", function(maximum)
|
add("string_max_length", function(maximum)
|
||||||
--- @cast maximum number
|
--- @cast maximum number
|
||||||
@@ -94,7 +89,6 @@ types.string_max_length =
|
|||||||
end)
|
end)
|
||||||
|
|
||||||
--- A number
|
--- A number
|
||||||
--- @type Commands.InputParser
|
|
||||||
types.number =
|
types.number =
|
||||||
add("number", function(input)
|
add("number", function(input)
|
||||||
local number = tonumber(input)
|
local number = tonumber(input)
|
||||||
@@ -106,7 +100,6 @@ types.number =
|
|||||||
end)
|
end)
|
||||||
|
|
||||||
--- An integer, number which has been floored
|
--- An integer, number which has been floored
|
||||||
--- @type Commands.InputParser
|
|
||||||
types.integer =
|
types.integer =
|
||||||
add("integer", function(input)
|
add("integer", function(input)
|
||||||
local number = tonumber(input)
|
local number = tonumber(input)
|
||||||
@@ -118,7 +111,6 @@ types.integer =
|
|||||||
end)
|
end)
|
||||||
|
|
||||||
--- A number in a given inclusive range
|
--- A number in a given inclusive range
|
||||||
--- @type Commands.InputParserFactory
|
|
||||||
types.number_range =
|
types.number_range =
|
||||||
add("number_range", function(minimum, maximum)
|
add("number_range", function(minimum, maximum)
|
||||||
--- @cast minimum number
|
--- @cast minimum number
|
||||||
@@ -137,7 +129,6 @@ types.number_range =
|
|||||||
end)
|
end)
|
||||||
|
|
||||||
--- An integer in a given inclusive range
|
--- An integer in a given inclusive range
|
||||||
--- @type Commands.InputParserFactory
|
|
||||||
types.integer_range =
|
types.integer_range =
|
||||||
add("integer_range", function(minimum, maximum)
|
add("integer_range", function(minimum, maximum)
|
||||||
--- @cast minimum number
|
--- @cast minimum number
|
||||||
@@ -156,7 +147,6 @@ types.integer_range =
|
|||||||
end)
|
end)
|
||||||
|
|
||||||
--- A player who has joined the game at least once
|
--- A player who has joined the game at least once
|
||||||
--- @type Commands.InputParser
|
|
||||||
types.player =
|
types.player =
|
||||||
add("player", function(input)
|
add("player", function(input)
|
||||||
local player = game.get_player(input)
|
local player = game.get_player(input)
|
||||||
@@ -168,7 +158,6 @@ types.player =
|
|||||||
end)
|
end)
|
||||||
|
|
||||||
--- A player who is online
|
--- A player who is online
|
||||||
--- @type Commands.InputParser
|
|
||||||
types.player_online =
|
types.player_online =
|
||||||
add("player_online", function(input, player)
|
add("player_online", function(input, player)
|
||||||
local success, status, result = parse(input, player, Commands.types.player)
|
local success, status, result = parse(input, player, Commands.types.player)
|
||||||
@@ -183,8 +172,7 @@ types.player_online =
|
|||||||
end)
|
end)
|
||||||
|
|
||||||
--- A player who is online and alive
|
--- A player who is online and alive
|
||||||
--- @type Commands.InputParser
|
types.player_alive =
|
||||||
types.player_online =
|
|
||||||
add("player_alive", function(input, player)
|
add("player_alive", function(input, player)
|
||||||
local success, status, result = parse(input, player, Commands.types.player_online)
|
local success, status, result = parse(input, player, Commands.types.player_online)
|
||||||
--- @cast result LuaPlayer
|
--- @cast result LuaPlayer
|
||||||
@@ -198,7 +186,6 @@ types.player_online =
|
|||||||
end)
|
end)
|
||||||
|
|
||||||
--- A force within the game
|
--- A force within the game
|
||||||
--- @type Commands.InputParser
|
|
||||||
types.force =
|
types.force =
|
||||||
add("force", function(input)
|
add("force", function(input)
|
||||||
local force = game.forces[input]
|
local force = game.forces[input]
|
||||||
@@ -210,7 +197,6 @@ types.force =
|
|||||||
end)
|
end)
|
||||||
|
|
||||||
--- A surface within the game
|
--- A surface within the game
|
||||||
--- @type Commands.InputParser
|
|
||||||
types.surface =
|
types.surface =
|
||||||
add("surface", function(input)
|
add("surface", function(input)
|
||||||
local surface = game.surfaces[input]
|
local surface = game.surfaces[input]
|
||||||
@@ -222,7 +208,6 @@ types.surface =
|
|||||||
end)
|
end)
|
||||||
|
|
||||||
--- A planet within the game
|
--- A planet within the game
|
||||||
--- @type Commands.InputParser
|
|
||||||
types.planet =
|
types.planet =
|
||||||
add("planet", function(input)
|
add("planet", function(input)
|
||||||
local surface = game.planets[input]
|
local surface = game.planets[input]
|
||||||
@@ -234,7 +219,6 @@ types.planet =
|
|||||||
end)
|
end)
|
||||||
|
|
||||||
--- A name of a color from the predefined list, too many colours to use string-key
|
--- A name of a color from the predefined list, too many colours to use string-key
|
||||||
--- @type Commands.InputParser
|
|
||||||
types.color =
|
types.color =
|
||||||
add("color", function(input)
|
add("color", function(input)
|
||||||
local color = auto_complete(Commands.color, input, true)
|
local color = auto_complete(Commands.color, input, true)
|
||||||
|
|||||||
@@ -1,5 +1,3 @@
|
|||||||
color-tag=[color=__1__]__2__[/color]
|
|
||||||
|
|
||||||
[exp-commands]
|
[exp-commands]
|
||||||
help=__1__- __2____3__
|
help=__1__- __2____3__
|
||||||
aliases=\n Aliaies: __1__
|
aliases=\n Aliaies: __1__
|
||||||
|
|||||||
@@ -57,6 +57,7 @@ end)
|
|||||||
local ExpUtil = require("modules/exp_util")
|
local ExpUtil = require("modules/exp_util")
|
||||||
local Search = require("modules/exp_commands/search")
|
local Search = require("modules/exp_commands/search")
|
||||||
|
|
||||||
|
--- @class Commands
|
||||||
local Commands = {
|
local Commands = {
|
||||||
color = ExpUtil.color,
|
color = ExpUtil.color,
|
||||||
format_rich_text_color = ExpUtil.format_rich_text_color,
|
format_rich_text_color = ExpUtil.format_rich_text_color,
|
||||||
@@ -64,11 +65,9 @@ local Commands = {
|
|||||||
format_player_name = ExpUtil.format_player_name,
|
format_player_name = ExpUtil.format_player_name,
|
||||||
format_player_name_locale = ExpUtil.format_player_name_locale,
|
format_player_name_locale = ExpUtil.format_player_name_locale,
|
||||||
|
|
||||||
types = {}, --- @type { [string]: Commands.InputParser | Commands.InputParserFactory } Stores all input parsers and validators for different data types
|
registered_commands = {}, --- @type table<string, Commands.ExpCommand> Stores a reference to all registered commands
|
||||||
registered_commands = {}, --- @type { [string]: Commands.ExpCommand } Stores a reference to all registered commands
|
|
||||||
permission_authorities = {}, --- @type Commands.PermissionAuthority[] Stores a reference to all active permission authorities
|
permission_authorities = {}, --- @type Commands.PermissionAuthority[] Stores a reference to all active permission authorities
|
||||||
status = {}, -- Contains the different status values a command can return
|
|
||||||
|
|
||||||
--- @package Stores the event handlers
|
--- @package Stores the event handlers
|
||||||
events = {
|
events = {
|
||||||
[defines.events.on_player_locale_changed] = Search.on_player_locale_changed,
|
[defines.events.on_player_locale_changed] = Search.on_player_locale_changed,
|
||||||
@@ -77,6 +76,14 @@ local Commands = {
|
|||||||
},
|
},
|
||||||
}
|
}
|
||||||
|
|
||||||
|
--- @class Commands._status: table<string, Commands.Status>
|
||||||
|
--- Contains the different status values a command can return
|
||||||
|
Commands.status = {}
|
||||||
|
|
||||||
|
--- @class Commands._types: table<string, Commands.InputParser | Commands.InputParserFactory>
|
||||||
|
--- Stores all input parsers and validators for different data types
|
||||||
|
Commands.types = {}
|
||||||
|
|
||||||
--- @package
|
--- @package
|
||||||
function Commands.on_init() Search.prepare(Commands.registered_commands) end
|
function Commands.on_init() Search.prepare(Commands.registered_commands) end
|
||||||
|
|
||||||
@@ -91,7 +98,7 @@ end
|
|||||||
|
|
||||||
--- @class Commands.Argument
|
--- @class Commands.Argument
|
||||||
--- @field name string The name of the argument
|
--- @field name string The name of the argument
|
||||||
--- @field description LocalisedString The description of the argument
|
--- @field description LocalisedString? The description of the argument
|
||||||
--- @field input_parser Commands.InputParser The input parser for the argument
|
--- @field input_parser Commands.InputParser The input parser for the argument
|
||||||
--- @field optional boolean True when the argument is optional
|
--- @field optional boolean True when the argument is optional
|
||||||
--- @field default any? The default value of the argument
|
--- @field default any? The default value of the argument
|
||||||
@@ -135,15 +142,17 @@ Commands.server = setmetatable({
|
|||||||
show_on_map = false,
|
show_on_map = false,
|
||||||
valid = true,
|
valid = true,
|
||||||
object_name = "LuaPlayer",
|
object_name = "LuaPlayer",
|
||||||
|
print = rcon.print,
|
||||||
}, {
|
}, {
|
||||||
|
-- To prevent unnecessary logging Commands.error is called here and error is filtered by command_callback
|
||||||
__index = function(_, key)
|
__index = function(_, key)
|
||||||
if key == "__self" or type(key) == "number" then return nil end
|
if key == "__self" or type(key) == "number" then return nil end
|
||||||
Commands.error("Command does not support rcon usage, requires reading player." .. key)
|
Commands.error("Command does not support rcon usage, requires LuaPlayer." .. key)
|
||||||
error("Command does not support rcon usage, requires reading player." .. key)
|
error("Command does not support rcon usage, requires LuaPlayer." .. key)
|
||||||
end,
|
end,
|
||||||
__newindex = function(_, key)
|
__newindex = function(_, key)
|
||||||
Commands.error("Command does not support rcon usage, requires reading player." .. key)
|
Commands.error("Command does not support rcon usage, requires LuaPlayer." .. key)
|
||||||
error("Command does not support rcon usage, requires setting player." .. key)
|
error("Command does not support rcon usage, requires LuaPlayer." .. key)
|
||||||
end,
|
end,
|
||||||
})
|
})
|
||||||
|
|
||||||
@@ -155,7 +164,6 @@ Commands.server = setmetatable({
|
|||||||
--- Used to signal success from a command, data type parser, or permission authority
|
--- Used to signal success from a command, data type parser, or permission authority
|
||||||
--- @param msg LocalisedString? An optional message to be included when a command completes (only has an effect in command callbacks)
|
--- @param msg LocalisedString? An optional message to be included when a command completes (only has an effect in command callbacks)
|
||||||
--- @return Commands.Status, LocalisedString # Should be returned directly without modification
|
--- @return Commands.Status, LocalisedString # Should be returned directly without modification
|
||||||
--- @type Commands.Status
|
|
||||||
function Commands.status.success(msg)
|
function Commands.status.success(msg)
|
||||||
return Commands.status.success, msg or { "exp-commands.success" }
|
return Commands.status.success, msg or { "exp-commands.success" }
|
||||||
end
|
end
|
||||||
@@ -164,7 +172,6 @@ end
|
|||||||
--- For data type parsers and permission authority, an error return will prevent the command from being executed
|
--- For data type parsers and permission authority, an error return will prevent the command from being executed
|
||||||
--- @param msg LocalisedString? An optional error message to be included in the output, a generic message is used if not provided
|
--- @param msg LocalisedString? An optional error message to be included in the output, a generic message is used if not provided
|
||||||
--- @return Commands.Status, LocalisedString # Should be returned directly without modification
|
--- @return Commands.Status, LocalisedString # Should be returned directly without modification
|
||||||
--- @type Commands.Status
|
|
||||||
function Commands.status.error(msg)
|
function Commands.status.error(msg)
|
||||||
return Commands.status.error, { "exp-commands.error", msg or { "exp-commands.error-default" } }
|
return Commands.status.error, { "exp-commands.error", msg or { "exp-commands.error-default" } }
|
||||||
end
|
end
|
||||||
@@ -173,7 +180,6 @@ end
|
|||||||
--- For permission authorities, an unauthorised return will prevent the command from being executed
|
--- For permission authorities, an unauthorised return will prevent the command from being executed
|
||||||
--- @param msg LocalisedString? An optional error message to be included in the output, a generic message is used if not provided
|
--- @param msg LocalisedString? An optional error message to be included in the output, a generic message is used if not provided
|
||||||
--- @return Commands.Status, LocalisedString # Should be returned directly without modification
|
--- @return Commands.Status, LocalisedString # Should be returned directly without modification
|
||||||
--- @type Commands.Status
|
|
||||||
function Commands.status.unauthorised(msg)
|
function Commands.status.unauthorised(msg)
|
||||||
return Commands.status.unauthorised, msg or { "exp-commands.unauthorized", msg or { "exp-commands.unauthorized-default" } }
|
return Commands.status.unauthorised, msg or { "exp-commands.unauthorized", msg or { "exp-commands.unauthorized-default" } }
|
||||||
end
|
end
|
||||||
@@ -182,7 +188,6 @@ end
|
|||||||
--- For data type parsers, an invalid_input return will prevent the command from being executed
|
--- For data type parsers, an invalid_input return will prevent the command from being executed
|
||||||
--- @param msg LocalisedString? An optional error message to be included in the output, a generic message is used if not provided
|
--- @param msg LocalisedString? An optional error message to be included in the output, a generic message is used if not provided
|
||||||
--- @return Commands.Status, LocalisedString # Should be returned directly without modification
|
--- @return Commands.Status, LocalisedString # Should be returned directly without modification
|
||||||
--- @type Commands.Status
|
|
||||||
function Commands.status.invalid_input(msg)
|
function Commands.status.invalid_input(msg)
|
||||||
return Commands.status.invalid_input, msg or { "exp-commands.invalid-input" }
|
return Commands.status.invalid_input, msg or { "exp-commands.invalid-input" }
|
||||||
end
|
end
|
||||||
@@ -191,12 +196,11 @@ end
|
|||||||
--- @param msg LocalisedString A message detailing the error which has occurred, will be logged and outputted
|
--- @param msg LocalisedString A message detailing the error which has occurred, will be logged and outputted
|
||||||
--- @return Commands.Status, LocalisedString # Should be returned directly without modification
|
--- @return Commands.Status, LocalisedString # Should be returned directly without modification
|
||||||
--- @package
|
--- @package
|
||||||
--- @type Commands.Status
|
|
||||||
function Commands.status.internal_error(msg)
|
function Commands.status.internal_error(msg)
|
||||||
return Commands.status.internal_error, { "exp-commands.internal-error", msg }
|
return Commands.status.internal_error, { "exp-commands.internal-error", msg }
|
||||||
end
|
end
|
||||||
|
|
||||||
--- @type { [Commands.Status]: string }
|
--- @type table<Commands.Status, string>
|
||||||
local valid_command_status = {} -- Hashmap lookup for testing if a status is valid
|
local valid_command_status = {} -- Hashmap lookup for testing if a status is valid
|
||||||
for name, status in pairs(Commands.status) do
|
for name, status in pairs(Commands.status) do
|
||||||
valid_command_status[status] = name
|
valid_command_status[status] = name
|
||||||
@@ -205,7 +209,7 @@ end
|
|||||||
--- Permission Authority.
|
--- Permission Authority.
|
||||||
-- Functions that control who can use commands
|
-- Functions that control who can use commands
|
||||||
|
|
||||||
--- @alias Commands.PermissionAuthority fun(player: LuaPlayer, command: Commands.ExpCommand): boolean | Commands.Status, LocalisedString?
|
--- @alias Commands.PermissionAuthority fun(player: LuaPlayer, command: Commands.ExpCommand): boolean|Commands.Status, LocalisedString?
|
||||||
|
|
||||||
--- Add a permission authority, a permission authority is a function which provides access control for commands, multiple can be active at once
|
--- Add a permission authority, a permission authority is a function which provides access control for commands, multiple can be active at once
|
||||||
--- When multiple are active, all authorities must give permission for the command to execute, if any deny access then the command is not ran
|
--- When multiple are active, all authorities must give permission for the command to execute, if any deny access then the command is not ran
|
||||||
@@ -241,7 +245,7 @@ end
|
|||||||
--- @param player LuaPlayer? The player to test the permission of, nil represents the server and always returns true
|
--- @param player LuaPlayer? The player to test the permission of, nil represents the server and always returns true
|
||||||
--- @param command Commands.ExpCommand The command the player is attempting to use
|
--- @param command Commands.ExpCommand The command the player is attempting to use
|
||||||
--- @return boolean # True if the player has permission to use the command
|
--- @return boolean # True if the player has permission to use the command
|
||||||
--- @return LocalisedString # When permission is denied, this is the reason permission was denied
|
--- @return LocalisedString? # When permission is denied, this is the reason permission was denied
|
||||||
function Commands.player_has_permission(player, command)
|
function Commands.player_has_permission(player, command)
|
||||||
if player == nil or player == Commands.server then return true end
|
if player == nil or player == Commands.server then return true end
|
||||||
|
|
||||||
@@ -257,9 +261,7 @@ function Commands.player_has_permission(player, command)
|
|||||||
return false, msg
|
return false, msg
|
||||||
end
|
end
|
||||||
else
|
else
|
||||||
local class_name = ExpUtil.get_class_name(status)
|
error("Permission authority returned unexpected value: " .. ExpUtil.get_class_name(status))
|
||||||
local _, rtn_msg = Commands.status.internal_error("Permission authority returned unexpected value: " .. class_name)
|
|
||||||
return false, rtn_msg
|
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
|
|
||||||
@@ -269,16 +271,14 @@ end
|
|||||||
--- Data Type Parsing.
|
--- Data Type Parsing.
|
||||||
-- Functions that parse and validate player input
|
-- Functions that parse and validate player input
|
||||||
|
|
||||||
--- @generic T
|
--- @alias Commands.InputParser<T> fun(input: string, player: LuaPlayer): Commands.Status, (T | LocalisedString)
|
||||||
--- @alias Commands.InputParser (fun(input: string, player: LuaPlayer): T) | (fun(input: string, player: LuaPlayer): Commands.Status, LocalisedString | T)
|
|
||||||
|
|
||||||
--- @generic T
|
--- @alias Commands.InputParserFactory<T> fun(...: any): Commands.InputParser<T>
|
||||||
--- @alias Commands.InputParserFactory fun(...: any): Commands.InputParser<T>
|
|
||||||
|
|
||||||
--- Add a new input parser to the command library, this method validates that it does not already exist
|
--- Add a new input parser to the command library, this method validates that it does not already exist
|
||||||
--- @generic T : Commands.InputParser | Commands.InputParserFactory
|
--- @generic T : Commands.InputParser | Commands.InputParserFactory
|
||||||
--- @param data_type string The name of the data type the input parser reads in and validates, becomes a key of Commands.types
|
--- @param data_type string The name of the data type the input parser reads in and validates, becomes a key of Commands.types
|
||||||
--- @param input_parser `T` The function used to parse and validate the data type
|
--- @param input_parser T The function used to parse and validate the data type
|
||||||
--- @return T # The function which was provided as the second argument
|
--- @return T # The function which was provided as the second argument
|
||||||
function Commands.add_data_type(data_type, input_parser)
|
function Commands.add_data_type(data_type, input_parser)
|
||||||
if Commands.types[data_type] then
|
if Commands.types[data_type] then
|
||||||
@@ -310,33 +310,25 @@ end
|
|||||||
--- @return Commands.Status status, T | LocalisedString result # If success is false then Remaining values should be returned directly without modification
|
--- @return Commands.Status status, T | LocalisedString result # If success is false then Remaining values should be returned directly without modification
|
||||||
function Commands.parse_input(input, player, input_parser)
|
function Commands.parse_input(input, player, input_parser)
|
||||||
local status, status_msg = input_parser(input, player)
|
local status, status_msg = input_parser(input, player)
|
||||||
if status == nil then
|
if status == nil or not valid_command_status[status] then
|
||||||
local data_type = table.get_key(Commands.types, input_parser) or ExpUtil.get_function_name(input_parser, true)
|
local data_type = table.get_key(Commands.types, input_parser) or ExpUtil.get_function_name(input_parser, true)
|
||||||
local rtn_status, rtn_msg = Commands.status.internal_error("Parser for data type \"" .. data_type .. "\" returned a nil value")
|
error("Parser for data type \"" .. data_type .. "\" did not return a valid status got: " .. ExpUtil.get_class_name(status))
|
||||||
return false, rtn_status, rtn_msg
|
|
||||||
elseif valid_command_status[status] then
|
|
||||||
if status ~= Commands.status.success then
|
|
||||||
return false, status, status_msg
|
|
||||||
else
|
|
||||||
return true, status, status_msg -- status_msg is the parsed data
|
|
||||||
end
|
|
||||||
else
|
|
||||||
return true, Commands.status.success, status -- status is the parsed data
|
|
||||||
end
|
end
|
||||||
|
return status == Commands.status.success, status, status_msg
|
||||||
end
|
end
|
||||||
|
|
||||||
--- List and Search
|
--- List and Search
|
||||||
-- Functions used to list and search for commands
|
-- Functions used to list and search for commands
|
||||||
|
|
||||||
--- Returns a list of all registered custom commands
|
--- Returns a list of all registered custom commands
|
||||||
--- @return { [string]: Commands.ExpCommand } # A dictionary of commands
|
--- @return table<string,Commands.ExpCommand> # A dictionary of commands
|
||||||
function Commands.list_all()
|
function Commands.list_all()
|
||||||
return Commands.registered_commands
|
return Commands.registered_commands
|
||||||
end
|
end
|
||||||
|
|
||||||
--- Returns a list of all registered custom commands which the given player has permission to use
|
--- Returns a list of all registered custom commands which the given player has permission to use
|
||||||
--- @param player LuaPlayer? The player to get the command of, nil represents the server but list_all should be used
|
--- @param player LuaPlayer? The player to get the command of, nil represents the server but list_all should be used
|
||||||
--- @return { [string]: Commands.ExpCommand } # A dictionary of commands
|
--- @return table<string,Commands.ExpCommand> # A dictionary of commands
|
||||||
function Commands.list_for_player(player)
|
function Commands.list_for_player(player)
|
||||||
local rtn = {}
|
local rtn = {}
|
||||||
|
|
||||||
@@ -351,7 +343,7 @@ end
|
|||||||
|
|
||||||
--- Searches all custom commands and game commands for the given keyword
|
--- Searches all custom commands and game commands for the given keyword
|
||||||
--- @param keyword string The keyword to search for
|
--- @param keyword string The keyword to search for
|
||||||
--- @return { [string]: Commands.Command } # A dictionary of commands
|
--- @return table<string,Commands.Command> # A dictionary of commands
|
||||||
function Commands.search_all(keyword)
|
function Commands.search_all(keyword)
|
||||||
return Search.search_commands(keyword, Commands.list_all(), "en")
|
return Search.search_commands(keyword, Commands.list_all(), "en")
|
||||||
end
|
end
|
||||||
@@ -359,7 +351,7 @@ end
|
|||||||
--- Searches custom commands allowed for this player and all game commands for the given keyword
|
--- Searches custom commands allowed for this player and all game commands for the given keyword
|
||||||
--- @param keyword string The keyword to search for
|
--- @param keyword string The keyword to search for
|
||||||
--- @param player LuaPlayer? The player to search the commands of, nil represents server but search_all should be used
|
--- @param player LuaPlayer? The player to search the commands of, nil represents server but search_all should be used
|
||||||
--- @return { [string]: Commands.Command } # A dictionary of commands
|
--- @return table<string,Commands.Command> # A dictionary of commands
|
||||||
function Commands.search_for_player(keyword, player)
|
function Commands.search_for_player(keyword, player)
|
||||||
return Search.search_commands(keyword, Commands.list_for_player(player), player and player.locale)
|
return Search.search_commands(keyword, Commands.list_for_player(player), player and player.locale)
|
||||||
end
|
end
|
||||||
@@ -368,7 +360,13 @@ end
|
|||||||
-- Prints output to the player or rcon connection
|
-- Prints output to the player or rcon connection
|
||||||
|
|
||||||
local print_format_options = { max_line_count = 20 }
|
local print_format_options = { max_line_count = 20 }
|
||||||
local print_default_settings = { sound_path = "utility/scenario_message" }
|
local print_settings_default = { sound_path = "utility/scenario_message", color = ExpUtil.color.white }
|
||||||
|
local print_settings_error = { sound_path = "utility/wire_pickup", color = ExpUtil.color.orange_red }
|
||||||
|
|
||||||
|
Commands.print_settings = {
|
||||||
|
default = print_settings_default,
|
||||||
|
error = print_settings_error,
|
||||||
|
}
|
||||||
|
|
||||||
--- Print a message to the user of a command, accepts any value and will print in a readable and safe format
|
--- Print a message to the user of a command, accepts any value and will print in a readable and safe format
|
||||||
--- @param message any The message / value to be printed
|
--- @param message any The message / value to be printed
|
||||||
@@ -379,9 +377,9 @@ function Commands.print(message, settings)
|
|||||||
rcon.print(ExpUtil.format_any(message))
|
rcon.print(ExpUtil.format_any(message))
|
||||||
else
|
else
|
||||||
if not settings then
|
if not settings then
|
||||||
settings = print_default_settings
|
settings = print_settings_default
|
||||||
elseif not settings.sound_path then
|
elseif not settings.sound_path then
|
||||||
settings.sound_path = print_default_settings.sound_path
|
settings.sound_path = print_settings_default.sound_path
|
||||||
end
|
end
|
||||||
player.print(ExpUtil.format_any(message, print_format_options), settings)
|
player.print(ExpUtil.format_any(message, print_format_options), settings)
|
||||||
end
|
end
|
||||||
@@ -390,18 +388,21 @@ end
|
|||||||
--- Print an error message to the user of a command, accepts any value and will print in a readable and safe format
|
--- Print an error message to the user of a command, accepts any value and will print in a readable and safe format
|
||||||
--- @param message any The message / value to be printed
|
--- @param message any The message / value to be printed
|
||||||
function Commands.error(message)
|
function Commands.error(message)
|
||||||
Commands.print(message, {
|
Commands.print(message, print_settings_error)
|
||||||
color = ExpUtil.color.orange_red,
|
|
||||||
sound_path = "utility/wire_pickup",
|
|
||||||
})
|
|
||||||
end
|
end
|
||||||
|
|
||||||
--- Command Prototype
|
--- Command Prototype
|
||||||
-- The prototype definition for command objects
|
-- The prototype definition for command objects
|
||||||
|
|
||||||
|
local function assert_command_mutable(command)
|
||||||
|
if not Commands.registered_commands[command.name] then
|
||||||
|
error("Command cannot be modified after being registered.", 3)
|
||||||
|
end
|
||||||
|
end
|
||||||
|
|
||||||
--- Returns a new command object, this will not register the command but act as a way to start construction
|
--- Returns a new command object, this will not register the command but act as a way to start construction
|
||||||
--- @param name string The name of the command as it will be registered later
|
--- @param name string The name of the command as it will be registered later
|
||||||
--- @param description LocalisedString The description of the command displayed in the help message
|
--- @param description LocalisedString? The description of the command displayed in the help message
|
||||||
--- @return Commands.ExpCommand
|
--- @return Commands.ExpCommand
|
||||||
function Commands.new(name, description)
|
function Commands.new(name, description)
|
||||||
ExpUtil.assert_argument_type(name, "string", 1, "name")
|
ExpUtil.assert_argument_type(name, "string", 1, "name")
|
||||||
@@ -411,7 +412,7 @@ function Commands.new(name, description)
|
|||||||
|
|
||||||
return setmetatable({
|
return setmetatable({
|
||||||
name = name,
|
name = name,
|
||||||
description = description,
|
description = description or "",
|
||||||
help_text = description, -- Will be replaced in command:register
|
help_text = description, -- Will be replaced in command:register
|
||||||
callback = default_command_callback, -- Will be replaced in command:register
|
callback = default_command_callback, -- Will be replaced in command:register
|
||||||
defined_at = ExpUtil.safe_file_path(2),
|
defined_at = ExpUtil.safe_file_path(2),
|
||||||
@@ -426,10 +427,11 @@ end
|
|||||||
|
|
||||||
--- Add a new required argument to the command of the given data type
|
--- Add a new required argument to the command of the given data type
|
||||||
--- @param name string The name of the argument being added
|
--- @param name string The name of the argument being added
|
||||||
--- @param description LocalisedString The description of the argument being added
|
--- @param description LocalisedString? The description of the argument being added
|
||||||
--- @param input_parser Commands.InputParser The input parser to be used for the argument
|
--- @param input_parser Commands.InputParser The input parser to be used for the argument
|
||||||
--- @return Commands.ExpCommand
|
--- @return Commands.ExpCommand
|
||||||
function Commands._prototype:argument(name, description, input_parser)
|
function Commands._prototype:argument(name, description, input_parser)
|
||||||
|
assert_command_mutable(self)
|
||||||
if self.min_arg_count ~= self.max_arg_count then
|
if self.min_arg_count ~= self.max_arg_count then
|
||||||
error("Can not have required arguments after optional arguments", 2)
|
error("Can not have required arguments after optional arguments", 2)
|
||||||
end
|
end
|
||||||
@@ -446,10 +448,11 @@ end
|
|||||||
|
|
||||||
--- Add a new optional argument to the command of the given data type
|
--- Add a new optional argument to the command of the given data type
|
||||||
--- @param name string The name of the argument being added
|
--- @param name string The name of the argument being added
|
||||||
--- @param description LocalisedString The description of the argument being added
|
--- @param description LocalisedString? The description of the argument being added
|
||||||
--- @param input_parser Commands.InputParser The input parser to be used for the argument
|
--- @param input_parser Commands.InputParser The input parser to be used for the argument
|
||||||
--- @return Commands.ExpCommand
|
--- @return Commands.ExpCommand
|
||||||
function Commands._prototype:optional(name, description, input_parser)
|
function Commands._prototype:optional(name, description, input_parser)
|
||||||
|
assert_command_mutable(self)
|
||||||
self.max_arg_count = self.max_arg_count + 1
|
self.max_arg_count = self.max_arg_count + 1
|
||||||
self.arguments[#self.arguments + 1] = {
|
self.arguments[#self.arguments + 1] = {
|
||||||
name = name,
|
name = name,
|
||||||
@@ -461,9 +464,10 @@ function Commands._prototype:optional(name, description, input_parser)
|
|||||||
end
|
end
|
||||||
|
|
||||||
--- Set the defaults for optional arguments, any not provided will have their value as nil
|
--- Set the defaults for optional arguments, any not provided will have their value as nil
|
||||||
--- @param defaults table The default values for the optional arguments, the key is the name of the argument
|
--- @param defaults table<string, (fun(player: LuaPlayer): any) | any> The default values for the optional arguments, the key is the name of the argument
|
||||||
--- @return Commands.ExpCommand
|
--- @return Commands.ExpCommand
|
||||||
function Commands._prototype:defaults(defaults)
|
function Commands._prototype:defaults(defaults)
|
||||||
|
assert_command_mutable(self)
|
||||||
local matched = {}
|
local matched = {}
|
||||||
for _, argument in ipairs(self.arguments) do
|
for _, argument in ipairs(self.arguments) do
|
||||||
if defaults[argument.name] then
|
if defaults[argument.name] then
|
||||||
@@ -489,6 +493,7 @@ end
|
|||||||
--- @param flags table An array of strings or a dictionary of flag names and values, when an array is used the flags values are set to true
|
--- @param flags table An array of strings or a dictionary of flag names and values, when an array is used the flags values are set to true
|
||||||
--- @return Commands.ExpCommand
|
--- @return Commands.ExpCommand
|
||||||
function Commands._prototype:add_flags(flags)
|
function Commands._prototype:add_flags(flags)
|
||||||
|
assert_command_mutable(self)
|
||||||
for name, value in pairs(flags) do
|
for name, value in pairs(flags) do
|
||||||
if type(name) == "number" then
|
if type(name) == "number" then
|
||||||
self.flags[value] = true
|
self.flags[value] = true
|
||||||
@@ -504,6 +509,7 @@ end
|
|||||||
--- @param aliases string[] An array of string names to use as aliases to this command
|
--- @param aliases string[] An array of string names to use as aliases to this command
|
||||||
--- @return Commands.ExpCommand
|
--- @return Commands.ExpCommand
|
||||||
function Commands._prototype:add_aliases(aliases)
|
function Commands._prototype:add_aliases(aliases)
|
||||||
|
assert_command_mutable(self)
|
||||||
local start_index = #self.aliases
|
local start_index = #self.aliases
|
||||||
for index, alias in ipairs(aliases) do
|
for index, alias in ipairs(aliases) do
|
||||||
self.aliases[start_index + index] = alias
|
self.aliases[start_index + index] = alias
|
||||||
@@ -515,32 +521,41 @@ end
|
|||||||
--- Enable concatenation of all arguments after the last, this should be used for user provided reason text
|
--- Enable concatenation of all arguments after the last, this should be used for user provided reason text
|
||||||
--- @return Commands.ExpCommand
|
--- @return Commands.ExpCommand
|
||||||
function Commands._prototype:enable_auto_concatenation()
|
function Commands._prototype:enable_auto_concatenation()
|
||||||
|
assert_command_mutable(self)
|
||||||
self.auto_concat = true
|
self.auto_concat = true
|
||||||
return self
|
return self
|
||||||
end
|
end
|
||||||
|
|
||||||
--- Register the command to the game with the given callback, this must be the final step as the object becomes immutable afterwards
|
--- Register the command to the game with the given callback, this must be the final step as the object becomes immutable afterwards
|
||||||
--- @param callback Commands.Callback The function which is called to perform the command action
|
--- @param callback Commands.Callback The function which is called to perform the command action
|
||||||
|
--- @return Commands.ExpCommand
|
||||||
function Commands._prototype:register(callback)
|
function Commands._prototype:register(callback)
|
||||||
|
assert_command_mutable(self)
|
||||||
Commands.registered_commands[self.name] = self
|
Commands.registered_commands[self.name] = self
|
||||||
self.callback = callback
|
self.callback = callback
|
||||||
|
|
||||||
-- Generates a description to be used
|
-- Generates a description to be used
|
||||||
local argument_names = { "" } --- @type LocalisedString
|
local argument_names = { "" } --- @type LocalisedString
|
||||||
local argument_help_text = { "", "" } --- @type LocalisedString
|
local argument_verbose = { "" } --- @type LocalisedString
|
||||||
local help_text = { "exp-commands.help", argument_names, self.description, argument_help_text } --- @type LocalisedString
|
self.help_text = { "exp-commands.help", argument_names, self.description, argument_verbose } --- @type LocalisedString
|
||||||
self.help_text = help_text
|
|
||||||
if next(self.aliases) then
|
if next(self.aliases) then
|
||||||
argument_help_text[2] = { "exp-commands.aliases", table.concat(self.aliases, ", ") }
|
argument_verbose[2] = { "exp-commands.aliases", table.concat(self.aliases, ", ") }
|
||||||
end
|
end
|
||||||
|
|
||||||
|
local verbose_index = #argument_verbose
|
||||||
for index, argument in pairs(self.arguments) do
|
for index, argument in pairs(self.arguments) do
|
||||||
if argument.optional then
|
if argument.optional then
|
||||||
argument_names[index + 2] = { "exp-commands.optional", argument.name }
|
argument_names[index + 1] = { "exp-commands.optional", argument.name }
|
||||||
argument_help_text[index + 2] = { "exp-commands.optional-verbose", argument.name, argument.description }
|
if argument.description and argument.description ~= "" then
|
||||||
|
verbose_index = verbose_index + 1
|
||||||
|
argument_verbose[verbose_index] = { "exp-commands.optional-verbose", argument.name, argument.description }
|
||||||
|
end
|
||||||
else
|
else
|
||||||
argument_names[index + 2] = { "exp-commands.argument", argument.name }
|
argument_names[index + 1] = { "exp-commands.argument", argument.name }
|
||||||
argument_help_text[index + 2] = { "exp-commands.argument-verbose", argument.name, argument.description }
|
if argument.description and argument.description ~= "" then
|
||||||
|
verbose_index = verbose_index + 1
|
||||||
|
argument_verbose[verbose_index] = { "exp-commands.argument-verbose", argument.name, argument.description }
|
||||||
|
end
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
|
|
||||||
@@ -565,6 +580,8 @@ function Commands._prototype:register(callback)
|
|||||||
for _, alias in ipairs(self.aliases) do
|
for _, alias in ipairs(self.aliases) do
|
||||||
commands.add_command(alias, self.help_text, command_callback)
|
commands.add_command(alias, self.help_text, command_callback)
|
||||||
end
|
end
|
||||||
|
|
||||||
|
return self
|
||||||
end
|
end
|
||||||
|
|
||||||
--- Command Runner
|
--- Command Runner
|
||||||
@@ -633,7 +650,6 @@ end
|
|||||||
--- Internal event handler for the command event
|
--- Internal event handler for the command event
|
||||||
--- @param event CustomCommandData
|
--- @param event CustomCommandData
|
||||||
--- @return nil
|
--- @return nil
|
||||||
--- @package
|
|
||||||
function Commands._event_handler(event)
|
function Commands._event_handler(event)
|
||||||
local command = Commands.registered_commands[event.name]
|
local command = Commands.registered_commands[event.name]
|
||||||
if command == nil then
|
if command == nil then
|
||||||
@@ -695,20 +711,20 @@ function Commands._event_handler(event)
|
|||||||
end
|
end
|
||||||
end
|
end
|
||||||
|
|
||||||
-- Run the command, dont need xpcall here because errors are caught in command_callback
|
-- Run the command, don't need xpcall here because errors are caught in command_callback
|
||||||
local status, status_msg = command.callback(player, table.unpack(arguments))
|
local status, status_msg = command.callback(player, table.unpack(arguments))
|
||||||
if status and valid_command_status[status] then
|
if status == nil then
|
||||||
if status ~= Commands.status.success then
|
|
||||||
log_command("Custom Error", command, player, event.parameter, status_msg)
|
|
||||||
return Commands.error(status_msg)
|
|
||||||
else
|
|
||||||
log_command("Command Ran", command, player, event.parameter)
|
|
||||||
return Commands.print(status_msg)
|
|
||||||
end
|
|
||||||
else
|
|
||||||
log_command("Command Ran", command, player, event.parameter)
|
log_command("Command Ran", command, player, event.parameter)
|
||||||
local _, msg = Commands.status.success()
|
local _, msg = Commands.status.success()
|
||||||
return Commands.print(msg)
|
return Commands.print(msg)
|
||||||
|
elseif not valid_command_status[status] then
|
||||||
|
error("Command \"" .. command.name .. "\" did not return a valid status got: " .. ExpUtil.get_class_name(status))
|
||||||
|
elseif status ~= Commands.status.success then
|
||||||
|
log_command("Custom Error", command, player, event.parameter, status_msg)
|
||||||
|
return Commands.error(status_msg)
|
||||||
|
else
|
||||||
|
log_command("Command Ran", command, player, event.parameter)
|
||||||
|
return Commands.print(status_msg)
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
|
|
||||||
|
|||||||
@@ -3,8 +3,8 @@ local Search = {}
|
|||||||
local Storage = require("modules/exp_util/storage")
|
local Storage = require("modules/exp_util/storage")
|
||||||
|
|
||||||
--- Setup the storage to contain the pending translations and the completed ones
|
--- Setup the storage to contain the pending translations and the completed ones
|
||||||
local pending = {} --- @type { [uint]: { [1]: string, [2]: string }? }
|
local pending = {} --- @type { [1]: string, [2]: string }[]
|
||||||
local translations = {} --- @type { [string]: { [string]: string } }
|
local translations = {} --- @type table<string, table<string, string>>
|
||||||
Storage.register({
|
Storage.register({
|
||||||
pending,
|
pending,
|
||||||
translations,
|
translations,
|
||||||
@@ -14,13 +14,13 @@ Storage.register({
|
|||||||
end)
|
end)
|
||||||
|
|
||||||
local command_names = {} --- @type string[]
|
local command_names = {} --- @type string[]
|
||||||
local command_objects = {} --- @type { [string]: Commands.Command }
|
local command_objects = {} --- @type table<string, Commands.Command>
|
||||||
local required_translations = {} --- @type LocalisedString[]
|
local required_translations = {} --- @type LocalisedString[]
|
||||||
|
|
||||||
--- Gets the descriptions of all commands, not including their aliases
|
--- Gets the descriptions of all commands, not including their aliases
|
||||||
--- @param custom_commands { [string]: Commands.ExpCommand } The complete list of registered custom commands
|
--- @param custom_commands table<string, Commands.ExpCommand> The complete list of registered custom commands
|
||||||
function Search.prepare(custom_commands)
|
function Search.prepare(custom_commands)
|
||||||
local known_aliases = {} --- @type { [string]: string }
|
local known_aliases = {} --- @type table<string, string>
|
||||||
for name, command in pairs(custom_commands) do
|
for name, command in pairs(custom_commands) do
|
||||||
for _, alias in ipairs(command.aliases) do
|
for _, alias in ipairs(command.aliases) do
|
||||||
known_aliases[alias] = name
|
known_aliases[alias] = name
|
||||||
@@ -85,11 +85,11 @@ end
|
|||||||
|
|
||||||
--- Searches all game commands and the provided custom commands for the given keyword
|
--- Searches all game commands and the provided custom commands for the given keyword
|
||||||
--- @param keyword string The keyword to search for
|
--- @param keyword string The keyword to search for
|
||||||
--- @param custom_commands { [string]: Commands.ExpCommand } A dictionary of commands to search
|
--- @param custom_commands table<string, Commands.ExpCommand> A dictionary of commands to search
|
||||||
--- @param locale string? The local to search, default is english ("en")
|
--- @param locale string? The local to search, default is english ("en")
|
||||||
--- @return { [string]: Commands.Command } # A dictionary of commands
|
--- @return table<string, Commands.Command> # A dictionary of commands
|
||||||
function Search.search_commands(keyword, custom_commands, locale)
|
function Search.search_commands(keyword, custom_commands, locale)
|
||||||
local rtn = {} --- @type { [string]: Commands.Command }
|
local rtn = {} --- @type table<string, Commands.Command>
|
||||||
keyword = keyword:lower()
|
keyword = keyword:lower()
|
||||||
locale = locale or "en"
|
locale = locale or "en"
|
||||||
|
|
||||||
|
|||||||
Reference in New Issue
Block a user