From 43b7851b9f91a0d5abc50a5622268445df8c639c Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Marco=20Diego=20Aur=C3=A9lio=20Mesquita?= Date: Mon, 4 Sep 2017 18:53:36 -0300 Subject: [PATCH] Improve execute command prompt MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit Signed-off-by: Marco Diego Aurélio Mesquita --- src/files.c | 105 +++++++++++++++++++++++++++++++++++++++++++++++++++++++---- src/global.c | 10 ++++-- src/nano.c | 6 ++++ src/nano.h | 1 + src/proto.h | 5 +++ src/rcfile.c | 3 ++ src/search.c | 13 ++++++++ 7 files changed, 135 insertions(+), 8 deletions(-) diff --git a/src/files.c b/src/files.c index 6a6bb1ca..12c13c7c 100644 --- a/src/files.c +++ b/src/files.c @@ -1039,6 +1039,8 @@ void do_insertfile(void) { int i; const char *msg; + static char *lastcommand = NULL; + char *prompt; char *given = mallocstrcpy(NULL, ""); /* The last answer the user typed at the statusbar prompt. */ #ifndef NANO_TINY @@ -1069,6 +1071,10 @@ void do_insertfile(void) msg = _("File to insert [from %s]"); } + if(!execute || lastcommand == NULL || asprintf(&prompt, "%s [%s]", msg, lastcommand) == -1) + prompt = (char*)msg; + + present_path = mallocstrcpy(present_path, "./"); i = do_prompt(TRUE, TRUE, @@ -1077,17 +1083,17 @@ void do_insertfile(void) #endif MINSERTFILE, given, #ifndef DISABLE_HISTORIES - NULL, + execute ? &execute_history : NULL, #endif - edit_refresh, msg, + edit_refresh, prompt, #ifndef DISABLE_OPERATINGDIR operating_dir != NULL ? operating_dir : #endif "./"); - /* If we're in multibuffer mode and the filename or command is + /* If we're in multibuffer mode and the filename is * blank, open a new buffer instead of canceling. */ - if (i == -1 || (i == -2 && !ISSET(MULTIBUFFER))) { + if (i == -1 || (i == -2 && lastcommand == NULL) || (!execute && i == -2 && !ISSET(MULTIBUFFER))) { statusbar(_("Cancelled")); break; } else { @@ -1128,7 +1134,7 @@ void do_insertfile(void) } #endif /* If we don't have a file yet, go back to the prompt. */ - if (i != 0 && (!ISSET(MULTIBUFFER) || i != -2)) + if (!execute && ((i != 0 && (!ISSET(MULTIBUFFER) || i != -2)))) continue; #ifndef NANO_TINY @@ -1139,7 +1145,13 @@ void do_insertfile(void) open_buffer("", FALSE); #endif /* Save the command's output in the current buffer. */ - execute_command(answer); + if (*answer != '\0') { + execute_command(answer); + lastcommand = strdup(answer); + update_history(&execute_history, answer); + } else { + execute_command(lastcommand); + } #ifdef ENABLE_MULTIBUFFER /* If this is a new buffer, put the cursor at the top. */ @@ -2720,6 +2732,11 @@ char *histfilename(void) return construct_filename("/.nano/search_history"); } +char *executehistfilename(void) +{ + return construct_filename("/.nano/execute_history"); +} + /* Construct the legacy history filename. */ /* (To be removed in 2018.) */ char *legacyhistfilename(void) @@ -2774,6 +2791,48 @@ int check_dotnano(void) return ret; } +/* Load the search and replace histories from ~/.nano/command_history. */ +void load_executehistory(void) +{ + char *searchhist = executehistfilename(); + FILE *hist; + + /* If no home directory was found, we can't do anything. */ + if (searchhist == NULL) + return; + + hist = fopen(searchhist, "rb"); + + if (hist == NULL) { + if (errno != ENOENT) { + UNSET(EXECUTELOG); + /* When reading failed, don't save history when we quit. */ + history_error(N_("Error reading %s: %s"), searchhist, + strerror(errno)); + } + } else { + /* Load the two history lists -- first the search history, then + * the replace history -- from the oldest entry to the newest. + * The two lists are separated by an empty line. */ + filestruct **history = &execute_history; + char *line = NULL; + size_t buf_len = 0; + ssize_t read; + + while ((read = getline(&line, &buf_len, hist)) > 1) { + line[--read] = '\0'; + /* Encode any embedded NUL as 0x0A. */ + unsunder(line, read); + update_history(history, line); + } + + fclose(hist); + free(line); + } + + free(searchhist); +} + /* Load the search and replace histories from ~/.nano/search_history. */ void load_history(void) { @@ -2859,6 +2918,40 @@ bool writehist(FILE *hist, const filestruct *head) } /* Save the search and replace histories to ~/.nano/search_history. */ +void save_executehistory(void) +{ + char *searchhist; + FILE *hist; + + /* If the histories are unchanged or empty, don't bother saving them. */ + if (!history_has_changed() || executebot->lineno == 1) + return; + + searchhist = executehistfilename(); + + if (searchhist == NULL) + return; + + hist = fopen(searchhist, "wb"); + + if (hist == NULL) + fprintf(stderr, _("Error writing %s: %s\n"), searchhist, + strerror(errno)); + else { + /* Don't allow others to read or write the history file. */ + chmod(searchhist, S_IRUSR | S_IWUSR); + + if (!writehist(hist, executeage)) + fprintf(stderr, _("Error writing %s: %s\n"), searchhist, + strerror(errno)); + + fclose(hist); + } + + free(searchhist); +} + +/* Save the search and replace histories to ~/.nano/search_history. */ void save_history(void) { char *searchhist; diff --git a/src/global.c b/src/global.c index e2017115..dd27c726 100644 --- a/src/global.c +++ b/src/global.c @@ -205,6 +205,12 @@ filestruct *searchage = NULL; /* The top of the search string history list. */ filestruct *searchbot = NULL; /* The bottom of the search string history list. */ +filestruct *execute_history = NULL; + /* The search string history list. */ +filestruct *executeage = NULL; + /* The top of the search string history list. */ +filestruct *executebot = NULL; + /* The bottom of the search string history list. */ filestruct *replace_history = NULL; /* The replace string history list. */ filestruct *replaceage = NULL; @@ -1265,8 +1271,8 @@ void shortcut_init(void) add_to_sclist(MWHEREIS|MREPLACE|MREPLACEWITH|MWHEREISFILE|MFINDINHELP, "^N", 0, get_history_newer_void, 0); #ifdef ENABLE_UTF8 if (using_utf8()) { - add_to_sclist(MWHEREIS|MREPLACE|MREPLACEWITH|MWHEREISFILE|MFINDINHELP, "\xE2\x86\x91", KEY_UP, get_history_older_void, 0); - add_to_sclist(MWHEREIS|MREPLACE|MREPLACEWITH|MWHEREISFILE|MFINDINHELP, "\xE2\x86\x93", KEY_DOWN, get_history_newer_void, 0); + add_to_sclist(MWHEREIS|MREPLACE|MREPLACEWITH|MWHEREISFILE|MFINDINHELP|MEXTCMD, "\xE2\x86\x91", KEY_UP, get_history_older_void, 0); + add_to_sclist(MWHEREIS|MREPLACE|MREPLACEWITH|MWHEREISFILE|MFINDINHELP|MEXTCMD, "\xE2\x86\x93", KEY_DOWN, get_history_newer_void, 0); } else #endif { diff --git a/src/nano.c b/src/nano.c index f29cea90..cb9babc9 100644 --- a/src/nano.c +++ b/src/nano.c @@ -564,6 +564,8 @@ void finish(void) #ifndef DISABLE_HISTORIES if (ISSET(HISTORYLOG)) save_history(); + if (ISSET(EXECUTELOG)) + save_executehistory(); if (ISSET(POS_HISTORY)) { update_poshistory(openfile->filename, openfile->current->lineno, xplustabs() + 1); save_poshistory(); @@ -2252,6 +2254,7 @@ int main(int argc, char **argv) #ifdef ENABLE_NANORC no_rcfiles = TRUE; UNSET(HISTORYLOG); + UNSET(EXECUTELOG); UNSET(POS_HISTORY); #endif } @@ -2374,11 +2377,14 @@ int main(int argc, char **argv) get_homedir(); if (homedir == NULL || check_dotnano() == 0) { UNSET(HISTORYLOG); + UNSET(EXECUTELOG); UNSET(POS_HISTORY); } } if (ISSET(HISTORYLOG)) load_history(); + if (ISSET(EXECUTELOG)) + load_executehistory(); if (ISSET(POS_HISTORY)) load_poshistory(); #endif /* !DISABLE_HISTORIES */ diff --git a/src/nano.h b/src/nano.h index 1a77097a..ee48c4fb 100644 --- a/src/nano.h +++ b/src/nano.h @@ -501,6 +501,7 @@ enum NO_COLOR_SYNTAX, PRESERVE, HISTORYLOG, + EXECUTELOG, RESTRICTED, SMART_HOME, WHITESPACE_DISPLAY, diff --git a/src/proto.h b/src/proto.h index 8ee4eb0e..9c3a0215 100644 --- a/src/proto.h +++ b/src/proto.h @@ -159,6 +159,9 @@ extern subnfunc *uncutfunc; extern filestruct *search_history; extern filestruct *searchage; extern filestruct *searchbot; +extern filestruct *execute_history; +extern filestruct *executeage; +extern filestruct *executebot; extern filestruct *replace_history; extern filestruct *replaceage; extern filestruct *replacebot; @@ -319,6 +322,8 @@ const char *tail(const char *path); #ifndef DISABLE_HISTORIES void load_history(void); void save_history(void); +void load_executehistory(void); +void save_executehistory(void); int check_dotnano(void); void load_poshistory(void); void save_poshistory(void); diff --git a/src/rcfile.c b/src/rcfile.c index 3750bf3e..fd715031 100644 --- a/src/rcfile.c +++ b/src/rcfile.c @@ -44,6 +44,9 @@ static const rcoption rcopts[] = { #endif {"const", CONSTANT_SHOW}, /* deprecated form, remove in 2018 */ {"constantshow", CONSTANT_SHOW}, +#ifndef DISABLE_HISTORIES + {"executelog", EXECUTELOG}, +#endif #ifndef DISABLE_WRAPJUSTIFY {"fill", 0}, #endif diff --git a/src/search.c b/src/search.c index 92d90223..c2aa46db 100644 --- a/src/search.c +++ b/src/search.c @@ -1103,6 +1103,11 @@ void history_init(void) searchage = search_history; searchbot = search_history; + execute_history = make_new_node(NULL); + execute_history->data = mallocstrcpy(NULL, ""); + executeage = execute_history; + executebot = execute_history; + replace_history = make_new_node(NULL); replace_history->data = mallocstrcpy(NULL, ""); replaceage = replace_history; @@ -1114,6 +1119,8 @@ void history_reset(const filestruct *h) { if (h == search_history) search_history = searchbot; + else if (h == execute_history) + execute_history = executebot; else if (h == replace_history) replace_history = replacebot; } @@ -1145,6 +1152,9 @@ void update_history(filestruct **h, const char *s) if (*h == search_history) { hage = &searchage; hbot = &searchbot; + } else if (*h == execute_history) { + hage = &executeage; + hbot = &executebot; } else if (*h == replace_history) { hage = &replaceage; hbot = &replacebot; @@ -1245,6 +1255,9 @@ char *get_history_completion(filestruct **h, char *s, size_t len) if (*h == search_history) { hage = searchage; hbot = searchbot; + } else if (*h == execute_history) { + hage = executeage; + hbot = executebot; } else if (*h == replace_history) { hage = replaceage; hbot = replacebot; -- 2.11.0