Line data Source code
1 : /* SPDX-License-Identifier: GPL-3.0-or-later */
2 : /* Copyright 2026 Peter Csaszar */
3 :
4 : /**
5 : * @file test_tg_tui_argv.c
6 : * @brief Unit tests for tg-tui argv dispatch helpers.
7 : *
8 : * Exercises the logic that was added in FEAT-15:
9 : * - --phone / --code / --password values are picked up from argv
10 : * - PromptCtx fields are populated correctly
11 : * - Interactive fallback (NULL) is preserved when a flag is absent
12 : *
13 : * Because tg_tui.c has a `main()` we cannot link it directly. The tests
14 : * replicate the argv-scanning logic inline and verify invariants.
15 : */
16 :
17 : #include "test_helpers.h"
18 :
19 : #include <string.h>
20 : #include <stddef.h>
21 :
22 : /* ---- replicate the argv scanning logic from tg_tui.c:main() ---- */
23 :
24 : typedef struct {
25 : const char *phone;
26 : const char *code;
27 : const char *password;
28 : } TuiBatchOpts;
29 :
30 : /**
31 : * @brief Scan argv for --phone / --code / --password / --tui.
32 : *
33 : * This is the same loop that lives in tg_tui.c:main().
34 : */
35 4 : static TuiBatchOpts scan_tui_argv(int argc, char **argv) {
36 4 : TuiBatchOpts opts = { NULL, NULL, NULL };
37 11 : for (int i = 1; i < argc; i++) {
38 7 : if (strcmp(argv[i], "--phone") == 0 && i + 1 < argc) {
39 2 : opts.phone = argv[++i];
40 5 : } else if (strcmp(argv[i], "--code") == 0 && i + 1 < argc) {
41 2 : opts.code = argv[++i];
42 3 : } else if (strcmp(argv[i], "--password") == 0 && i + 1 < argc) {
43 1 : opts.password = argv[++i];
44 : }
45 : }
46 4 : return opts;
47 : }
48 :
49 : /** Helper: detect --logout flag. */
50 2 : static int has_logout_flag(int argc, char **argv) {
51 2 : for (int i = 1; i < argc; i++) {
52 1 : if (strcmp(argv[i], "--logout") == 0) return 1;
53 : }
54 1 : return 0;
55 : }
56 :
57 : /** Helper: detect --tui flag. */
58 3 : static int has_tui_flag(int argc, char **argv) {
59 3 : for (int i = 1; i < argc; i++) {
60 2 : if (strcmp(argv[i], "--tui") == 0) return 1;
61 : }
62 1 : return 0;
63 : }
64 :
65 : /* ---- tests ---- */
66 :
67 : /** Batch credentials are extracted from argv correctly. */
68 1 : static void test_batch_creds_parsed(void) {
69 1 : char *argv[] = {
70 : "tg-tui",
71 : "--phone", "+15551234567",
72 : "--code", "12345",
73 : "--password", "s3cr3t",
74 : NULL
75 : };
76 1 : TuiBatchOpts opts = scan_tui_argv(7, argv);
77 1 : ASSERT(opts.phone != NULL, "phone must be set");
78 1 : ASSERT(strcmp(opts.phone, "+15551234567") == 0, "phone value correct");
79 1 : ASSERT(opts.code != NULL, "code must be set");
80 1 : ASSERT(strcmp(opts.code, "12345") == 0, "code value correct");
81 1 : ASSERT(opts.password != NULL, "password must be set");
82 1 : ASSERT(strcmp(opts.password, "s3cr3t") == 0, "password value correct");
83 : }
84 :
85 : /** When no batch flags are given all fields stay NULL (interactive mode). */
86 1 : static void test_batch_creds_absent(void) {
87 1 : char *argv[] = { "tg-tui", NULL };
88 1 : TuiBatchOpts opts = scan_tui_argv(1, argv);
89 1 : ASSERT(opts.phone == NULL, "phone must be NULL when absent");
90 1 : ASSERT(opts.code == NULL, "code must be NULL when absent");
91 1 : ASSERT(opts.password == NULL, "password must be NULL when absent");
92 : }
93 :
94 : /** --tui flag is detected. */
95 1 : static void test_tui_flag_detected(void) {
96 1 : char *argv_yes[] = { "tg-tui", "--tui", NULL };
97 1 : char *argv_no[] = { "tg-tui", NULL };
98 1 : ASSERT(has_tui_flag(2, argv_yes) == 1, "--tui detected");
99 1 : ASSERT(has_tui_flag(1, argv_no) == 0, "--tui absent");
100 : }
101 :
102 : /** --logout flag is detected. */
103 1 : static void test_logout_flag_detected(void) {
104 1 : char *argv_yes[] = { "tg-tui", "--logout", NULL };
105 1 : char *argv_no[] = { "tg-tui", NULL };
106 1 : ASSERT(has_logout_flag(2, argv_yes) == 1, "--logout detected");
107 1 : ASSERT(has_logout_flag(1, argv_no) == 0, "--logout absent");
108 : }
109 :
110 : /** --phone without a following value is silently ignored (no OOB access). */
111 1 : static void test_phone_missing_value(void) {
112 1 : char *argv[] = { "tg-tui", "--phone", NULL };
113 1 : TuiBatchOpts opts = scan_tui_argv(2, argv);
114 1 : ASSERT(opts.phone == NULL, "--phone with no value leaves phone NULL");
115 : }
116 :
117 : /** Mixed batch + --tui flags coexist correctly. */
118 1 : static void test_batch_and_tui_coexist(void) {
119 1 : char *argv[] = {
120 : "tg-tui",
121 : "--tui",
122 : "--phone", "+447911123456",
123 : "--code", "99999",
124 : NULL
125 : };
126 1 : TuiBatchOpts opts = scan_tui_argv(6, argv);
127 1 : ASSERT(has_tui_flag(6, argv) == 1, "--tui detected alongside batch flags");
128 1 : ASSERT(opts.phone != NULL, "phone set with --tui present");
129 1 : ASSERT(strcmp(opts.phone, "+447911123456") == 0, "phone value correct");
130 1 : ASSERT(opts.code != NULL, "code set with --tui present");
131 1 : ASSERT(opts.password == NULL, "password NULL when not given");
132 : }
133 :
134 1 : void run_tg_tui_argv_tests(void) {
135 1 : RUN_TEST(test_batch_creds_parsed);
136 1 : RUN_TEST(test_batch_creds_absent);
137 1 : RUN_TEST(test_tui_flag_detected);
138 1 : RUN_TEST(test_logout_flag_detected);
139 1 : RUN_TEST(test_phone_missing_value);
140 1 : RUN_TEST(test_batch_and_tui_coexist);
141 1 : }
|