Próbuję dodać nagłówek licencji do wszystkich plików nagłówka i plików źródłowych w katalogu projektu za pomocą pętli for. To nie działa, czy używasz innego podejścia sed
?
Próbuję dodać nagłówek licencji do wszystkich plików nagłówka i plików źródłowych w katalogu projektu za pomocą pętli for. To nie działa, czy używasz innego podejścia sed
?
Odpowiedzi:
for f in **/*.cpp; do
cat header_file $f > $f.new
mv $f.new $f
done
globstar
bash, aby to zadziałało.
To mniej więcej rozszerzony komentarz do odpowiedzi Daniela Serodio . Zacząłem pisać jako komentarz, ale szybko stał się zbyt duży ...
Aby bash glob był rekurencyjny, wymaga tego shopt -s globstar
. Musisz włączyć globstar, w przeciwnym razie **
nie działa. Opcja powłoki globstar została wprowadzona do wersji 4 bash.
Aby uniknąć przetwarzania katalogu, takiego jak my.cpp/
: użyj testu [[ -f $f ]]
... Gdy test jest w nawiasach kwadratowych, zmienne nie muszą być cudzysłowione.
Można również rozważyć możliwość braku dopasowania pasujących plików shopt -s nullglob
, co pozwala na rozwinięcie wzorców, które nie pasują do żadnego pliku, do łańcucha zerowego, a nie do siebie.
Aby obsługiwać wiele wzorów, można łańcucha wzorców glob: **/*.cpp **/*.h
, ale może preferrably, gdy opcja powłoki extglob jest on za pośrednictwem shopt -s extglob
, można użyć takich konstruktów, takich jak **/*.@(cpp|h)
co pozwala uniknąć wielu przechodzi nad systemem plików; raz dla każdego wzoru.
Jeśli chcesz .files
zostać uwzględniony, użyj .*.cpp
itp. Lub użyjshopt -s dotglob
Aby bezpiecznie obsłużyć modyfikowanie pliku, który jest przesyłany potokiem, użyj sponge
z pakietu moreutils
(oszczędza to konieczności tworzenia własnego pliku tymczasowego)
printf "// The License\n\n" > /tmp/$USER-license
shopt -s globstar nullglob extglob
for f in **/*.@(cpp|h) ;do
[[ -f $f ]] && cat "/tmp/$USER-license" "$f" | sponge "$f"
done
[[
może z wdziękiem obsłużyć wartość zerową $f
.
unset x; [ -f $x ] && echo exists
**/*.@(cpp|h)
ją$( find . -name "*.h" -name "*.cpp")
Dziękuję @fred, @maxmackie, @enzotib.
Czy możesz sprawdzić procedurę, którą zastosowałem.
#!/bin/sh
# script to copy the headers to all the source files and header files
for f in *.cpp; do
if (grep Copyright $f);then
echo "No need to copy the License Header to $f"
else
cat license.txt $f > $f.new
mv $f.new $f
echo "License Header copied to $f"
fi
done
w przeciwnym razie nagłówek licencji zostanie skopiowany wiele razy.
Proszę zasugerować mi wzorzec, który powinien przejść przez wszystkie nagłówki i źródła w katalogu projektu i podkatalogach.
Nie mogłem w pełni zrozumieć, co sugeruje @fred.
targln=2; findln=$(sed -rne $targln'{\|// Copyright|=;q}' "$f"); if ((findln==targln));then
... ale oczywiście ponad wszystko, najpierw dokładnie go przetestuj ... PS. Oczywiście w Unix i Linuxie kurs jest taki, żeby zamieszczać takie dodatki w oryginalnym pytaniu, a nie jako odpowiedź ...
grep
, dodaj -q
opcję do grep
. Zawsze dodawaj podwójne cudzysłowy $f
.
Możesz to zrobić za pomocą ex
lub ed
jeśli wolisz (nie powinieneś tego robić sed
zgodnie z życzeniem, sed
jest przeznaczony do edycji strumieni, -i
to zły pomysł z różnych powodów):
shopt -s globstar
for _file in **/*.@(cpp|h); do
ed -s "${_file}" << EOF
0a
/* This file is licensed under the foo license.
All copyright strictly enforced by the copyright monster. */
.
w
EOF
done
sed -i
to zły pomysł?
sed -i
łamie dowiązania symboliczne i dowiązania twarde, co powoduje nieoczekiwane zachowanie. W najlepszym wypadku jest to nieintuicyjne, w gorszym jest aktywnie szkodliwe.
#!/bin/bash
for i in `find . -name '*.[m|h]'` # or whatever other pattern...
do
echo $i
if ! grep -q Copyright $i
then
cat copyright.txt $i >$i.new && mv $i.new $i
fi
done
enter code here
Blog Gerharda Gappmeiera - Howto rekurencyjnie zastępuje nagłówki plików źródłowych
Wpis na blogu załączył tar.gz
plik zawierający potrzebne pliki.
Ma header.template
plik, w którym możesz napisać własny komentarz, może obejmować wiele wierszy.
Ma remove_header.awk
skrypt, który zastępuje istniejące nagłówki nowym nagłówkiem.
Aby go uruchomić:
find . -name "*.h" -exec ~/rh/replace_header.sh {} \;