chmod, chown und chgrp nur auf verzeichnisse anwenden
Cruz
- programmiertechnik
0 Mathias Brodala0 Cruz
3 Christian Seiler
Hallo Forum,
immer wieder stehe ich vor dem Problem, dass ich die Permissions in einem größerem Teilbaum des Filesystems neu setzen muss und es nicht hinkriege die ch* Kommandos gezielt nur auf Verzeichnisse oder Nichtverzeichnisse anzuwenden. Sagen wir ich habe gerade /neu in mein Filesystem assimiliert. Ich möchte dass alles in diesem Ordner (inkl. /neu) Cruz gehört:
chown -R cruz /neu
und der Gruppe users:
chgrp -R users /neu
Und jetzt sollen der owner und die group alle Dateien und Verzeichnisse beschreiben dürfen, also muss ich allen Dateien 664 und allen Verzeichnissen 775 geben. Wie kriege ich das mit nur 2 Kommandos hin?
Gruß,
Cruz
Hallo Cruz.
Und jetzt sollen der owner und die group alle Dateien und Verzeichnisse beschreiben dürfen, also muss ich allen Dateien 664 und allen Verzeichnissen 775 geben. Wie kriege ich das mit nur 2 Kommandos hin?
Es geht sogar mit einem. Folgendes Script habe ich irgendwann einmal irgendwo gefunden und seitdem residiert es bei mir unter /usr/bin/rchmod:
#!/bin/sh
# recursive chmod with arguments for files and directories
# save internal field separator
IFS_save=$IFS
# set internal field separator, thx to matthias
IFS=$'
'
# read arguments
chmodf=$1 # chmod for files
chmodd=$2 # chmod for directories
dir=$3 # start directory
# test for arguments $1 and $2
if [ -z "$chmodf" -o -z "$chmodd" ]
then
echo "Usage: `basename $0` fff ddd [pfad]"
echo " fff ... chmod argument for files (644)"
echo " ddd ... chmod argument for direcories (755)"
echo " pfad ... nothing for current directory"
exit
fi
# if no start directory, use current directory
if [ -z "$dir" ]
then
dir="."
fi
#"\$x='$x'"
# find backwards all files and directories
for file in `find "$dir" -name "*"`
do
# debug print
#echo "$file"
if [ -d $file ] # directory
then
# chmod
chmod $chmodd $file
elif [ -e $file ] # file
then
# chmod
chmod $chmodf $file
else
echo "error: $file"
fi
done
#set back internal field separator
IFS=$IFS_sav
Es hat mir bisher schon viel Arbeit abgenommen.
Einen schönen Dienstag noch.
Gruß, Mathias
Hallo Mathias,
funktioniert gut danke! Ich hatte gehofft ich finde eine Lösung, die ich nicht von Server zu Server mitschleppen muss, aber eine Menge Arbeit spart das Ding auch so. :)
Cruz
Hallo Cruz,
Und jetzt sollen der owner und die group alle Dateien und Verzeichnisse beschreiben dürfen, also muss ich allen Dateien 664 und allen Verzeichnissen 775 geben. Wie kriege ich das mit nur 2 Kommandos hin?
find /neu -type d -print0 | xargs -0 chmod 0775
find /neu -type f -print0 | xargs -0 chmod 0664
Zur Erläuterung: find sucht im Dateisystem nach Dateien. Es erwartet sowohl einen Parameter, der sagt, wo die Suche losgehen soll, als auch weitere Parameter, die das Verhalten bestimmen. Im einzelnen:
find /neu -type d -print0
/neu: Dort soll die Suche anfangen
-type d: Es soll nach Verzeichnissen gesucht werden
-print0: find soll die Ergebnisse mit 0-bytes getrennt ausgeben
Die Ausgabe von find wird bei obigen Befehlen per Pipe (|) an xargs weitergeleitet. xargs wandelt die Eingabe in Parameter des Befehls, der dahinter steht. Ein
echo test tester | xargs ls
ist folglich identisch mit
ls test tester
Folglich macht der Befehl
xargs -0 chmod 0775
folgendes:
-0: Sagt xargs, dass die Eingabe mit 0-bytes getrennt daherkommt (die Trennung mit 0-Bytes ist deswegen praktisch, weil man sich dann irgendwelche Leerzeichensonderbehandlungskramsereien sparen kann)
chmod 0775: Der Befehl, an den die Eingabe als Parameter angehängt werden sollen.
Viele Grüße,
Christian
find /neu -type d -print0 | xargs -0 chmod 0775
find /neu -type f -print0 | xargs -0 chmod 0664
Jaaaa genau danke!
Hi,
find /neu -type d -print0 | xargs -0 chmod 0775
find /neu -type d -exec chmod 0775 {} ;
Das erspart das "Rumhampeln" mit print, pipe und xargs.
-exec führt das folgende Kommando aus, das mit ; beendet wird.
{} steht dabei für den gefundenen Dateinamen
cu,
Andreas
Hallo Andreas,
find /neu -type d -print0 | xargs -0 chmod 0775
find /neu -type d -exec chmod 0775 {} ;
Das erspart das "Rumhampeln" mit print, pipe und xargs.
-exec führt das folgende Kommando aus, das mit ; beendet wird.
{} steht dabei für den gefundenen Dateinamen
Hat allerdings den Nachteil, dass für jedes gefundene Verzeichnis ein neuer Prozess angelegt wird (was sehr ineffizient werden kann), bei find | xargs werden dagegen nur zwei Prozesse erzeugt (in seltenen Fällen mehr, falls mehr Verzeichnisse als die maximale Anzahl an Argumenten für einen Prozess gefunden werden).
Viele Grüße,
Christian