首頁 > shell教程 閱讀:0更新時間:2020-03-28 02:20:15

Shell history:歷史命令

今天我們要介紹的 history 是 linux 中的 history 命令。

“使用 Linux 系統總是要輸入大量的命令吧?”“嗯嗯。”
“這些命令里一定有不少是重復的吧?”“還真是。”
“是不是感覺輸入重復命令很浪費生命?”“唉,說多了都是淚。”
“那想不想減少重復命令的輸入從而節省時間呢?”“必須的??!”

如果真是這樣的話,那么今天你有福啦,本文就是要與大家一起來學習減少重復命令輸入的各種技巧。

列出曾經輸入的命令

要減少輸入,首先要知道曾經輸入過什么命令,對于這個問題,Linux 有很好的解決方案,它就是今天的主角——history。

我們直接輸入 history 命令:

[roc@roclinux ~]$ history
    1  cat .bash_history
    2  echo "" > .bash_history
    3  ls
    4  man ls
    5  date
    6  logout
    7  history


看到了什么?是不是曾經輸入的命令都列了出來。但這里有一個問題,雖然命令都列了出來,但沒有時間戳呀,也不知道命令是什么時候執行的,這怎么能稱得上是“history”呢?不用擔心,我們試試下面的命令。

#我們設置了一個環境變量
[roc@roclinux ~]$ export HISTTIMEFORMAT='%F %T '
 
#再來看history
[roc@roclinux ~]$ history
    1  2016-04-06 12:15:59 cat .bash_history
    2  2016-04-06 12:15:59 echo "" > .bash_history
    3  2016-04-06 12:15:59 ls
    4  2016-04-06 12:15:59 man ls
    5  2016-04-06 12:15:59 date
    6  2016-04-06 12:15:59 logout
    7  2016-04-06 12:16:16 history
    8  2016-04-06 12:18:15 export HISTTIMEFORMAT='%F %T '
    9  2016-04-06 12:18:20 history

看看是不是已經給命令打上了時間的烙印了。

雖然時間戳出現了,但還有兩個問題困擾著我們:

  1. 系統是怎么知道我們在什么時間執行了哪些命令呢?

  2. 有沒有發現,輸出內容中的前 6 條命令的時間戳竟然是完全一樣的,都是“2016-04-0612:15:59”,這又是為什么呢?


我們先來重新登錄一下系統,然后輸入下面的命令,一起來尋找問題的答案:

[roc@roclinux ~]$ cat .bash_history
 
cat .bash_history
echo "" > .bash_history
ls
man ls
date
logout
#1459916176
history
#1459916295
export HISTTIMEFORMAT='%F %T '
#1459916300
history
#1459916459
logout


看到文件中的“#1459916176”這種格式的字符串了嗎?這些就是命令執行的時間戳,通過這些標記,history 就能正確顯示命令的執行時間了。

為什么前 6 條命令的時間戳是一樣的呢?這是因為這些命令執行時沒有開啟“時間戳記錄功能”,在后面需要顯示時間戳時,它們只能取距離它們最近的有時間記錄的那個時間點作為它們的時間戳。這也就是前 6 條命令所顯示的時間戳都是同一個時間點的原因。

重復上一次的執行

平時大家最常遇到的一個場景應該是“想重復執行上一條命令”,對于這種情況,我們首先想到的方法就是按“上方向鍵”,但其實我們有四種方法可以實現這一效果:

  1. 使用向上方向鍵,并回車執行。

  2. 輸入 ??!,并回車執行。

  3. 輸入 !-1,并回車執行。

  4. 輸入 Ctrl+P 組合鍵并回車執行。

嘆號定位法

如果想執行以前執行過的某條命令,該怎么辦呢?這也是一種經常會遇到的情況,下面我們就一起來看看:

[roc@roclinux ~]$ history
    7  ls
    8  vi test.go
    9  ls
   10  history
   11  export HISTTIMEFORMAT='%F %T'
   12  histroy
   13  export HISTTIMEFORMAT='%F %T'
   14  history
   15  export HISTTIMEFORMAT=
   16  man grep
   17  ls
   18  ll
   19  history


看到 man grep了嗎?假設這條命令就是你想執行的命令,你可以先記下它前面的標號 16,然后這樣來執行:

[roc@roclinux ~]$ !16
Ctrl+R 搜索曾經的命令


上面的嘆號定位法雖然好用,但有個缺點,就是不太方便,這個方法需要我們先找出命令的編號,然后才能執行。下面,我們再為大家介紹一種更方便的方法,那就是“搜索定位法”。

搜索定位法,就是通過 Ctrl+R 來實現歷史命令關鍵字的搜索功能,快速查找到要執行的命令并執行。

下面,同學們可以嘗試一下,在你們的 shell 中按一下 Ctrl+R 組合鍵,是不是會出現下面的提示:

(reverse-i-search)`':


然后輸入一些關鍵字,比如“man”:

(reverse-i-search)`man': man grep


系統是不是就找到 man grep 這條歷史命令了,如果這條命令正是你想要執行的,那么就直接回車,命令就會立即執行了。

注意:如果找到的命令和想執行的命令稍微有點不同的話,你可以按一下向左或向右方向鍵來對命令進行微調,等調整成你想要執行的命令后,再按回車執行。

清除所有的命令

安全是計算機世界里的頭等大事,出于安全的考慮,我們常常需要清除曾經輸入的命令,避免被其他別有用心的人看到。這種情況下,我們就要用 -c 選項來幫忙了。

[roc@roclinux ~]$ history -c


-c表示 clear,只要一執行,那么我們的歷史命令列表瞬間就變得一干二凈了,曾經的歷史命令統統不見了,這樣我們就再也不用擔心信息泄露了。

其實,你想刪除歷史記錄可沒那么容易,上面的方法其實只是個障眼法,它只是讓系統暫時不顯示歷史命令。當你再次重新登錄系統后,以前的歷史就又會重新出現。

我們試了一下,確實是這樣子的,這到底是怎么一回事呢?

事情的真相是這樣的:history-c 命令刪除的只是 Linux 系統內存中的歷史命令,當 Shell 退出時,就不會有歷史命令追加到文件 .bash_history 中。但當重新登錄到 Shell 時,Shell 便會加載文件 .bash_history,該文件中存儲著曾經輸入的歷史命令,因此,系統的歷史命令就又出現了。

那么如何真正徹徹底底地刪除所有的歷史命令呢?我們可以采用以下方法。

[roc@roclinux ~]$ history -c
[roc@roclinux ~]$ history -w


history-w 的作用就是用內存中的歷史命令覆蓋 .bash_histroy 文件的內容,這樣,即使 Shell 重新加載也加載不到任何命令了,因為此時 .bash_history 文件中已經空空如也了。

history的配置

工欲善其事,必先利其器,科學地配置 history 命令,可以大大提高我們的工作效率,下面我們就來看看 history 都有哪些配置項。

(1) 設置歷史記錄的時間:

export HISTTIMEFORMAT='%F %T '     # 注意有個空格, 這樣在顯示時日期與命令之間會有空格分隔


(2) 控制歷史命令記錄的總個數:

export HISTSIZE=1000         # 設置內存中的history命令的個數
export HISTFILESIZE=1000     # 設置文件中的history命令的個數


(3) 更換歷史命令的存儲位置:
一般情況下,歷史命令會被存儲在 ~/.bash_history 文件中。如果不想存儲在這個文件中,而想存儲在其他文件中,那么可以通過下面的方式來更改:

export HISTFILE=~/history.log


(4) 還有很多更加個性化的配置供大家選擇:

export HISTCONTROL=erasedups    # 清除整個命令歷史中的重復條目
export HISTCONTROL=ignoredups   # 忽略記錄命令歷史中連續重復的命令
export HISTCONTROL=ignorespace  # 忽略記錄空格開始的命令
export HISTCONTROL=ignoreboth   # 等價于ignoredups和ignorespace

尊重重要命令的隱私

試想一下,我們操作 Linux 系統,如果把所有的命令都記錄到 .bash_history 中,會不會有風險呢?

當然有風險啦,如果哪一天我們不幸中招,黑客攻入了我們的系統,他只要查看一下 history 就能知道我們的很多秘密,比如一些登錄密碼。為了避免該類事情的發生,我們希望 history 不要顯示含有隱私信息的歷史命令,只顯示不含有隱私信息的命令。這個需求太個性化,但 history 仍然能夠實現,下面我們就為大家介紹兩種行之有效的解決方案。

第一種靠譜的解決方案:

  • 第1步:設置 HISTCONTROL 環境變量:export HISTCONTROL=ignorespace。

  • 第2步:輸入重要命令時,記得在輸入命令前加上空格。

  • 第3步:執行 history,可以看到剛輸入的重要命令沒有出現在 history 中。


通過設置 HISTCONTROL=ignorespace,可以讓 history 不記錄你的特殊輸入(命令前加空格),這樣可以在一定程度上有效地保護我們的系統。

第二種靠譜的解決方案:

  • 第1步:設置 HISTIGNORE 環境變量 export HISTIGNORE=*。

  • 第2步:輸入重要命令,比如 mysql-uroot-p123。

  • 第3步:查看你的 history,可以看到剛輸入的 mysql 命令沒有記錄在 history 中。

  • 第4步:恢復命令的記錄 export HISTIGNORE=。

  • 第4步后,系統又恢復正常,輸入的命令又能被正常記錄了。


這個方法雖然略顯煩瑣,需要你每次在輸入重要命令時都要先設置 HISTIGNORE=*,執行完命令后再設置 HISTIGNORE=,但是,這種方法能規避由于你的粗心大意(忘記命令前加空格)帶來的巨大安全隱患,確保機密信息不會被泄露出去。

beylze編程學院,一個分享編程知識和seo優化知識的網站。跟著beylze一起學習,每天都有進步。

通俗易懂,深入淺出,一篇文章只講一個知識點。

文章不深奧,不需要鉆研,在公交、在地鐵、在廁所都可以閱讀,隨時隨地漲姿勢。

文章不涉及代碼,不燒腦細胞,人人都可以學習。

當你決定關注beylze(公眾號:beylze),你已然超越了90%的其他從業者!

相關文章

優秀教程

国产亚洲欧美日韩