用于diff sqlite表的Git钩子

Nic*_*son 3 git sqlite githooks

我在Git存储库中有一个Sqlite数据库.今天我想在两个不同的提交中做一个视图的差异.我是这样做的:

$ sqlite3 -list file.sqlite "SELECT * FROM contact_list_detailed" >/tmp/newlist
$ git checkout 51c24d13c file.sqlite
$ sqlite3 -list file.sqlite "SELECT * FROM contact_list_detailed" >/tmp/oldlist
$ git checkout -- file.sqlite
$ diff /tmp/oldlist /tmp/newlist
Run Code Online (Sandbox Code Playgroud)

它工作,如果我想,我可以编写脚本.但是有没有任何"好"的方法来做钩子这样做?

Bri*_*ton 15

以下是如何使用git的textconv功能来显示sqlite文件版本之间的差异.它只是进行转储,因此对于大型数据库来说可能不是非常有效.没有必要的钩子.

该链接似乎不再可用,因此我使用的是存档版本.

它的要点是,在git属性文件(.gitattributes,或.git/info/attributes)中,添加模式匹配以强制sqlite3差异(假设您的数据库文件具有扩展名.sqlite3):

*.sqlite3 diff=sqlite3
Run Code Online (Sandbox Code Playgroud)

然后在你的git配置文件(~/.gitconfig.git/config)中:

[diff "sqlite3"]
    binary = true
    textconv = "echo .dump | sqlite3"
Run Code Online (Sandbox Code Playgroud)

如果您只想跟踪架构更改,请使用.schema而不是.dump.

  • 我必须使用这个 `textconv = "f(){ sqlite3 -batch \"$1\" .dump; }; f"`。 (3认同)

ste*_*nct 6

万一真的想跟踪 git 中的二进制数据库文件,就会出现一些问题。由于 sqlite 数据库可能会有所不同,而存储在其中的数据没有更改,因此 的输出git status对于确定是否应该提交并没有真正的帮助,并且git diff只显示类似Binary files a/foo.sql and b/foo.sql differ. 为了获得正确的输出,git diff基本上有两种方法来比较各个文件:

  1. 用于将文件转换为纯文本,如Biran Mintontextconv的答案所示。
  2. 设置能够直接创建差异的自定义差异应用程序。

sqldiff我将概述下面使用sqlite 附带的第二种方法。与该textconv方法一样,需要更改属性和配置文件。

属性:

*.sql* diff=sqldiff
Run Code Online (Sandbox Code Playgroud)

配置:

[diff "sqldiff"]
    command = gitsqldiff
Run Code Online (Sandbox Code Playgroud)

上面的字符串gitsqldiff指的是一个包装脚本,需要它来排列 git 给出的参数以供sqldiff. 它必须是可执行的并且可以通过PATH环境变量访问(将其放入~/bin应该没问题)。因为(截至目前) 的退出值sqldiff始终为 0,因此毫无用处,我们必须检查它打印的内容以向用户提供反馈 - 特别是在数据库中没有任何更改的情况下,根据sqldiff它根本不会产生任何输出。为此并向用户显示完整的输出,我们使用一种技巧将输出重定向到附加文件描述符并stdout通过tee.

gitsqldiff:

*.sql* diff=sqldiff
Run Code Online (Sandbox Code Playgroud)

这当然不会使 sql 文件成为 git 存储库中的一等公民,但可能会促进仍然有效的工作流程。


CL.*_*CL. 5

您将使用HEADHEAD^来访问之前和当前的修订版;有关示例,请参阅git post-commit hook - 已提交文件上的脚本。

用于git show将文件提取到临时目录而不覆盖工作副本。


除非绝对必要,否则我不会存储二进制文件gitsqlite3 file.sqlite .dump如果您使用 SQL 命令创建一个文本文件并将放入 git 中,并且仅将二进制数据库作为生成的文件,则可以避免许多麻烦。(但是你必须关心在必要时重新生成 SQL 文件。)

  • 是的(但我猜你想要“结帐后”)。 (2认同)