Bash history search, partial + up-arrow

121,813

Solution 1

Create ~/.inputrc and add these lines:

# Respect default shortcuts.
$include /etc/inputrc

## arrow up
"\e[A":history-search-backward
## arrow down
"\e[B":history-search-forward

TIP: Read at the bottom for an explanation of $include /etc/inputrc or what to do if you already have the file ~/.inputrc.

Lines starting with # are comments.

I can't remember what is backward and what forward. Experiment with it. Maybe you have to switch backward and forward.

Close and re-open all terminals for the new behaviour to become effective.


A bit background information:

Bash is using readline to handle the prompt. ~/.inputrc is the configuration file for readline. Note that this will also take effect in other software using the readline library, for example IPython.

Read the bash manual for more information about readline. There you can also find more history related readline commands.

To get the escape codes for the arrow keys you can do the following:

  1. Start cat in a terminal (just cat, no further arguments).
  2. Type keys on keyboard, you will get things like ^[[A for up arrow and ^[[B for down arrow.
  3. Replace ^[ with \e.

For more information about ^[ and \e see here: https://unix.stackexchange.com/a/89817/380515


About the line $include /etc/inputrc:

Readline tries to read ~/.inputrc for configuration. If that file does not exists it will try to read /etc/inputrc. That means if ~/.inputrc exists it will not read /etc/inputrc.

Some distros have prepared some config in /etc/inputrc. If you then create ~/.inputrc you will lose the prepared config. This may or may not be what you want. To still keep the prepared config in /etc/inputrc you can use the line $include /etc/inputrc in your ~/.inputrc.

If you already have the file ~/.inputrc that means you either already know what you are doing. Or you inherited if from the person who set up your system. Or you previously followed a different guide which told you to create the file and forgot about it. Either way you might want to check /etc/inputrc and decide if you want to keep it with the line $include /etc/inputrc.

Solution 2

Create a file named setup_readline.sh with mode 644 in /etc/profile.d/ with following content, login and check you preferred keys:

bind '"\e[A": history-search-backward'
bind '"\e[B": history-search-forward'

I think is the best way to do this. Mostly if you using configuration management systems such as chef, puppet, etc

And system config still untouched!

Solution 3

Ctrl + R will give you this sort of functionality. Start typing a partial command and it will come up with old ones which you can navigate with the up and down arrows.

More info here.

Solution 4

To complete lesmana's answer regarding ~/.inputrc that I should create under my Trusty 14.04, verify/add in ~/.bashrc (the first line already exists in my ~/.bashrc):

shopt -s histappend  
PROMPT_COMMAND='history -a'  

It's already explained in French here.

Solution 5

The following solution combines & extends some of the above mentioned approaches: add the following lines to your ~/.bash_aliases file (no need for ~/.inputrc) in order to achieve the following behavior:

  1. move up/down in history (only entries with same prefix) by pressing CTRL+UP and CTRL+DOWN. This can co-exist to the standard functionality of moving up/down in the full history via UP and DOWN alone
  2. jump to next/previous word in a commandline by pressing CTRL+RIGHT and CTRL+LEFT
bind '"\e[1;5A":history-search-backward'
bind '"\e[1;5B":history-search-forward'
bind '"\e[1;5C":forward-word'
bind '"\e[1;5D":backward-word'

Re-login to the shell (or run source ./bash_aliases) in order to apply the changes.

Share:
121,813

Related videos on Youtube

kesari
Author by

kesari

Programming Perl since 1998. I love the problem solving and creativity involved in writing good perl code. I enjoy StackOverflow.com for the challenges I am presented with.

Updated on September 18, 2022

Comments

  • kesari
    kesari over 1 year

    I have searched, but not found anything on this. I am looking for a functionality in bash, using a terminal.

    Way back when, I had a user on a debian system, and a friend set me up with a convenient history search feature (I believe I used tcsh then), where I would type the beginning of a previous command, hit up-arrow, and it would do a search, based on the partial string.

    E.g. if my history is:

    ./script.pl
    ./script.pl arg1
    cat output
    cat output | grep yada
    

    And I type ., and press up-arrow, it would show me: ./script.pl arg1. Press it again and it would show ./script.pl, etc.

    Very much like it would perform a grep on .bash_history. Is there a way to get this functionality?

  • kesari
    kesari over 12 years
    Thanks for your reply. Yes, I have tried that, but I find it a bit... finicky. It will not allow me to scroll through commands beginning with the partial, it only shows the first. It also searches the entire command for the character, which is sort of useless.
  • VishApp
    VishApp over 9 years
    @TLP, repeat hitting Ctrl+r
  • Joe
    Joe almost 9 years
    Oddly the ~/inputrc didn't work for me - but putting these commands into .bash_profile did.
  • Eyal
    Eyal about 8 years
    Great, but this solution disables the ctrl-left/ctrl-right shortcuts.
  • Shital Shah
    Shital Shah almost 8 years
    This command basically instructs bash to immediately append command to history file instead of waiting for session to end. Its useful if you have lot of terminals open and don't want to loose history in one but otherwise not necessary. digitalocean.com/community/tutorials/…
  • Shital Shah
    Shital Shah almost 8 years
    .inputrc doesn't exist in my home folder and I prefer to have these kind of settings in .bashrc anyway so I can just carry around one file for my settings. So this is probably a better answer then accepted one.
  • Orwellophile
    Orwellophile over 7 years
    .inputrc works fabulously for me, but not after I load screen. The odd thing is, other .inputrc shortcuts work, but not these. So I use both solutions now.
  • Hitesh Kumar
    Hitesh Kumar about 7 years
    Can anyone tell me how can I achieve the same for make
  • Mike D
    Mike D over 6 years
    @lesmana, i would give extra points for the cat part alone
  • danmactough
    danmactough over 6 years
    This is super-helpful when, for example, you log into a server to do things and are missing the heck out of these and don't want to edit and reload the ~/.inputrc on the server.
  • kbrose
    kbrose over 5 years
    Seconding @Eyal, anyone have advice on how I can have this but preserve ctrl-left/ctrl-right shortcuts?
  • kbrose
    kbrose over 5 years
    Figured it out, somehow readline must have been inferring some default if .inputrc did not exist, but got rid of those defaults when the file was detected. In addition to the shortcuts from the answer, add lines to preserve the ctrl-left/ctrl-right shortcuts: e.g. "\e[1;5C":forward-word and "\e[1;5D":backward-word
  • Tulio Casagrande Alberto
    Tulio Casagrande Alberto over 5 years
    To preserve all defaults add $include /etc/inputrc, preferably on the first line.
  • αғsнιη
    αғsнιη over 4 years
  • Ekanshdeep Gupta
    Ekanshdeep Gupta almost 4 years
    Hi, do you know where I can find out about how to create more complicated keyboard shortcuts? Perhaps what this notation is called etc?
  • user27164
    user27164 almost 4 years
    Related terms are "keycode" or "scancode" (I am no expert). However, pragmatic solution: Running showkey -a gives you helpful output, e.g., "^[[1;5A" which means "\e[1;5A", that is, the leading "^[" seems to refer to "\e".
  • dashesy
    dashesy almost 4 years
    Is there any reason why after certain commands in bash, this behavior is broken? I will need another bash for it to work again.
  • Soren
    Soren almost 4 years
    This is just writing ~ symbols in my shell.
  • Yohai Devir
    Yohai Devir over 2 years
    In addition to the above answer, you can find all key codes here: en.wikipedia.org/wiki/ANSI_escape_code
  • Tinashe Chinyanga
    Tinashe Chinyanga over 2 years
    I removed the comments for the lines "\e[5~": history-search-backward "\e[6~": history-search-forward in my existing /etc/inputrc file
  • Admin
    Admin over 2 years
    Good idea but you also have to change "\e[5~" to "\e[A" and "\e[6~" to "\e[B" or it won't work.
  • xeruf
    xeruf about 2 years
    the second point seems to be the default anyways, and this does not work for me - had to remove the 1;5
  • Admin
    Admin almost 2 years
    ctrl+R doesn't do the up/down arrow by default. You can only repeat ctrl+R to "search up". There is no "search down".
  • Admin
    Admin almost 2 years
    @wisbucky there's "search down"; unfortunately, by default, it's not available. stty -ixon "enables" it.