diff --git a/src/module.c b/src/module.c index 59b432d7d3..c4ec3f7277 100644 --- a/src/module.c +++ b/src/module.c @@ -6082,6 +6082,14 @@ const char *moduleTypeModuleName(moduleType *mt) { return mt->module->name; } +/* Return the module name from a module command */ +const char *moduleNameFromCommand(struct redisCommand *cmd) { + serverAssert(cmd->proc == RedisModuleCommandDispatcher); + + RedisModuleCommand *cp = (void*)(unsigned long)cmd->getkeys_proc; + return cp->module->name; +} + /* Create a copy of a module type value using the copy callback. If failed * or not supported, produce an error reply and return NULL. */ diff --git a/src/server.c b/src/server.c index 84f21fed3e..21c96a4538 100644 --- a/src/server.c +++ b/src/server.c @@ -4562,6 +4562,7 @@ void addReplyCommandDocs(client *c, struct redisCommand *cmd) { long maplen = 1; if (cmd->summary) maplen++; if (cmd->since) maplen++; + if (cmd->flags & CMD_MODULE) maplen++; if (cmd->complexity) maplen++; if (cmd->doc_flags) maplen++; if (cmd->deprecated_since) maplen++; @@ -4588,6 +4589,10 @@ void addReplyCommandDocs(client *c, struct redisCommand *cmd) { addReplyBulkCString(c, "complexity"); addReplyBulkCString(c, cmd->complexity); } + if (cmd->flags & CMD_MODULE) { + addReplyBulkCString(c, "module"); + addReplyBulkCString(c, moduleNameFromCommand(cmd)); + } if (cmd->doc_flags) { addReplyBulkCString(c, "doc_flags"); addReplyDocFlagsForCommand(c, cmd); diff --git a/src/server.h b/src/server.h index edfea2226c..02c00de5c7 100644 --- a/src/server.h +++ b/src/server.h @@ -2349,6 +2349,7 @@ int moduleGetCommandChannelsViaAPI(struct redisCommand *cmd, robj **argv, int ar moduleType *moduleTypeLookupModuleByID(uint64_t id); void moduleTypeNameByID(char *name, uint64_t moduleid); const char *moduleTypeModuleName(moduleType *mt); +const char *moduleNameFromCommand(struct redisCommand *cmd); void moduleFreeContext(struct RedisModuleCtx *ctx); void unblockClientFromModule(client *c); void moduleHandleBlockedClients(void); diff --git a/tests/unit/moduleapi/cmdintrospection.tcl b/tests/unit/moduleapi/cmdintrospection.tcl index 375b3e406a..8ac49ed9ff 100644 --- a/tests/unit/moduleapi/cmdintrospection.tcl +++ b/tests/unit/moduleapi/cmdintrospection.tcl @@ -36,6 +36,7 @@ start_server {tags {"modules"}} { # Compare the maps. We need to pop "group" first. dict unset redis_reply group dict unset module_reply group + dict unset module_reply module assert_equal $redis_reply $module_reply } diff --git a/tests/unit/moduleapi/subcommands.tcl b/tests/unit/moduleapi/subcommands.tcl index 11d2432435..5bc881d842 100644 --- a/tests/unit/moduleapi/subcommands.tcl +++ b/tests/unit/moduleapi/subcommands.tcl @@ -15,8 +15,8 @@ start_server {tags {"modules"}} { set docs_reply [r command docs subcommands.bitarray] set docs [dict create {*}[lindex $docs_reply 1]] set subcmds_in_cmd_docs [dict create {*}[dict get $docs subcommands]] - assert_equal [dict get $subcmds_in_cmd_docs "subcommands.bitarray|get"] {group module} - assert_equal [dict get $subcmds_in_cmd_docs "subcommands.bitarray|set"] {group module} + assert_equal [dict get $subcmds_in_cmd_docs "subcommands.bitarray|get"] {group module module subcommands} + assert_equal [dict get $subcmds_in_cmd_docs "subcommands.bitarray|set"] {group module module subcommands} } test "Module pure-container command fails on arity error" {