mycli
mycli copied to clipboard
Add fzf history search feature
Description
Background
Previously, the history function of mycli only allowed viewing history one line at a time, making it feel like peering through a keyhole. Users had to navigate through the history by typing on the keyboard to see the previous and next entries, making it difficult to find the desired history entry. A request for a feature to enable fzf-like history search was made at https://github.com/dbcli/mycli/issues/726.
Achievements
Implemented the ability to perform fzf search on mycli history. fzf is a software written in Go, and its binary file is also named fzf. (See: junegunn/fzf: :cherry_blossom: A command-line fuzzy finder) The mycli history fzf search feature is designed to switch between the old implementation and the new one based on the presence of the fzf binary. (It might be better to have this feature turned off by default and enabled via an option. Feedback is welcome.)
The history format is <timestamp> <stmt>
. (Placing the timestamp at the end makes formatting difficult and searching by date harder.) Currently, the timestamp is handled as a string and displayed with seconds. Using FormattedText
from prompt_toolkit
to gray out the timestamp could improve visibility, but to keep the scope of this PR focused, this enhancement is not included.
Since fzf provides line-based selection functionality, newlines in the history are replaced with spaces for the suggestion list. However, when setting data to the buffer, the original text is retrieved and set.
Regarding the fzf search score, the tiebreak=index
option is used. This is because I believe that when searching for SQL queries, users often prefer to use the most recent ones. If the default length
option is used, searching for a common term like select
would bring up entries where select
was mistakenly entered by itself, which can be annoying. For more details, see the fzf tiebreak option documentation.
This implementation is an ad-hoc override of some prompt_toolkit
behavior. Therefore, the implementation is gathered under a toolkit
subpackage within the packages
directory.
Alternative Approach
Ideally, we should contribute to prompt_toolkit
and use the history functionality implemented there in mycli. However, prompt_toolkit
is pure Python, and fzf cannot be integrated directly. Rewriting the Go-based program in Python and adapting it to the prompt_toolkit
Completion mechanism would be a significant undertaking.
For this reason, I decided to override some history-related implementations and keybindings in mycli.
Comments
mycli is a great tool, and I have greatly benefited from it. I am pleased to have the opportunity to contribute to this excellent software and hope that mycli will become an even more convenient tool.
Checklist
- [x] I've added this contribution to the
changelog.md
. - [x] I've added my name to the
AUTHORS
file (or it's already there).