|
8 | 8 | #include <stdio.h> |
9 | 9 | #include <git2.h> |
10 | 10 | #include "cli.h" |
| 11 | +#include "cmd.h" |
11 | 12 |
|
| 13 | +static int show_help = 0; |
12 | 14 | static int show_version = 0; |
| 15 | +static char *command = NULL; |
| 16 | +static char **args = NULL; |
13 | 17 |
|
14 | | -static const cli_opt_spec common_opts[] = { |
15 | | - { CLI_OPT_TYPE_SWITCH, "version", 0, &show_version, 1, |
16 | | - CLI_OPT_USAGE_DEFAULT, NULL, "display the version" }, |
| 18 | +const cli_opt_spec cli_common_opts[] = { |
| 19 | + { CLI_OPT_TYPE_SWITCH, "help", 0, &show_help, 1, |
| 20 | + CLI_OPT_USAGE_DEFAULT, NULL, "display help information" }, |
| 21 | + { CLI_OPT_TYPE_SWITCH, "version", 0, &show_version, 1, |
| 22 | + CLI_OPT_USAGE_DEFAULT, NULL, "display the version" }, |
| 23 | + { CLI_OPT_TYPE_ARG, "command", 0, &command, 0, |
| 24 | + CLI_OPT_USAGE_REQUIRED, "command", "the command to run" }, |
| 25 | + { CLI_OPT_TYPE_ARGS, "args", 0, &args, 0, |
| 26 | + CLI_OPT_USAGE_DEFAULT, "args", "arguments for the command" }, |
17 | 27 | { 0 } |
18 | 28 | }; |
19 | 29 |
|
| 30 | +const cli_cmd_spec cli_cmds[] = { |
| 31 | + { "help", cmd_help, "Display help information" }, |
| 32 | + { NULL } |
| 33 | +}; |
| 34 | + |
20 | 35 | int main(int argc, char **argv) |
21 | 36 | { |
| 37 | + const cli_cmd_spec *cmd; |
22 | 38 | cli_opt_parser optparser; |
23 | 39 | cli_opt opt; |
| 40 | + int args_len = 0; |
24 | 41 | int ret = 0; |
25 | 42 |
|
26 | 43 | if (git_libgit2_init() < 0) { |
27 | 44 | cli_error("failed to initialize libgit2"); |
28 | 45 | exit(CLI_EXIT_GIT); |
29 | 46 | } |
30 | 47 |
|
31 | | - cli_opt_parser_init(&optparser, common_opts, argv + 1, argc - 1, CLI_OPT_PARSE_GNU); |
| 48 | + cli_opt_parser_init(&optparser, cli_common_opts, argv + 1, argc - 1, CLI_OPT_PARSE_GNU); |
32 | 49 |
|
33 | 50 | /* Parse the top-level (common) options and command information */ |
34 | 51 | while (cli_opt_parser_next(&opt, &optparser)) { |
35 | 52 | if (!opt.spec) { |
36 | 53 | cli_opt_status_fprint(stderr, PROGRAM_NAME, &opt); |
37 | | - cli_opt_usage_fprint(stderr, PROGRAM_NAME, NULL, common_opts); |
| 54 | + cli_opt_usage_fprint(stderr, PROGRAM_NAME, NULL, cli_common_opts); |
38 | 55 | ret = CLI_EXIT_USAGE; |
39 | 56 | goto done; |
40 | 57 | } |
| 58 | + |
| 59 | + /* |
| 60 | + * When we see a command, stop parsing and capture the |
| 61 | + * remaining arguments as args for the command itself. |
| 62 | + */ |
| 63 | + if (command) { |
| 64 | + args = &argv[optparser.idx]; |
| 65 | + args_len = (int)(argc - optparser.idx); |
| 66 | + break; |
| 67 | + } |
41 | 68 | } |
42 | 69 |
|
43 | 70 | if (show_version) { |
44 | 71 | printf("%s version %s\n", PROGRAM_NAME, LIBGIT2_VERSION); |
45 | 72 | goto done; |
46 | 73 | } |
47 | 74 |
|
| 75 | + /* If there was no command, we want to invoke "help" */ |
| 76 | + if (!command || show_help) { |
| 77 | + cli_opt_usage_fprint(stdout, PROGRAM_NAME, NULL, cli_common_opts); |
| 78 | + goto done; |
| 79 | + } |
| 80 | + |
| 81 | + if ((cmd = cli_cmd_spec_byname(command)) == NULL) { |
| 82 | + ret = cli_error("'%s' is not a %s command. See '%s help'.", |
| 83 | + command, PROGRAM_NAME, PROGRAM_NAME); |
| 84 | + goto done; |
| 85 | + } |
| 86 | + |
| 87 | + ret = cmd->fn(args_len, args); |
| 88 | + |
48 | 89 | done: |
49 | 90 | git_libgit2_shutdown(); |
50 | 91 | return ret; |
|
0 commit comments