jsonrpc: help, even for a single item, should be in an array.

This is what we do for every other can-be-single JSON API.

Signed-off-by: Rusty Russell <rusty@rustcorp.com.au>
This commit is contained in:
Rusty Russell 2019-02-04 21:25:35 +10:30
parent a1ebfc9e5e
commit da355284de
3 changed files with 28 additions and 19 deletions

View file

@ -24,6 +24,7 @@ and this project adheres to [Semantic Versioning](http://semver.org/spec/v2.0.0.
- The `short_channel_id` separator has been changed to be `x` to match the specification. - The `short_channel_id` separator has been changed to be `x` to match the specification.
- JSON API: `listpeers` now includes `funding_allocation_msat`, which returns a map of the amounts initially funded to the channel by each peer, indexed by channel id. - JSON API: `listpeers` now includes `funding_allocation_msat`, which returns a map of the amounts initially funded to the channel by each peer, indexed by channel id.
- `option_data_loss_protect` is now enabled by default. - `option_data_loss_protect` is now enabled by default.
- JSON API: `help` with a `command` argument gives a JSON array, like other commands.
### Deprecated ### Deprecated

View file

@ -329,6 +329,17 @@ static void json_add_help_command(struct command *cmd,
} }
static const struct json_command *find_command(struct json_command **commands,
const char *buffer,
const jsmntok_t *cmdtok)
{
for (size_t i = 0; i < tal_count(commands); i++) {
if (json_tok_streq(buffer, cmdtok, commands[i]->name))
return commands[i];
}
return NULL;
}
static struct command_result *json_help(struct command *cmd, static struct command_result *json_help(struct command *cmd,
const char *buffer, const char *buffer,
const jsmntok_t *obj UNNEEDED, const jsmntok_t *obj UNNEEDED,
@ -337,6 +348,7 @@ static struct command_result *json_help(struct command *cmd,
struct json_stream *response; struct json_stream *response;
const jsmntok_t *cmdtok; const jsmntok_t *cmdtok;
struct json_command **commands = cmd->ld->jsonrpc->commands; struct json_command **commands = cmd->ld->jsonrpc->commands;
const struct json_command *one_cmd;
if (!param(cmd, buffer, params, if (!param(cmd, buffer, params,
p_opt("command", param_tok, &cmdtok), p_opt("command", param_tok, &cmdtok),
@ -344,29 +356,25 @@ static struct command_result *json_help(struct command *cmd,
return command_param_failed(); return command_param_failed();
if (cmdtok) { if (cmdtok) {
for (size_t i = 0; i < tal_count(commands); i++) { one_cmd = find_command(commands, buffer, cmdtok);
if (json_tok_streq(buffer, cmdtok, commands[i]->name)) { if (!one_cmd)
response = json_stream_success(cmd); return command_fail(cmd, JSONRPC2_METHOD_NOT_FOUND,
json_add_help_command(cmd, response, commands[i]); "Unknown command '%.*s'",
goto done; cmdtok->end - cmdtok->start,
} buffer + cmdtok->start);
} } else
return command_fail(cmd, JSONRPC2_METHOD_NOT_FOUND, one_cmd = NULL;
"Unknown command '%.*s'",
cmdtok->end - cmdtok->start,
buffer + cmdtok->start);
}
response = json_stream_success(cmd); response = json_stream_success(cmd);
json_object_start(response, NULL); json_object_start(response, NULL);
json_array_start(response, "help"); json_array_start(response, "help");
for (size_t i=0; i<tal_count(commands); i++) { for (size_t i = 0; i < tal_count(commands); i++) {
json_add_help_command(cmd, response, commands[i]); if (!one_cmd || one_cmd == commands[i])
json_add_help_command(cmd, response, commands[i]);
} }
json_array_end(response); json_array_end(response);
json_object_end(response); json_object_end(response);
done:
return command_success(cmd, response); return command_success(cmd, response);
} }

View file

@ -731,7 +731,7 @@ def test_cli(node_factory):
'-J', '-J',
'help', 'command=help']).decode('utf-8') 'help', 'command=help']).decode('utf-8')
j, _ = json.JSONDecoder().raw_decode(out) j, _ = json.JSONDecoder().raw_decode(out)
assert 'help [command]' in j['verbose'] assert 'help [command]' in j['help'][0]['verbose']
# Test keyword input (forced) # Test keyword input (forced)
out = subprocess.check_output(['cli/lightning-cli', out = subprocess.check_output(['cli/lightning-cli',
@ -740,7 +740,7 @@ def test_cli(node_factory):
'-J', '-k', '-J', '-k',
'help', 'command=help']).decode('utf-8') 'help', 'command=help']).decode('utf-8')
j, _ = json.JSONDecoder().raw_decode(out) j, _ = json.JSONDecoder().raw_decode(out)
assert 'help [command]' in j['verbose'] assert 'help [command]' in j['help'][0]['verbose']
# Test ordered input (autodetect) # Test ordered input (autodetect)
out = subprocess.check_output(['cli/lightning-cli', out = subprocess.check_output(['cli/lightning-cli',
@ -749,7 +749,7 @@ def test_cli(node_factory):
'-J', '-J',
'help', 'help']).decode('utf-8') 'help', 'help']).decode('utf-8')
j, _ = json.JSONDecoder().raw_decode(out) j, _ = json.JSONDecoder().raw_decode(out)
assert 'help [command]' in j['verbose'] assert 'help [command]' in j['help'][0]['verbose']
# Test ordered input (forced) # Test ordered input (forced)
out = subprocess.check_output(['cli/lightning-cli', out = subprocess.check_output(['cli/lightning-cli',
@ -758,7 +758,7 @@ def test_cli(node_factory):
'-J', '-o', '-J', '-o',
'help', 'help']).decode('utf-8') 'help', 'help']).decode('utf-8')
j, _ = json.JSONDecoder().raw_decode(out) j, _ = json.JSONDecoder().raw_decode(out)
assert 'help [command]' in j['verbose'] assert 'help [command]' in j['help'][0]['verbose']
# Test missing parameters. # Test missing parameters.
try: try: