Er det muligt at bruge 2 kommandoer i -exec
del af find
kommando?
Jeg har prøvet noget som:
find . -name "*" -exec chgrp -v new_group {} ; chmod -v 770 {} \;
og jeg får:
find: manglende argument til -exec
chmod: kan ikke få adgang {}: Ingen sådan fil eller katalog
chmod: kan ikke få adgang ;: Ingen sådan fil eller katalog
Kommentarer
Svar
Hvad angår kommandoen find
, kan du også bare tilføje flere -exec
kommandoer i træk:
find . -name "*" -exec chgrp -v new_group "{}" \; -exec chmod -v 770 "{}" \;
Bemærk, at denne kommando er i sin resultat t, svarende til at bruge
chgrp -v ny_group-fil & & chmod -v 770 fil
på hver fil.
Alle find
“s parametre såsom -name
, -exec
, -size
og så videre, er faktisk test : find
vil fortsætte med at køre dem en efter en, så længe hele kæden indtil videre er vurderet til sand . Så hver på hinanden følgende -exec
kommando udføres kun hvis de foregående returnerede sand (dvs. 0
kommandoer udgangsstatus). Men find
forstår også logiske operatorer som eller (-o
) og ikke (!
). Brug derfor en kæde af -exec
test uanset af de tidligere resultater, man skal bruge noget som dette:
find . -name "*" \( -exec chgrp -v new_group {} \; -o -true \) -exec chmod -v 770 {} \;
Kommentarer
- +1: Ja, det ' er den mest elegante måde at gøre det på. Hvis du kan forklare, hvorfor du bruger
'{}'
(apostrofer omkring seler), kan du besøge: unix.stackexchange.com/q/ 8647/4485 - @user Desværre ved jeg ikke ' om det stadig er nødvendigt. Jeg lavede nogle test lige nu og har ikke ' ikke stødt på en situation, hvor det ville ændre noget. Jeg antager, at det ' er bare " god praksis ", der vil dø ud.
- Citaterne er vigtige for filer med mellemrum i deres navne.
- @ naught101 Nej, citaterne er muligvis nødvendige i nogle ikke-standardskaller, f.eks.
fish
ogcsh
, men er bestemt ikke nødvendige i POSIX-lignende skaller (sh
,dash
,bash
,zsh
,ksh
,yash
).
Svar
find . -name "*" -exec sh -c "chgrp -v new_group "$0" ; chmod -v 770 "$0"" {} \;
Kommentarer
- @Gilles: Underet ved
-c
' s ulige håndtering på $ 0 får mig til at tro, at dette er forkert, hver gang jeg kigger på det, men det er bestemt korrekt. - Jeg kan godt lide, at den eksplicitte skal defineres …
- Dette svar (og Giles ' er en svare) virker som det bedre svar på spørgsmålet givet
sh -c
.
Svar
Din kommando parses først af skallen i to kommandoer adskilt af en ;
, hvilket svarer til en ny linje:
find . -name "*" -exec chgrp -v new_group {} chmod -v 770 {} \;
Hvis du vil køre en shell-kommando, skal du påberåbe en shell eksplicit med bash -c
(eller sh -c
hvis du er ligeglad med, at skallen specifikt er bash):
find . -name "*" -exec sh -c "chgrp -v new_group "$0"; chmod -v 770 "$0"" {} \;
Bemærk brugen af {}
argument til skallen; det er nul-argumentet (som normalt er navnet på skallen eller scriptet, men dette betyder ikke noget her), derfor refereret til "$0"
.
Du kan sende flere filnavne til skallen ad gangen og få skallen til at gentage dem, det “bliver hurtigere. Her sender jeg _
som scriptnavnet og følgende argumenter er filnavne, som for x
(en genvej til for x in "$@"
) gentages over.
find . -name "*" -exec sh -c "for x; do chgrp -v new_group "$x"; chmod -v 770 "$x"; done" _ {} +
Bemærk at siden bash 4 eller i zsh behøver du slet ikke finde her. I bash skal du køre shopt -s globstar
(læg det i din ~/.bashrc
) for at aktivere **/
står for en rekursiv biblioteksglob. (I zsh er dette aktiv hele tiden.) Derefter
chgrp -v new_group -- **/*; chmod -v 770 -- **/*
eller hvis du ønsker, at filerne skal gentages i rækkefølge
for x in **/*; do chgrp -v new_group -- "$x" chmod -v 770 -- "$x" done
En forskel med find
kommandoen er, at skallen ignorerer prikfiler (filer hvis navn begynder med en .
For at inkludere dem skal du først indstille GLOBIGNORE=.:..
i bash; i zsh skal du bruge **/*(D)
som globmønsteret.
Kommentarer
- Dette svar (og Glenn ' s svar) virker som det bedre svar på spørgsmålet givet
sh -c
. - Både
chgrp
ogchmod
har en-R
mulighed for rekursiv operation.
-name "*"
matcher hvert navn, så det er ' en no-op test, der kan fjernes. Også bådechmod
ogchgrp
har en-R
mulighed for rekursiv operation.