2015-10-19 53 views
3

我在我的一些项目文件的顶部有一个小标题,我希望每次更改它们时都要更新当前年份。我在Git中与我的清洁过滤器的一个问题抛出一个错误:在git上更新文件添加干净的过滤器和sed

首先,我有一个文件在我的主分支称为testClass.cs

// ********************* 
// File active 2011-2014 
// ********************* 

我然后做一个小改动,文件:

// ********************* 
// File active 2011-2014 
// ********************* 

// First commit, wahoo! 

然后我运行git add testClass.cs来进行下一次提交的更改。这会运行我的git clean过滤器,它使用sed来尝试编辑位置文件以将标题中的年份更新到2015年(即2011-2014应更改为2011-2015)。下面是配置,与过滤器设置:

[core] 
    repositoryformatversion = 0 
    filemode = false 
    bare = false 
    logallrefupdates = true 
    symlinks = false 
    ignorecase = true 
    hideDotFiles = dotGitOnly 

[filter "updatedate"] 
    clean = sed -i "s/2011-[[:digit:]]\\{4\\}/2011-$(date '+%Y')/" %f 

,我遇到的问题是,在添加/更新失败因“设备或资源忙”的错误。看似与sed创建的临时文件有关。如果我在命令行上测试它,sed命令可以正常工作,但在用作过滤器时会失败。

$ git add testClass.cs 
sed: cannot rename ./sed0jmaI2: Device or resource busy 
error: external filter sed -i s/2011-[[:digit:]]\{4\}/2011-$(date '+%Y')/ %f failed 4 
error: external filter sed -i s/2011-[[:digit:]]\{4\}/2011-$(date '+%Y')/ %f failed 

我使用git bash版本2.5.3(MINGW64)。

+0

你确定sed看到的文件名存在于它应该在哪里吗?过滤器似乎期望标准输入上的文件内容,并且预计会写入标准输出。也许尝试删除'-i'和'%f'? (你也许想确保你不会修改远离文件的任何东西) –

+0

@EtanReisner,放掉'-i'标志似乎更像我想要的(反正错误消失了) 。我现在看到的问题是,日期更新作为git历史的一部分(我可以看到它添加到diff),但文件本身并未修改。 – njenson

+0

这不是过滤器所做的。他们显式更改工作树和存储库之间的数据。故意。这就是他们的目的。 –

回答

2

你在这里有一些奇怪的事情,其中​​之一是你没有像流一样使用sedclean需要标准输入运行它,并将该文件修改为标准输出。它更像是cat foo.txt | sed 's/foo/bar/'。所以不需要-i它会破坏事情。除此之外,我认为git并不喜欢正则表达式,在这种情况下,通过更具体的方法可以做得更好。

[filter "updatedate"] 
    clean = sed "s/2011-20[01][0-9]/2011-$(date '+%Y')/" 

请注意,这不会改变你的本地副本,你将不得不拉来看到拉目录的变化,从而smudge命令。