J'utilise souvent le find
pour rechercher dans le code source, supprimer des fichiers, etc. De manière ennuyeuse, parce que Subversion stocke des duplicatas de chaque fichier dans sa base de données de fichiers. .svn/text-base/
mes simples recherches aboutissent à de nombreux résultats en double. Par exemple, je veux rechercher de façon récursive uint
dans de multiples messages.h
y messages.cpp
des fichiers :
# find -name 'messages.*' -exec grep -Iw uint {} +
./messages.cpp: Log::verbose << "Discarding out of date message: id " << uint(olderMessage.id)
./messages.cpp: Log::verbose << "Added to send queue: " << *message << ": id " << uint(preparedMessage->id)
./messages.cpp: Log::error << "Received message with invalid SHA-1 hash: id " << uint(incomingMessage.id)
./messages.cpp: Log::verbose << "Received " << *message << ": id " << uint(incomingMessage.id)
./messages.cpp: Log::verbose << "Sent message: id " << uint(preparedMessage->id)
./messages.cpp: Log::verbose << "Discarding unsent message: id " << uint(preparedMessage->id)
./messages.cpp: for (uint i = 0; i < 10 && !_stopThreads; ++i) {
./.svn/text-base/messages.cpp.svn-base: Log::verbose << "Discarding out of date message: id " << uint(olderMessage.id)
./.svn/text-base/messages.cpp.svn-base: Log::verbose << "Added to send queue: " << *message << ": id " << uint(preparedMessage->id)
./.svn/text-base/messages.cpp.svn-base: Log::error << "Received message with invalid SHA-1 hash: id " << uint(incomingMessage.id)
./.svn/text-base/messages.cpp.svn-base: Log::verbose << "Received " << *message << ": id " << uint(incomingMessage.id)
./.svn/text-base/messages.cpp.svn-base: Log::verbose << "Sent message: id " << uint(preparedMessage->id)
./.svn/text-base/messages.cpp.svn-base: Log::verbose << "Discarding unsent message: id " << uint(preparedMessage->id)
./.svn/text-base/messages.cpp.svn-base: for (uint i = 0; i < 10 && !_stopThreads; ++i) {
./virus/messages.cpp:void VsMessageProcessor::_progress(const string &fileName, uint scanCount)
./virus/messages.cpp:ProgressMessage::ProgressMessage(const string &fileName, uint scanCount)
./virus/messages.h: void _progress(const std::string &fileName, uint scanCount);
./virus/messages.h: ProgressMessage(const std::string &fileName, uint scanCount);
./virus/messages.h: uint _scanCount;
./virus/.svn/text-base/messages.cpp.svn-base:void VsMessageProcessor::_progress(const string &fileName, uint scanCount)
./virus/.svn/text-base/messages.cpp.svn-base:ProgressMessage::ProgressMessage(const string &fileName, uint scanCount)
./virus/.svn/text-base/messages.h.svn-base: void _progress(const std::string &fileName, uint scanCount);
./virus/.svn/text-base/messages.h.svn-base: ProgressMessage(const std::string &fileName, uint scanCount);
./virus/.svn/text-base/messages.h.svn-base: uint _scanCount;
Comment puis-je dire find
d'ignorer le .svn
des répertoires ?
Mise à jour : Si vous mettez à jour votre client SVN vers version 1.7 ce n'est plus un problème.
Une caractéristique clé des changements introduits dans Subversion 1.7 est la centralisation du stockage des métadonnées de la copie de travail en un seul endroit. Au lieu d'un
.svn
dans chaque répertoire de la copie de travail, les copies de travail de Subversion 1.7 n'ont qu'un seul répertoire..svn
dans le répertoire Root de la copie de travail. Ce répertoire inclut (entre autres choses) une base de données soutenue par SQLite qui contient toutes les métadonnées dont Subversion a besoin pour cette copie de travail.
4 votes
Pour des raisons de performance, essayez d'utiliser
find ... -print0 | xargs -0 egrep ...
au lieu defind ... -exec grep ...
(ne bifurque pasgrep
pour chaque fichier, mais pour un groupe de fichiers à la fois). En utilisant ce formulaire, vous pouvez également élaguer.svn
sans utiliser l'option-prune
option de recherche, c'est-à-direfind ... -print0 | egrep -v '/\.svn' | xargs -0 egrep ...
3 votes
@Vlad : Pour autant que je sache, l'utilisation de
-exec
con+
ne fourche pasgrep
pour chaque fichier, tout en l'utilisant avec;
fait. Utilisation de-exec
est en fait plus correct que d'utiliserxargs
. Veuillez noter que des commandes commels
font quelque chose même si la liste d'arguments est vide, tandis que des commandes commechmod
donner une erreur si les arguments sont insuffisants. Pour voir ce que je veux dire, essayez simplement la commande suivante dans un répertoire qui ne contient pas de shell script :find /path/to/dir -name '*.sh' -print0 | xargs -0 chmod 755
. Comparez avec celui-ci :find /path/to/dir -name '*.sh' -exec chmod 755 '{}' '+'
.2 votes
@Vlad : D'ailleurs,
grep
-sortir.svn
n'est pas non plus une bonne idée. Alors quefind
est spécialisé dans la gestion des propriétés des fichiers,grep
ne le fait pas. Dans votre exemple, un fichier nommé '.svn.txt' sera également filtré par votreegrep
commandement. Bien que vous puissiez modifier votre regex pour '^/ \.svn $' mais ce n'est toujours pas une bonne pratique de le faire. Le site-prune
prédicat defind
fonctionne parfaitement pour filtrer un fichier (par nom de fichier, ou par date de création, ou toute autre condition que vous avez fournie). C'est comme si vous pouviez tuer un cafard à l'aide d'une grande épée, cela ne veut pas dire que c'est la meilleure façon de le faire :-).3 votes
Le passage à Git a réglé ce problème (parmi beaucoup d'autres). Git ne crée qu'un dossier .git à la racine de la copie de travail, et non dans tous les dossiers de celle-ci comme dans SVN. De plus, le dossier .git ne contient pas de fichiers simples qui pourraient être confondus avec vos fichiers réels portant le même nom.
3 votes
2Dan Moulding : svn 1.7 ne crée qu'un seul répertoire de premier niveau .svn
0 votes
Voir aussi serverfault.com/q/33308/29419