Dodaj przedrostek do tar

17

Obecnie bardzo nieefektywnie robię w skrypcie:

cp -a $MYPATH /tmp/$VERSION
cd /tmp
tar cjf archive.tar.bz2 $VERSION

Chcę, aby wszystko było zawarte w katalogu o nazwie $ VERSION - czy istnieje sposób, aby to zrobić bez konieczności kopiowania wszystkiego, jak w powyższym skrypcie?

Robby75
źródło
Po co go kopiować? Dlaczego nie tar cjf archive.tar.bz2 $MYPATH?
Chewie
2
@Chewie powiedział, że chce wersji $ jako katalog macierzysty w archiwum.
Kent
Och, teraz to widzę.
Chewie

Odpowiedzi:

26

Wersja GNU tarobsługuje tę --transformopcję (i jej alias --xform), możesz jej użyć w ten sposób

tar --transform "s/^$MYPATH/$VERSION/" -cf archive.tar.bz2 "$MYPATH"

Na przykład, biorąc pod uwagę to drzewo katalogów

foo
└── foo.txt

Komenda

tar --transform "s/^foo/bar/" -cf foo.tar.bz2 foo

stworzy archiwum podobne do

$ tar -tf foo.tar.bz2
bar/
bar/foo.txt
toro2k
źródło
3
Warto zauważyć, że takie podejście może zerwać dowiązania symboliczne. Przygotowywanie flags=r;rozwiązuje problem, jak wspomniano w stackoverflow.com/a/29661783/388803 .
eregon
nie dołączaj ukośnika; kiedy wstawiam ukośnik w transformacji, oryginalny prefiks jest pomijany; np s/^a\//b\//. tar -tnadal pokazuje, a/gdy wszystkie inne pliki są poniżej b/; Zakładam, że jest to niebezpieczne i nie muszę tak naprawdę chronić przed jakimś innym plikiem z tym samym prefiksem, który nie jest katalogiem w pliku tar; więc żaden ukośnik nie jest w porządku, nie mam nic przeciwko, aby wiedzieć, jak najlepiej poradzić sobie z przypadkiem a/transformacji, ale nie, aa/jeśli byłoby to rodzeństwo węzła głównego.
ThorSummoner,
15

Aby załadować bieżący katalog i dodać prefiks, działało to dla mnie:

tar --transform 's,^\.,$VERSION,' -cf foo.tar .
Andy Balaam
źródło
0

Jeśli możesz uciec bez zachowania dowiązań symbolicznych w drzewie plików, na które celujesz, możesz to zrobić

ln -s $MYPATH /tmp/$VERSION
cd /tmp
tar cjhf archive.tar.bz2 $VERSION

Te hśrodki opcja dereference dowiązania, czyli zawierać plik lub katalog, że dowiązanie zamiast po prostu rejestrując fakt, że nie było dowiązanie symboliczne i co wskazał.

Ian Roberts
źródło
0

Aby wygodnie dodać prefiks katalogu, użyj innego separatora niż /w --transformargumencie, np. +Lub ,jak w odpowiedzi Andy'ego.

Tak więc, dla prostszego przypadku, masz kilka plików w bieżącym katalogu i nie chcesz tworzyć tarbomb .

tar czf logs_nightly.tar.gz --tranform 's+^+logs_nightly/+' *.log

Składnia jest s+search+replace+, i ^dlatego po prostu pasuje do początku nazwy pliku.

A teraz, aby odpowiedzieć na OP - cóż, można uniknąć kopiowania całego katalogu /tmp, uruchamiając:

mv $MYPATH $VERSION
tar cjf archive.tar.bz2 $VERSION
mv $VERSION $MYPATH

Alternatywnie:

ln $MYPATH $VERSION
tar cjf archive.tar.bz2 $VERSION

(twardy link, unika problemów z dowiązaniami symbolicznymi)

Dwa ostatnie zostały uwzględnione w celach rozrywkowych, ja sam trzymałbym się odpowiedzi toro2k.

Tomasz Gandor
źródło