Shell prompt lag in macOS
Longtime user and fan of z.sh. After many attempts to no avail at debugging the following, I'm opening this issue for discussion.
I'm running two machines, a macOS (local) and an Ubuntu (remote,) with the same dotfiles and shell configuration. Both are running the same version of bash (5.1.16(1).) Both shells are interactive login shells. And yet, when z.sh is sourced, the macOS shell prompt experiences a short but highly noticeable lag on each Return press, while the Ubuntu prompt is rendered instantly.
I was wondering if anyone else is experiencing the same issue (or similar) and how to fix — if possible.
Shell environment settings: (also available in my repo)
-
~/.bash_profilewhich sources three different bash files where.shell/utils.shis relevant for our case -
~/.shell/utilswhich exportsPROMPT_COMMANDwithhistory -aand at the end of the file sourcesz.shfrom a specific directory:
export PROMPT_COMMAND="history -a"
# other lines...
# point to and source z in order to track and build dir list
. $HOME/.bin/z.sh
- No other changes to
PROMPT_COMMANDor other shell configurations occur at the shell level after sourcingz.shabove.
As such, the PROMPT_COMMAND reads: history -a (_z --add "$(command pwd -P 2>/dev/null)" 2>/dev/null &);
$HOME/.bin/z.sh reflects the latest version from the master brach.
This has been also tested on a fresh macOS virtual machine with the same results.
Kind bump. Thanks!
have you tried adding ; after history -a ?
as in:
export PROMPT_COMMAND="history -a ; "
# other lines...
# point to and source z in order to track and build dir list
. $HOME/.bin/z.sh
Thanks, @Lockszmith-GH. I've just now -- no noticeable improvement.
$ echo $PROMPT_COMMAND
history -a; (_z --add "$(command pwd -P 2>/dev/null)" 2>/dev/null &);
Z stores it's history in a ~/.z file. How large is it in macOS compared to the Linux one?
One way I use to debug my .bashrc is to run it like this:
bash -xv ~/.bashrc
it will output every line before evaluation (-v) and after (-x) it executes. This might help identify where the stalling is happening.
If it's opaque and in the z source, try running the same command calling z that stalls the same way, and that may help identify the cause.
Thanks for the reply.
macOS:
-rw-r--r-- 2.1K Oct 26 09:45 .z
Ubuntu:
-rw-rw-r-- 1.1K Nov 4 14:13 .z
If it's opaque and in the z source, try running the same command calling z that stalls the same way, and that may help identify the cause.
I'm not sure what you mean here. Here's an excerpt from -xv ~/.shell/utils.sh:
# point to and source z in order to track and build dir list
. $HOME/.bin/z.sh
+ . /Users/apas/.bin/z.sh
.
.
. the entire z.sh script
.
.
++ type compctl
++ type complete
++ complete -o filenames -C '_z --complete "$COMP_LINE"' z
++ '[' '' ']'
++ grep '_z --add'
++ PROMPT_COMMAND='history -a;
(_z --add "$(command pwd -P 2>/dev/null)" 2>/dev/null &);'
OK, so if .bashrc runs properly (no lag), but each prompt rendering is slow - the issue isn't with .bashrc.
I'm assuming that when you have only history -a; in PROMPT_COMMAND - it returns instantaneous, and it's only the _z function call that lags.
What you need to 'look into' is _z, the way to do that is:
- Clear the
PROMPT_COMMAND- so you'll be sure it's the source. - Run each of the command, and see which is the one causing the most delay:
-
history -a -
command pwd -P 2>/dev/null- If this is slow you can use the same exact binary path instead of allowing
commandto dynamically resolve the location of pwd binary everytime:
PWD_PATH="$(type -fP pwd)" - If this is slow you can use the same exact binary path instead of allowing
-
_z --add "$(command pwd -P 2>/dev/null)" 2>/dev/null &);- Try this without the
&in the end - this runs the command in a forked subshell job. See if without & it returns faster. - Try replacing the
command pwd...with$PWD_PATH 2>/dev/nullafter defining the variable as mentioned above. - Remove the
2>/dev/nullfrom the command line and see if there are any errors.
- Try this without the
-
-
_zis still the cause of the slow-down, run the above command withset -xbefore it; andset +xafter it, like this:
This switches on the printout of each command, should also affect the internals of _z. See if you can find the point where it slows down.set -x; _z --add "$(command pwd -P 2>/dev/null)" 2>/dev/null &); set +x;
Hope all of this actually helps.