2020-06-13 17:24:36 +00:00
#!/usr/bin/env python3
# This is a very fragile test. Sorry about that. But interactively entering
# commands and verifying they are recorded correctly in the interactive
# history and that history can be manipulated is inherently difficult.
#
# This is meant to verify just a few of the most basic behaviors of the
# interactive history to hopefully keep regressions from happening. It is not
# meant to be a comprehensive test of the history subsystem. Those types of
# tests belong in the src/fish_tests.cpp module.
#
# The history function might pipe output through the user's pager. We don't
# want something like `less` to complicate matters so force the use of `cat`.
from pexpect_helper import SpawnedProc
import os
os . environ [ " PAGER " ] = " cat "
sp = SpawnedProc ( env = os . environ . copy ( ) )
send , sendline , sleep , expect_prompt , expect_re , expect_str = (
sp . send ,
sp . sendline ,
sp . sleep ,
sp . expect_prompt ,
sp . expect_re ,
sp . expect_str ,
)
expect_prompt ( )
# ==========
# Start by ensuring we're not affected by earlier tests. Clear the history.
sendline ( " builtin history clear " )
expect_prompt ( )
# ==========
# The following tests verify the behavior of the history builtin.
# ==========
# ==========
# List our history which should be empty after just clearing it.
sendline ( " echo start1; builtin history; echo end1 " )
expect_prompt ( " start1 \r \n end1 \r \n " )
# Our history should now contain the previous command and nothing else.
sendline ( " echo start2; builtin history; echo end2 " )
expect_prompt ( " start2 \r \n echo start1; builtin history; echo end1 \r \n end2 \r \n " )
# ==========
# The following tests verify the behavior of the history function.
# ==========
# ==========
# Verify explicit searching for the first two commands in the previous tests
# returns the expected results.
sendline ( " history search --reverse ' echo start ' | cat " )
expect_prompt ( " echo start1;.* \r \n echo start2; " )
# ==========
# Verify searching is the implicit action.
sendline ( " history -p ' echo start ' " )
expect_prompt ( " echo start2.* \r \n echo start1 " )
# ==========
# Verify searching with a request for timestamps includes the timestamps.
sendline ( " history search --show-time= ' # %F % T % n ' --prefix ' echo start ' " )
2020-06-24 18:43:56 +00:00
expect_prompt (
2024-04-02 20:40:45 +00:00
" # \\ d \\ d \\ d \\ d- \\ d \\ d- \\ d \\ d \\ d \\ d: \\ d \\ d: \\ d \\ d \r \n echo start2; .* \r \n # \\ d \\ d \\ d \\ d- \\ d \\ d- \\ d \\ d \\ d \\ d: \\ d \\ d: \\ d \\ d \r \n echo start1; "
2020-06-24 18:43:56 +00:00
)
2020-06-13 17:24:36 +00:00
# ==========
# Verify explicit searching for an exact command returns just that command.
# returns the expected results.
sendline ( " echo hello " )
expect_prompt ( )
sendline ( " echo goodbye " )
expect_prompt ( )
sendline ( " echo hello again " )
expect_prompt ( )
sendline ( " echo hello AGAIN " )
expect_prompt ( )
sendline ( " history search --exact ' echo goodbye ' | cat " )
expect_prompt ( " echo goodbye \r \n " )
sendline ( " history search --exact ' echo hello ' | cat " )
expect_prompt ( " echo hello \r \n " )
# This is slightly subtle in that it shouldn't actually match anything between
# the command we sent and the next prompt.
sendline ( " history search --exact ' echo hell ' | cat " )
expect_prompt ( " history search --exact ' echo hell ' | cat \r \n " )
# Verify that glob searching works.
sendline ( " history search --prefix ' echo start*echo end ' | cat " )
expect_prompt ( " echo start1; builtin history; echo end1 \r \n " )
# ==========
# Delete a single command we recently ran.
sendline ( " history delete -e -C ' echo hello ' " )
2021-08-20 17:36:11 +00:00
expect_prompt ( " history delete -e -C ' echo hello ' \r \n " )
2020-06-13 17:24:36 +00:00
sendline ( " echo count hello (history search -e -C ' echo hello ' | wc -l | string trim) " )
2021-08-20 17:36:11 +00:00
expect_prompt ( " count hello 0 \r \n " )
2020-06-13 17:24:36 +00:00
# ==========
# Interactively delete one of multiple matched commands. This verifies that we
# delete the first entry matched by the prefix search (the most recent command
# sent above that matches).
sendline ( " history delete -p ' echo hello ' " )
expect_re ( " history delete -p ' echo hello ' \r \n " )
expect_re ( " \ [1 \ ] echo hello AGAIN \r \n " )
expect_re ( " \ [2 \ ] echo hello again \r \n \r \n " )
2020-06-24 18:43:56 +00:00
expect_re (
2024-01-07 14:13:34 +00:00
" Enter nothing to cancel the delete, or \r \n Enter one or more of the entry IDs or ranges like ' 5..12 ' , separated by a space. \r \n For example ' 7 10..15 35 788..812 ' . \r \n Enter ' all ' to delete all the matching entries. \r \n "
2020-06-24 18:43:56 +00:00
)
2023-06-10 13:23:29 +00:00
expect_re ( " Delete which entries \ ? " )
2020-06-13 17:24:36 +00:00
sendline ( " 1 " )
2021-08-20 17:36:11 +00:00
expect_prompt ( ' Deleting history entry 1: " echo hello AGAIN " \r \n ' )
2020-06-13 17:24:36 +00:00
# Verify that the deleted history entry is gone and the other one that matched
# the prefix search above is still there.
2020-06-24 18:43:56 +00:00
sendline (
" echo count AGAIN (history search -e -C ' echo hello AGAIN ' | wc -l | string trim) "
)
2021-08-20 17:36:11 +00:00
expect_prompt ( " count AGAIN 0 \r \n " )
2020-06-13 17:24:36 +00:00
2020-06-24 18:43:56 +00:00
sendline (
" echo count again (history search -e -C ' echo hello again ' | wc -l | string trim) "
)
2021-08-20 17:36:11 +00:00
expect_prompt ( " count again 1 \r \n " )
2020-06-13 17:24:36 +00:00
# Verify that the $history var has the expected content.
sendline ( " echo history2=$history \ [2 \ ] " )
2021-08-20 17:36:11 +00:00
expect_prompt ( " history2=echo count AGAIN .* \r \n " )
2020-09-22 14:11:39 +00:00
# Verify that history search is case-insensitive by default
sendline ( " echo term " )
2021-08-20 17:36:11 +00:00
expect_prompt ( " term " )
2020-09-22 14:11:39 +00:00
sendline ( " echo TERM " )
2021-08-20 17:36:11 +00:00
expect_prompt ( " TERM " )
2020-09-22 14:11:39 +00:00
sendline ( " echo banana " )
2021-08-20 17:36:11 +00:00
expect_prompt ( " banana " )
2020-09-22 14:11:39 +00:00
send ( " ter \x1b [A " ) # up-arrow
expect_re ( " echo TERM " )
2021-08-20 17:36:11 +00:00
sendline ( " " )
expect_prompt ( " TERM " )
# Check that leading space makes an ephemeral item
sendline ( " echo ephemeral " )
expect_prompt ( " ephemeral " )
2022-06-16 16:43:28 +00:00
send ( " \x1b [A " ) # up-arrow
2021-08-20 17:36:11 +00:00
expect_re ( " echo ephemeral " )
sendline ( " " )
expect_prompt ( " ephemeral " )
sendline ( " " )
expect_prompt ( )
send ( " \x1b [A " )
2022-06-16 16:43:28 +00:00
expect_re ( " echo TERM " ) # not ephemeral!
2021-10-18 02:27:46 +00:00
# Verify that clear-session works as expected
# Note: This test depends on that history merge resets the session from history clear-sessions point of view.
sendline ( " builtin history clear " )
expect_prompt ( )
# create before history
sendline ( " echo before1 " )
expect_prompt ( )
sendline ( " echo before2 " )
expect_prompt ( )
# "reset" session with history merge
sendline ( " history merge " )
expect_prompt ( )
# create after history
sendline ( " echo after " )
expect_prompt ( )
2022-06-16 16:43:28 +00:00
# clear session
2021-10-18 02:27:46 +00:00
sendline ( " history clear-session " )
expect_prompt ( )
sendline ( " history search --exact ' echo after ' | cat " )
expect_prompt ( " \r \n " )
2024-03-09 11:04:16 +00:00
# Check history filtering
# We store anything that starts with "echo ephemeral".
sendline ( " function fish_should_add_to_history; string match -q ' echo ephemeral* ' -- $argv; and return 2; return 0; end " )
expect_prompt ( " " )
# Check that matching the line works
# (fish_should_add_to_history is itself stored in history so we match "ephemeral!" to avoid it)
sendline ( " echo ephemeral! line " )
expect_prompt ( " ephemeral! line " )
sendline ( " echo nonephemeral! line " )
expect_prompt ( " nonephemeral! line " )
sendline ( " true " )
expect_prompt ( )
sendline ( " echo a; history search ' *ephemeral!* ' | cat; echo b " )
2024-05-18 17:54:13 +00:00
expect_prompt ( r " a \ r \ n.*echo nonephemeral! line \ r \ nb \ r \ n " )
2024-03-09 11:04:16 +00:00
# If fish_should_add_to_history exists, it will completely take over,
# so even lines with spaces are stored
sendline ( " echo spaced " )
expect_prompt ( " spaced " )
sendline ( " true " )
expect_prompt ( )
sendline ( " echo a; history search ' *spaced* ' | cat; echo b " )
2024-05-18 17:54:13 +00:00
expect_prompt ( " a \r \n .* echo spaced \r \n b \r \n " )