9

我有一个受版本控制的项目,例如/project.hgignore位于/project/.hgignore. 它的语法似乎是正确的,但问题是对于某些用户来说这个文件完全被忽略了,而其他用户仍然会对其进行解析。

说,跑步

su -l dipsy -c 'cd /project; hg status'

显示正确的结果而忽略了正确的文件,而

su -l laalaa -c 'cd /project; hg status'

还输出/project/.hgignore.

我已经检查过的内容:

  • ~/.hgrc两个用户的文件相同,. 的输出也是相同的hg showconfig
  • 两个用户都可以读取/project/.hgignore和写入。

我错过了什么?

(以防万一:Debian Lenny,Mercurial 1.6.3)

//对不起,如果用户名看起来很愚蠢,它们不是真实的(:

-- 添加于 2010 年 11 月 26 日 --

PS。有什么方法可以启动 hg 并在处理.hgignore-s 上获取调试输出?hg --debug status并且hg status --debug不要打印任何明智的东西。

-- 添加 2010-11026 --

调试hg status(结果各不相同):

# su -l dipsy -c 'cd /project; strace hg status 2>&1 >/dev/null | grep hgignore'
open("/project/.hgignore", O_RDONLY|O_LARGEFILE) = 4
fstatat64(4, ".hgignore", {st_mode=S_IFREG|0664, st_size=214, ...}, AT_SYMLINK_NOFOLLOW) = 0
write(1, "M .hgignore\nM foo/bar/baz"..., 4096) = 4096

# su -l laalaa -c 'cd /project; strace hg status 2>&1 >/dev/null | grep hgignore'
write(1, "M .hgignore\nM foo/bar/baz"..., 4096) = 4096

调试hg status --ignore(结果相同):

# su -l dipsy -c 'cd /project; strace hg status --ignore 2>&1 >/dev/null | grep hgignore'
open("/project/.hgignore", O_RDONLY|O_LARGEFILE) = 3
fstatat64(3, ".hgignore", {st_mode=S_IFREG|0664, st_size=214, ...}, AT_SYMLINK_NOFOLLOW) = 0

# su -l laalaa -c 'cd /project; strace hg status --ignore 2>&1 >/dev/null | grep hgignore'
open("/project/.hgignore", O_RDONLY|O_LARGEFILE) = 3
fstatat64(3, ".hgignore", {st_mode=S_IFREG|0664, st_size=214, ...}, AT_SYMLINK_NOFOLLOW) = 0

因此,/project/.hgignore在运行时读取并在运行时hg status --ignore跳过hg status。怎么回事?

4

5 回答 5

6

答案 1 - Dirstate 存储库损坏

昨晚我也遇到了这个问题,这让我很难找到原因。我最终找到了一个关于dirstate repository corruption的 wiki 页面。涉及跑步的第一步hg verify没有奏效。第二步,克隆 repo,确实有效!然后我删除了原始的 .hg 目录并将克隆的 .hg 目录复制到原始位置。

我猜在您的回答中,涉及提交/推送的步骤可能已经修复了您的存储库中的损坏。


答案 2 - inotify 扩展错误

在我最初修复了问题并发布了我的答案后,问题继续弹出,但方式不同:Mercurial 似乎部分服从 .hgignore 文件,但我对其所做的任何更新都没有生效。我碰巧正在创建一个脚本来创建几个相关的存储库,过了一会儿我注意到我的机器内存不足。我跑了一个ps -e,所有这些hg过程都在内存中徘徊。所有这些进程都是 inotify 服务器。

Inotify 是 Mercurial 附带的一个扩展,它订阅工作目录中的任何更改,以提高hg status大型存储库的性能。inotify扩展页面提到“它绝对必须被认为是实验性的”。似乎 inotify 服务器中的一些错误阻止 Mercurial 意识到 .hgignore 文件已更新,因此hg status始终使用过时的 .hgignore 版本。

为了尝试我的理论并暂时让 hg 刷新 .hgignore 我执行了:

killall -s 2 hg

此命令告诉所有驻留的 inotify 服务器退出。(killall类似于kill,但将信号发送给具有给定名称的所有进程。-s 2参数发送允许 inotify 正常关闭的 INT 信号。)

在那之后,事情开始变得非常好,但是 inotify 服务器在执行 hg 后不断弹出。为了阻止这种情况,我将以下代码段放入我的hgrc 文件中:

[extensions]
hgext.inotify = !

这会禁用 inotify 扩展(!指示 Mercurial 禁用扩展)。我的存储库足够小,我现在不需要它。

于 2010-12-10T19:40:05.770 回答
1

两个用户是否运行相同版本的hg? 他们都有权读取 .hgignore 文件吗?

于 2010-11-26T16:02:01.497 回答
1

Mercurial 是使用 python 编写的,因此找出发生的事情应该不会太难。您只需将跟踪放入mercurial/ignore.py(只需使用 warn() 函数,其目的是将警告打印到来自 mercurial 命令的控制台)。如果您在函数warn("I'm here")之前添加 of ,它应该在每次考虑到. 在那之后,由你来要求正确的痕迹来理解行为。如果你知道 python,它应该不会超过几分钟。pat = {}def ignore(root, files, warn).hgignore

于 2010-11-26T22:02:15.013 回答
1

人力资源管理系统。可以肯定的是,什么命令告诉您它们已被某些用户解析而被其他用户忽略?你用 确认hg status --ignored吗?有时人们会忘记 'hg add' 会覆盖忽略的文件状态,因此如果一个用户已经添加(并且可能已提交)这些文件但没有推送到另一个正在查看的 repo 中,那么该人很容易认为他们的 hgignore 不是当真的只是添加的文件使忽略无关紧要时被咨询。

如果是我,我会继续使用strace下一个。类似strace hg status --ignored | grep hgignore并比较两个用户的输出。

于 2010-11-26T20:30:52.777 回答
1

Grea^W 有些成功。

在其中一个子文件夹中隐藏了另一个 hg 存储库,这似乎是所描述问题的最可能原因。我猜另一个.hgignore是在我真正需要的之前阅读的,并且以下所有.hgignore-s 都被删除了。

但是,将该存储库移出并在其位置留下符号链接并没有立即帮助。

然后,我决定采取激进的行动:

  • ~/.hgcookies从(我猜是由 Kiln 身份验证模块创建的)删除了一个 cookie
  • /project/.hgignore完全删除
  • 删除了指向其他存储库的符号链接(如上所述)
  • 添加[ui] ignore = .hgignore~/.hgrc
  • 已提交/已推送的更改
  • 重新创建/project/.hgignore,添加/提交/再次推送
  • 添加了符号链接——现在任何一个用户都忽略它

不确定哪一步确实成功了,但现在一切似乎都按预期工作,/project/.hgignore为每个用户解析。

[ui] ignore = .hgignore不是解决方案,因为我后来删除了它,它没有破坏任何东西。

所以,问题解决了,但WTF仍然没有答案(:

谢谢你们。是的,不要依赖嵌套的存储库。

于 2010-11-29T16:16:41.747 回答