atuinsh / atuin

✨ Magical shell history
https://atuin.sh
MIT License
20.13k stars 543 forks source link

[Bug]: atuin + starship + zsh + accept-line override is clearing previous command? #2353

Open nk9 opened 1 month ago

nk9 commented 1 month ago

What did you expect to happen?

I have overridden zle's accept-line command to reset the prompt. My goal is to have the time in the current prompt reset on Return to be the time that the command was executed. Then the command finishes, and the new prompt shows the time the previous command ended, until it gets reset upon submitting the next command. Here's what I've added to my .zshrc:

function _reset-prompt-and-accept-line {
  zle reset-prompt
  zle .accept-line   # Note the . meaning the built-in accept-line
}
zle -N accept-line _reset-prompt-and-accept-line

This works correctly when I use Return to enter a new command. It also works if I turn off atuin and just use the up arrow to navigate the command history. Or if I use atuin to find a previous command, recall it with Tab, and then exectue it with Return.

What happened?

When I instead use atuin to recall a previous command and execute it using Return directly from the list, this accept-line override is causing the output of the previous command to be entirely cleared. The prompt does get reset (and the time is updated), then the output of the current command is shown, and then the next prompt is shown. But it's kind of a dealbreaker that the previous command's output disappears.

This doesn't happen if I disable the accept-line override, so that's clearly the problem. Of course, it also works fine if I turn off atuin. Am I missing a zle command here to make this rather unique use case work successfully with atuin?

Atuin doctor output

{
  "atuin": {
    "version": "18.3.0",
    "sync": {
      "cloud": true,
      "records": true,
      "auto_sync": true,
      "last_sync": "2024-08-07 19:20:59.086858 +00:00:00"
    },
    "sqlite_version": "3.46.0"
  },
  "shell": {
    "name": "zsh",
    "default": "zsh",
    "plugins": [
      "atuin"
    ],
    "preexec": "built-in"
  },
  "system": {
    "os": "Darwin",
    "arch": "arm64",
    "version": "14.5",
    "disks": [
      {
        "name": "Macintosh HD",
        "filesystem": "apfs"
      },
      {
        "name": "Macintosh HD",
        "filesystem": "apfs"
      },
      {
        "name": "Purple",
        "filesystem": "hfs"
      },
      {
        "name": "AV 3",
        "filesystem": "hfs"
      }
    ]
  }
}

Code of Conduct

nk9 commented 1 month ago

I had a look at the atuin.zsh file, and it appears that this problem isn't really a problem. By default, the _atuin_search() function already executes zle reset-prompt. It also runs zle accept-line without the leading period. And indeed, when I remove my code entirely, I'm seeing the shell prompt be reset as I was hoping.

I'm a little surprised, since having the time reset like this seems to be a side-effect of atuin and probably not intended behavior. Certainly I can't find anything in the docs about the prompt being reset like this, and what impact that could have. And I'm noticing that actually the prompt is reset perhaps more than is desirable: if you summon atuin with up arrow and then cancel the session by pressing Esc, the prompt will still be reset (and the time updated if you have one in your prompt).

But either way, my problem has been resolved. I'll leave this open for a bit for visibility, but will close it next week if there's no more discussion.