如何使用寻呼机进行长 git add --patch 大块头?

Tom*_*ale 10 git git-diff pager git-add

当我用 交互式添加diff大块头时git add --patch,有时会得到比屏幕长的大块头,但无法less用于翻阅大块头。

这对我来说很奇怪,因为我已经设置了:

[core]
      pager = less -FRX --tabs=4

[pager]

  diff = diff-highlight | less -FRX --tabs=4
Run Code Online (Sandbox Code Playgroud)

interactive.diffFilter=管道通过less也无助于分页。

我需要做什么git add--patch才能使用它less,以便我可以使用键盘来导航超过一个屏幕的任何输出?

vas*_*vas 6

You can't. It's the nature of the Unix pipeline model.

The reason that Git commands that use pagers can work with any generic stdin pager is because of this model. Such git commands write their output to stdout. The pager reads its input from stdin. The stdout of the former is piped to the stdin of the latter. It is precisely the simplicity of this pipeline model that makes pagers generic and allows git to allow you to choose your own pager, as long as it uses this model.

So why can't git add -p (or git add -i) do the same as git diff or git log?

Because there can only be one interactive app at a time.

git diff and git log are not interactive. git add -p and pagers are interactive.

The nature of the pipeline model means that only one application can be in control at a time, and an interactive app needs to be in control. For the pager to gain control of the terminal (so that it can display prompts and respond to your input), git add -p has to release control. Once it does it cannot get it back.

Look at it this way: There would be two command line prompts trying to interact with you: the one for git add -p and the one for the pager. How would they coordinate? It would have to go something like this:

  1. git add -p writes a hunk to stdout, along with an end-of-hunk (EOH) marker instead of the usual end-of-file (EOF) marker.
  2. git add -p then yields control of the terminal to whatever app is at the other end of the pipe.
  3. 寻呼机将接收该块,并通过控制终端显示该块的各个部分及其命令提示符。
  4. 寻呼机的行为与通常相同,但有很大差异。通常它会看到一个 EOF 标记,因此当您说完成(命令quit)时,它就会退出。但 EOH 制造商告诉寻呼机,“不要退出。当用户完成后,将控制权交还给上游应用程序。不要退出。等待。”
  5. 因此,当您使用各种寻呼机命令仔细阅读该块时,您将使用它的quit命令告诉它您已经完成,就像平常一样。
  6. 但现在寻呼机没有退出,而是以某种方式将终端控制权交回给git add.
  7. git add的终端提示符将取代寻呼机的...
  8. ...现在我们回到步骤 1。继续重复直到 EOF。

正如您所看到的,这不仅是一种糟糕的用户体验(使用寻呼机的quit命令返回到git add每个块),它还会完全破坏Unix 管道模型的功能和美观

出于同样的原因,git add -p不能使用diff-so-fancy

拥有类似寻呼机行为的唯一方法git -p是内置一个,或者定义一个“Git Pager API”,然后我们等待人们编写与该 API 一起使用的寻呼机。这就是插件模型,它与管道模型有很大不同。它还意味着紧密集成:git add -p命令和寻呼机命令必须组合起来并在每个命令提示符下可用。

使用终端应用程序的分页

我发现在终端窗口中向上滚动很容易。我的键盘命令允许我逐行或逐页移动。

使用git add -psplit命令

你有没有考虑过用git add -p'ssplit命令来拆散帅哥?无论如何,我发现小个子的帅哥更容易讲道理!


Tom*_*ale 1

根据AtnNn 的回答,我想出了以下别名:

ap = !"VISUAL=\"VISUAL='$VISUAL' bash -c 'set -m; less -K -+F \\\"\\$1\\\"' --\" git add -p \"$@\" #"
Run Code Online (Sandbox Code Playgroud)
  • 按此键e可寻呼该帅哥less
    • 按此q按钮可上演所显示的内容
    • 按下v可编辑显示的内容
    • ^C退出并重复交互式菜单

我正在制作一个 PR 来解决这个问题git