Utiliser la commande chmod de manière sélective

11

Je souhaite définir l'autorisation 755 sur tous les fichiers et sous-répertoires d'un répertoire spécifique, mais je souhaite exécuter chmod 755 uniquement pour les composants qui ne disposent pas de l'autorisation 755.

find /main_directory/ -exec chmod 755 {} \;

Si la findcommande renvoie une longue liste, cela prendra beaucoup de temps. Je sais que je peux utiliser la commande stat pour vérifier l'autorisation de niveau de fichier octal de chaque composant, puis utiliser if-else pour basculer l'autorisation de fichier, mais existe-t-il une approche sur une seule ligne utilisant findet xargspour vérifier d'abord quelle autorisation le fichier / répertoire a , puis utilisez-le chmodpour le remplacer par 755 s'il est défini sur autre chose.

Kumarjit Ghosh
la source
6
Cela peut être une optimisation prématurée, et cela peut même ne pas être plus rapide. Faire toutes ces vérifications peut le ralentir. Tester pour s'assurer qu'il est plus rapide ne sera rentable que si vous devez faire beaucoup de choses.
ctrl-alt-delor
3
Vous ne voulez probablement pas accorder d'autorisations d'exécution à tous les fichiers. Cela créera un risque pour la sécurité. (c'est l'un des vecteurs de virus sur Windows de Microsoft: tout est exécutable). En mode symbolique, vous pouvez dire u+rw,go+r,go-w,ugo+X- notez la capitale.
ctrl-alt-delor
Je suis d'accord avec @ ctrl-alt-delor mais suggérerais quelque chose de plus proche de ce que vous avez demandé, u = rwX, go = rX qui devrait réaliser la même chose.
penguin359

Réponses:

21

Si vous souhaitez modifier les autorisations 755sur les fichiers et les répertoires, il n'y a aucun avantage réel à utiliser find(du moins du point de vue des performances), et vous pouvez simplement le faire

chmod -R 755 /main_directory

Si vous voulez vraiment utiliser findpour éviter de modifier les autorisations sur des choses qui ont déjà des 755autorisations (pour éviter de mettre à jour leur horodatage ctime), vous devez également tester les autorisations actuelles sur chaque répertoire et fichier:

find /main_directory ! -perm 0755 -exec chmod 755 {} +

Le -exec ... {} +recueille autant de chemins que possible qui réussit le ! -perm 0755test et les exécute chmodtous en même temps.

Habituellement, on voudrait changer les autorisations sur les fichiers et les répertoires séparément, afin que tous les fichiers ne soient pas exécutables:

find /main_directory   -type d ! -perm 0755 -exec chmod 755 {} +
find /main_directory ! -type d ! -perm 0644 -exec chmod 644 {} +
Kusalananda
la source
A travaillé comme un charme, merci. Cordialement, Kumarjit
Kumarjit Ghosh
1
Je soupçonne que l'utilisation +au lieu de ;fait une grande différence ici.
Kevin
C'est le moyen rapide - évitez un contrôle. J'utiliserais en outre find pour faire une liste des seuls fichiers que vous êtes autorisé à modifier, cela évitera l'erreur de chmod sur les fichiers qu'il ne peut pas modifier. <pre> <code> # rwx, rw, wx, w ne trouve que. -user $ (whoami) -perm / 002! -perm 0755 -exec chmod 0755 {} \; # se divise en deux opérations. -user $ (whoami) -perm / 002! -perm 0755> /tmp/chfiles.txt pour le fichier dans $ (</ tmp / chfiles.txt) faire chmod --quiet 0755 "$ {file}" done </code> </pre>
Chris Reid
@ChrisReid Notez que le fait de boucler sur une liste de chemins comme celui-ci se cassera si un chemin contient un caractère d'espace.
Kusalananda
Je suppose que vous devez changer le séparateur de champ interne (IFS) en «\ n» dans un script. Ce sont des paramètres d'environnement, la façon dont le shell les interprète dépend des valeurs de ces paramètres. Je teste des scripts sur des fichiers factices avant de les utiliser pour dénicher des désastres maladroits comme renommer des fichiers ou les écraser. J'aime la façon shellf printf de définir IFS. IFS = $ (printf "\ n") # très lisible
Chris Reid
1

Comme l' finda obtenu la -exec ... +syntaxe, il n'y a pas grand intérêt à l'utiliser xargs, mais comme vous le demandez:

find /main_directory -not -perm 0755 | xargs chmod 755
Henrik soutient la communauté
la source
1
Notez également que les xargs sans -0(en combinaison avec -print0dans find; qui est l'extension GNU) peuvent être assez problématiques en termes de sécurité si un attaquant potentiel peut créer des noms de fichiers qui incluent des espaces ou d'autres caractères spéciaux. Il vaut donc mieux s'en tenir à -execquand vous le pouvez
Matija Nalis
Pas besoin de xargs(juste utiliser -exec), et si vous l'utilisez, vous devriez utiliser -print0/ -0comme Matija le dit.
Kevin