如何删除历史记录中与给定字符串匹配的命令?


13

我需要删除历史记录中与字符串匹配的所有命令。我试过了:

$ history | grep searchstring | cut -d" " -f2 | history -d
-bash: history: -d: option requires an argument

$ history | grep searchstring | cut -d" " -f2 | xargs history -d
xargs: history: No such file or directory

$ temparg() { while read i; do "$@" "$i"; done }
$ history | grep searchstring | cut -d" " -f2 | temparg history -d
(no error, but nothing is deleted)

什么是正确的方法?


1
尽管下面有有效的答案,但我仍然想知道为什么它不适用于history -d X。我碰到了这个问题,因为我刚刚做了history | grep search_str | sort -nr | awk '{print $1}' | while read i; do history -d $i; done。没有错误,但没有删除任何内容。有人可以解释为什么吗?
mivk 2013年

Answers:


18

history命令仅对您的历史记录文件$HISTFILE(通常是~/.history~/.bash_history)起作用。如果仅从该文件中删除行,则将容易得多,这可以通过多种方法来完成。grep是一种方法,但是您必须注意不要在仍然读取文件时覆盖文件:

$ grep -v searchstring "$HISTFILE" > /tmp/history
$ mv /tmp/history "$HISTFILE"

另一种方法是sed

$ sed -i '/searchstring/d' "$HISTFILE"

好答案; $HISTFILE可能包含空格,可能值得引用。
克里斯·

小心... histfile是不可预测的,如果您有许多打开的shell,就无法说明将保存什么以及以什么顺序保存。任何人都可以确认已经打开的外壳在关闭时不会重写初始化时加载的历史记录吗?
Orion

8

如果您不关心从当前会话中删除命令,Michael Mrozek的答案将起作用。如果这样做,则应在执行操作后,在其历史记录文件中写入历史文件history -a

另外,从历史记录文件中删除所需的条目后,可以通过发出history -c,然后重新加载history -r


3

对于那些寻找一线客的人:

while history -d $(history | grep 'SEARCH_STRING_GOES_HERE'| head -n 1 | awk {'print $1'}) ; do :; history -w; done

因此,如果您想例如。删除其中包含密码的多行,只需将“ SEARCH_STRING_GOES_HERE”替换为密码即可。这将在您的整个历史记录中搜索该搜索字符串并将其删除。

2件事要注意

  • grep使用正则表达式,除非您提供-F作为参数
  • 一旦没有更多的匹配,该命令将显示1错误。忽略它。

我收到一个错误(-bash:历史记录:-d:选项需要一个参数),但是它仍然有效吗?
paradroid

1
它会连续运行delete命令,直到失败并出现错误(因为没有其他要删除的内容)。只需忽略该错误即可。
thelogix

这不仅在线,而且是正确的简单答案。没错不要混淆有关history: -d: option requires an argument错误!它处于while循环的结尾=>预期 -它起作用,然后基本上说“我找不到其他东西!” :)
jave.web

2

根据迈克尔克里斯的回答,我提出了以下建议。将其添加到~/.bashrc文件中,然后使用. ~/.bashrc或加载它source ~/.bashrc

:<<COMMENT
    Deletes all lines from the history that match a search string, with a
    prompt. The history file is then reloaded into memory.

    Examples
        hxf "rm -rf"
        hxf ^source

    See:
    - https://unix.stackexchange.com/questions/57924/how-to-delete-commands-in-history-matching-a-given-string
COMMENT
#The unalias prevents odd errors when calling". ~/.bashrc" (May result in
#"not found" errors. That's okay).
unalias hxf
hxf()  {
    read -r -p "About to delete all items from history that match \"$1\". Are you sure? [y/N] " response
    response=${response,,}    # tolower
    if [[ $response =~ ^(yes|y)$ ]]
    then
        #Delete all matched items from the file, and duplicate it to a temp
        #location.
        echo -e "grep -v \"$1\" \"$HISTFILE\" > /tmp/history"
        grep -v "$1" "$HISTFILE" > /tmp/history

        #Clear all items in the current sessions history (in memory). This
        #empties out $HISTFILE.
        echo "history -c"
        history -c

        #Overwrite the actual history file with the temp one.
        echo -e "mv /tmp/history \"$HISTFILE\""
        mv /tmp/history "$HISTFILE"

        #Now reload it.
        echo -e "history -r \"$HISTFILE\""
        history -r "$HISTFILE"     #Alternative: exec bash
    else
        echo "Cancelled."
    fi
}

1
cat "$HISTFILE" | grep -v "commandToDelete" >> "$HISTFILE" && exit

这对我有用。历史-c &&历史-a没有为我正确地重新加载历史文件。因此,我只是在重写历史记录文件后立即退出会话,这样内存中的那个文件就不会覆盖它。

By using our site, you acknowledge that you have read and understand our Cookie Policy and Privacy Policy.
Licensed under cc by-sa 3.0 with attribution required.