私の環境では何かのアップデートをきっかけとしてWindows Drawが動かなくなることがあって、動かないと困るのでWindowsの「システムの復元」で動くところまでロールバックすることがある。 でも、この機能、消す必要のないファイルを消してくれることが多く、自分で作ったユーティリティとかも消えてリビルドするハメになったりする。 最近、Subversionの作業ディレクトリの内容が壊れて、svn upもsvn cleanupもできなくなることに気づいた。
よく現象を見てみると、
.svn/tmpディレクトリがなくなっている。
.svnディレクトリの隠し属性が消えている。
という感じになっている。
特に、最初の.svn/tmpディレクトリがなくなっている、というのが痛くて、svn cleanupをやってもにっちもさっちも行かなくなる。
全部の作業コピーがこうなるのではなく、復元開始時点から指定した復元ポイントまでの間に作業コピーで何かファイルを更新しているとこうなるらしい。
いずれにせよ、全部の作業ディレクトリを調べて回る羽目になるのは変わりない。
勘弁してくれ・・・。
復旧方法は各作業ディレクトリおよびそのサブディレクトリの.svnディレクトリを調べて、tmpがなければディレクトリを作る。
全部のディレクトリを調べ終わったらsvn upすれば(ほぼ)元通りになる。
失われた変更は戻ってきませんが。;-p
で、作業ディレクトリに10個ディレクトリがあって、そのそれぞれに10個のサブディレクトリがある、なんてことはよくある話で、手作業でやっていたら日が暮れてしまう。
そこでシェルスクリプトをちゃらっと作ってみた。
ご利用は各自の責任でお願いします。
#!/bin/bash
# THIS SOFTWARE IS PROVIDED BY THE AUTHOER "AS IS", WITHOUT ANY WARRANTY.
# use it at your own risk.
function check-svn-dir () {
attrib $1 | grep -v '^ *H ' > /dev/null
if [ "$?" == 0 ]; then
echo $1 is not hidden. Make it hidden.
attrib +H $1
fi
if [ ! -d "$1/tmp" ]; then
echo "$1/tmp doesn't exist. Create it."
mkdir $1/tmp
fi
}
export -f check-svn-dir
/usr/bin/find . -name '.svn' -type d -exec bash -c "check-svn-dir {}" ";"
unset -f check-svn-dir
シェル関数check-svn-dirでは引数で指定されたディレクトリに隠し属性が付いているかチェックして、付いてなければ隠し属性を設定する。
また、サブディレクトリtmpがなければ作る。
attribはMS-DOS時代からあるWindowsのコマンドで、行頭から適当に属性がアルファベット1文字で並び、その後にファイル名がフルパスで表示される。 余談だが、attrib /S /Dとやると、サブディレクトリの内容まで隠しファイルも全部表示されるので、DOS時代には隠しファイル探しによく使ったものだ。 隠し属性は「H」(Hidden)なので、Hが含まれているかどうかをgrepでチェックしている。 超適当にチェックしているので、隠し属性以外の属性が付いていたりするとうまく動かない。 まあ、隠し属性にならないだけで、大きな害はない、だろう。
このシェル関数に対して、findコマンド(Windowsにも同名のコマンドがあるが、ここではCygwinの方のfindコマンド。当たり前だけど)で.svnディレクトリを探し回り、次々に引数として渡していく。
実行はfindから呼び出されたサブシェルにやらせるので、サブシェルでこの関数が見えるように、export -fでシェル関数をエクスポートしておく。
最後にcheck-svn-dirシェル関数をunsetしておしまい。
このシェルスクリプトを実行したら、svn upを実行すれば、作業ディレクトリは元通り使えるようになる。 ただし、変更してあったファイルがロールバックで消された場合はそのファイルはもう戻ってこない。
Copyright (C) 2011 You SUZUKI
$Id: subversion.htm,v 1.3 2011/09/24 11:30:07 you Exp $