From: Mark Jamsek Subject: regress for tog log limit and search To: gameoftrees@openbsd.org Date: Wed, 30 Aug 2023 01:03:13 +1000 As per the subject, this adds another couple basic tog log tests: one for the limit view (&) and one for grep (/). I want to add more test cases (e.g., no matches) but this is a start. This needed a little change in tog.c, too, but just to parse the new test instructions and use the corresponding input string for our search terms, so only impacts test harness use. ----------------------------------------------- commit bf98ad5a80013b223a2a5248bc34d2d7ab55b826 (main) from: Mark Jamsek date: Tue Aug 29 14:45:03 2023 UTC tog: add basic regress for log limit and log search M regress/tog/log.sh | 142+ 0- M tog/tog.c | 70+ 43- 2 files changed, 212 insertions(+), 43 deletions(-) diff 2cafc7864a7ffed14fede7310877bc28c6e7ef8f bf98ad5a80013b223a2a5248bc34d2d7ab55b826 commit - 2cafc7864a7ffed14fede7310877bc28c6e7ef8f commit + bf98ad5a80013b223a2a5248bc34d2d7ab55b826 blob - c9e0f9386c09837c4f369034ac78348d9c7f2abd blob + 78b614f3984b52d0bfbfe54ccd9d9141bb7cf891 --- regress/tog/log.sh +++ regress/tog/log.sh @@ -586,6 +586,146 @@ test_log_show_base_commit() test_done "$testroot" "$ret" } +test_log_limit_view() +{ + test_init log_limit_view 80 4 + local repo="$testroot/repo" + local wt="$testroot/wt" + + got checkout "$repo" "$wt" > /dev/null + ret=$? + if [ $ret -ne 0 ]; then + echo "got checkout failed unexpectedly" + test_done "$testroot" "$ret" + return 1 + fi + + cd "$wt" # test is in a subshell + + echo "alpha0" > alpha + got commit -m alpha0 > /dev/null + ret=$? + if [ $ret -ne 0 ]; then + echo "got commit failed unexpectedly" >&2 + test_done "$testroot" "$ret" + return 1 + fi + + echo "beta0" > beta + got commit -m beta0 > /dev/null + ret=$? + if [ $ret -ne 0 ]; then + echo "got commit failed unexpectedly" >&2 + test_done "$testroot" "$ret" + return 1 + fi + + echo "alpha1" > alpha + got commit -m alpha1 > /dev/null + ret=$? + if [ $ret -ne 0 ]; then + echo "got commit failed unexpectedly" >&2 + test_done "$testroot" "$ret" + return 1 + fi + + echo "beta1" > beta + got commit -m beta1 > /dev/null + ret=$? + if [ $ret -ne 0 ]; then + echo "got commit failed unexpectedly" >&2 + test_done "$testroot" "$ret" + return 1 + fi + local author_time=$(git_show_author_time "$repo") + local ymd=$(date -u -r $author_time +"%G-%m-%d") + local id=$(git_show_head "$repo") + + # check base commit marker is not drawn + cat <<-EOF >$TOG_TEST_SCRIPT + &beta + SCREENDUMP + EOF + + cat <<-EOF >$testroot/view.expected + commit $id [1/2] master + $ymd flan_hacker [master] beta1 + $ymd flan_hacker beta0 + + EOF + + tog log + cmp -s "$testroot/view.expected" "$testroot/view" + ret=$? + if [ $ret -ne 0 ]; then + diff -u "$testroot/view.expected" "$testroot/view" + fi + test_done "$testroot" "$ret" +} + +test_log_search() +{ + test_init log_search 80 8 + local repo="$testroot/repo" + local wt="$testroot/wt" + local id=$(git_show_head "$repo") + + set -- "$id" + + got checkout "$repo" "$wt" > /dev/null + ret=$? + if [ $ret -ne 0 ]; then + echo "got checkout failed unexpectedly" + test_done "$testroot" "$ret" + return 1 + fi + + cd "$wt" # subshell + + for i in $(seq 16); do + echo "alpha $i" > alpha + + got ci -m "alpha commit $i" > /dev/null + ret=$? + if [ $ret -ne 0 ]; then + echo "got commit failed unexpectedly" >&2 + test_done "$testroot" "$ret" + return 1 + fi + + id=$(git_show_head "$repo") + set -- "$@" "$id" + done + + local author_time=$(git_show_author_time "$repo") + local ymd=$(date -u -r $author_time +"%G-%m-%d") + + cat <<-EOF >$TOG_TEST_SCRIPT + /alpha commit 8 + n + SCREENDUMP + EOF + + cat <<-EOF >$testroot/view.expected + commit $(pop_idx 9 $@) [9/17] no more matches + $ymd flan_hacker alpha commit 14 + $ymd flan_hacker alpha commit 13 + $ymd flan_hacker alpha commit 12 + $ymd flan_hacker alpha commit 11 + $ymd flan_hacker alpha commit 10 + $ymd flan_hacker alpha commit 9 + $ymd flan_hacker alpha commit 8 + EOF + + tog log + cmp -s "$testroot/view.expected" "$testroot/view" + ret=$? + if [ $ret -ne 0 ]; then + diff -u "$testroot/view.expected" "$testroot/view" + fi + test_done "$testroot" "$ret" +} + test_parseargs "$@" run_test test_log_hsplit_diff run_test test_log_vsplit_diff @@ -596,3 +736,5 @@ run_test test_log_hsplit_tree run_test test_log_logmsg_widechar run_test test_log_commit_keywords run_test test_log_show_base_commit +run_test test_log_limit_view +run_test test_log_search blob - cab4456a4b158f5d1d403cde77be97005c76057f blob + a3da7e007be3791e1abcc6838dc6f592581eeb65 --- tog/tog.c +++ tog/tog.c @@ -628,6 +628,7 @@ struct tog_io { FILE *cout; FILE *f; FILE *sdump; + char *input_str; int wait_for_ui; } tog_io; static int using_mock_io; @@ -1333,22 +1334,27 @@ view_search_start(struct tog_view *view, int fast_refr else if (view->mode == TOG_VIEW_SPLIT_VERT && view->parent) v = view->parent; - mvwaddstr(v->window, v->nlines - 1, 0, "/"); - wclrtoeol(v->window); + if (tog_io.input_str != NULL) { + if (strlcpy(pattern, tog_io.input_str, sizeof(pattern)) >= + sizeof(pattern)) + return got_error(GOT_ERR_NO_SPACE); + } else { + mvwaddstr(v->window, v->nlines - 1, 0, "/"); + wclrtoeol(v->window); + nodelay(v->window, FALSE); /* block for search term input */ + nocbreak(); + echo(); + ret = wgetnstr(v->window, pattern, sizeof(pattern)); + wrefresh(v->window); + cbreak(); + noecho(); + nodelay(v->window, TRUE); + if (!fast_refresh && !using_mock_io) + halfdelay(10); + if (ret == ERR) + return NULL; + } - nodelay(v->window, FALSE); /* block for search term input */ - nocbreak(); - echo(); - ret = wgetnstr(v->window, pattern, sizeof(pattern)); - wrefresh(v->window); - cbreak(); - noecho(); - nodelay(v->window, TRUE); - if (!fast_refresh && !using_mock_io) - halfdelay(10); - if (ret == ERR) - return NULL; - if (regcomp(&view->regex, pattern, REG_EXTENDED | REG_NEWLINE) == 0) { err = view->search_start(view); if (err) { @@ -1629,14 +1635,16 @@ tog_read_script_key(FILE *script, struct tog_view *vie const struct got_error *err = NULL; char *line = NULL; size_t linesz = 0; + ssize_t n; + if (view->count && --view->count) { *ch = view->ch; return NULL; } else *ch = -1; - if (getline(&line, &linesz, script) == -1) { + if ((n = getline(&line, &linesz, script)) == -1) { if (feof(script)) { *done = 1; goto done; @@ -1671,8 +1679,17 @@ tog_read_script_key(FILE *script, struct tog_view *vie *t = '\0'; /* ignore error, view->count is 0 if instruction is invalid */ view->count = strtonum(line, 0, INT_MAX, NULL); - } else + } else { *ch = *line; + if (n > 2 && (*ch == '/' || *ch == '&')) { + /* skip leading keymap and trim trailing newline */ + tog_io.input_str = strndup(line + 1, n - 2); + if (tog_io.input_str == NULL) { + err = got_error_from_errno("strndup"); + goto done; + } + } + } done: free(line); @@ -1963,6 +1980,8 @@ tog_io_close(void) err = got_ferror(tog_io.f, GOT_ERR_IO); if (tog_io.sdump && fclose(tog_io.sdump) == EOF && err == NULL) err = got_ferror(tog_io.sdump, GOT_ERR_IO); + if (tog_io.input_str != NULL) + free(tog_io.input_str); return err; } @@ -3547,19 +3566,24 @@ limit_log_view(struct tog_view *view) else if (view->mode == TOG_VIEW_SPLIT_VERT && view->parent) v = view->parent; - /* Get the pattern */ - wmove(v->window, v->nlines - 1, 0); - wclrtoeol(v->window); - mvwaddstr(v->window, v->nlines - 1, 0, "&/"); - nodelay(v->window, FALSE); - nocbreak(); - echo(); - ret = wgetnstr(v->window, pattern, sizeof(pattern)); - cbreak(); - noecho(); - nodelay(v->window, TRUE); - if (ret == ERR) - return NULL; + if (tog_io.input_str != NULL) { + if (strlcpy(pattern, tog_io.input_str, sizeof(pattern)) >= + sizeof(pattern)) + return got_error(GOT_ERR_NO_SPACE); + } else { + wmove(v->window, v->nlines - 1, 0); + wclrtoeol(v->window); + mvwaddstr(v->window, v->nlines - 1, 0, "&/"); + nodelay(v->window, FALSE); + nocbreak(); + echo(); + ret = wgetnstr(v->window, pattern, sizeof(pattern)); + cbreak(); + noecho(); + nodelay(v->window, TRUE); + if (ret == ERR) + return NULL; + } if (*pattern == '\0') { /* @@ -3670,19 +3694,22 @@ search_next_log_view(struct tog_view *view) doupdate(); if (s->search_entry) { - int errcode, ch; - errcode = pthread_mutex_unlock(&tog_mutex); - if (errcode) - return got_error_set_errno(errcode, - "pthread_mutex_unlock"); - ch = wgetch(view->window); - errcode = pthread_mutex_lock(&tog_mutex); - if (errcode) - return got_error_set_errno(errcode, - "pthread_mutex_lock"); - if (ch == CTRL('g') || ch == KEY_BACKSPACE) { - view->search_next_done = TOG_SEARCH_HAVE_MORE; - return NULL; + if (!using_mock_io) { + int errcode, ch; + + errcode = pthread_mutex_unlock(&tog_mutex); + if (errcode) + return got_error_set_errno(errcode, + "pthread_mutex_unlock"); + ch = wgetch(view->window); + errcode = pthread_mutex_lock(&tog_mutex); + if (errcode) + return got_error_set_errno(errcode, + "pthread_mutex_lock"); + if (ch == CTRL('g') || ch == KEY_BACKSPACE) { + view->search_next_done = TOG_SEARCH_HAVE_MORE; + return NULL; + } } if (view->searching == TOG_SEARCH_FORWARD) entry = TAILQ_NEXT(s->search_entry, entry); -- Mark Jamsek GPG: F2FF 13DE 6A06 C471 CA80 E6E2 2930 DC66 86EE CF68