Назад | Перейти на главную страницу

косая черта tar в начале периода

tar czf dist.tgz --exclude = ". gitignore".

Это создает файлы в tar с начальным "./", что позже превращается в проблему, когда серверу необходимо извлечь части tar.

Может ли кто-нибудь сказать мне, как его упаковать, чтобы не было ведущего "./"?

Попробуйте --xform option, который использует выражение замены, подобное sed. Это позволяет вам изменять ссылки на пути, идущие в архив, а не обрабатывать их во время извлечения (например, с помощью --strip-components).

tar --exclude=.gitignore -cz --xform s:'./':: -f dist.tgz ./

Чтобы отобразить файлы по мере их обработки, добавьте -v и --show-transformed-name параметры:

tar --exclude=.gitignore -cvz --xform s:'./':: --show-transformed-name -f dist.tgz ./

Аргумент для передачи --xform следует этой структуре: s/regexp/replace/[flags] Обратите внимание, что в моем примере я использовал : как разделитель; вы можете использовать любой символ, который хотите, при условии, что вы используете его постоянно. Хорошая ссылка Вот.

Есть несколько способов добиться этого, многие из которых уже упоминались в этом вопросе, а некоторые нет. Это моя попытка скомпилировать их все (со ссылками) и показать примеры для облегчения чтения, позволяя читателю выбрать тот, который соответствует его или ее потребностям.


Пример входного дерева

Это структура, которая будет показана в следующих примерах.

.dotfile
dir/
  .hidden
  file.txt
root.txt

Решение POSIX (кроссплатформенное, кросс-платформенное)

Вы можете использовать человек вместо дегтя, как Фил П. указал.

Обычное поведение:

$ pax -wzvf ../ball.tar.gz .
[…]
$ pax -zf ../ball.tar.gz
.
./.dotfile
./dir
./dir/.hidden
./dir/file.txt
./root.txt

Без точки-косой черты:

$ pax -wzvf ../ball.tar.gz -s ':^\./::' .
[…]
$ pax -zf ../ball.tar.gz
.
.dotfile
dir
dir/.hidden
dir/file.txt
root.txt

Решение Shell Globbing (кроссплатформенное)

Вы также можете использовать * вместо того ., как ott-- указал. Это решение представляет собой сокращенную форму наглости ответ, поскольку оболочка расширит звездочку в приведенном ниже примере на все не скрытые файлы, прежде чем передавать их в качестве аргументов в tar программа.

Нет точки-косой черты (но обратите внимание на отсутствие корневого уровня .dotfile):

$ tar -czvf ../ball.tar.gz *
[…]
$ tar -tzf ../ball.tar.gz
dir/
dir/.hidden
dir/file.txt
root.txt

Если вы не заботитесь об упаковке точечных файлов в CWD, все готово.

если ты делать забота, у тебя есть выход. На многих оболочках (например, bash) можно включить точечные файлы в глобус оболочки, изменив параметр оболочки. В bash это делается с помощью купил:

dotglob

Если установлено, трепать включает имена файлов, начинающиеся с символа '.' в результатах раскрытия имени пути.

$ shopt -s dotglob  # Include dot-files in pathname expansions
$ tar -czvf ../ball.tar.gz *
[…]
$ shopt -u dotglob  # Restore shell's default globbing behavior
$ tar -tzf ../ball.tar.gz
.dotfile
dir/
dir/.hidden
dir/file.txt
root.txt

Решение GNU (Linux)

Использовать --xform как упоминалось в Джордане Бонитатисе ответ.

Обычное поведение:

$ tar -czvf ../ball.tar.gz .
[…]
$ tar -tzf ../ball.tar.gz
./
./root.txt
./.dotfile
./dir/
./dir/file.txt
./dir/.hidden

Без точки-косой черты:

$ tar -czvf ../ball.tar.gz --xform 's:^\./::' . [--show-transformed-names|--show-stored-names]
[…]
$ tar -tzf ../ball.tar.gz
./
root.txt
.dotfile
dir/
dir/file.txt
dir/.hidden

Решение BSD (Mac OS X)

Использовать -s, что обманчиво похоже на человек/sed, но не совсем так, как показано ниже.

Обычное поведение:

$ tar -czvf ../ball.tar.gz .
[…]
$ tar -tzf ../ball.tar.gz
./
./.dotfile
./dir/
./root.txt
./dir/.hidden
./dir/file.txt

Без точки-косой черты:

$ tar -czvf ../ball.tar.gz -s '/.//' .
tar: Removing leading '/' from member names
[…]
$ tar -tzf ../ball.tar.gz 
.dotfile
dir/
root.txt
dir/.hidden
dir/file.txt

Не уверен, какая версия tar это так, но обычно вы должны указать, какие файлы вы хотите заархивировать. подобно tar c . чтобы сжать все в локальном каталоге. Запустив вашу команду на своей машине, я получаю:

tar: Cowardly refusing to create an empty archive

Итак, если вы не хотите попасть в лидеры ./, что вы получаете, когда сжимаете локальный каталог ., вы можете просто указать файлы напрямую. Например:

> tar c hosts fstab | tar tv
-rw-r--r-- root/root      1225 2012-10-20 13:37 hosts
-rw-r--r-- root/root       678 2012-05-13 22:09 fstab

Я использовал tar -P сохранить ведущую / (скорее, чем ./Не совсем понятно, поможет ли это в вашем случае.

-P, --absolute-names
    don't strip leading '/'s from file names 

человек смола

В старых версиях tar он использовал полные имена путей, которые вы указали в tar, но это как-то проблематично, так как может понадобиться вторая копия чего-то и непреднамеренное расширение tar-архива в дни старого формата, может перезаписать существующий файл или файлы.

Таким образом, в самых последних версиях двоичного файла tar, распространяемого практически в любом дистрибутиве Linux, в начале каждого файла, который он упаковывает, помещается ./, так что при непреднамеренном расширении архив расширяется до вашего текущего рабочего каталога и ниже.

Я не уверен, почему это вызывает у вас такую ​​проблему. если вы находитесь на правильном уровне каталога, куда вы хотите расширить этот архив, он сделает именно это. Например, допустим, у вас есть файл как

/tmp/myarchive.tar

и предположим, что содержимое архива

./etc/hosts
./etc/profile
./etc/passwd
./etc/group

если вы расширите этот архив, пока ваш текущий рабочий каталог находится на / (т.е. на корневом уровне), эти файлы перейдут и перезапишут существующий

/etc/hosts
/etc/profile
/etc/passwd
/etc/group

если это то, что вы хотите, вы это получили. Но предположим, вы хотели только файлы hosts из этого архива, но внезапно вы стерли пароль профиля и файлы группы. Надеюсь, у вас есть хорошая резервная копия, чтобы вы могли вернуть их

Но, если вы относитесь к типу системного администратора, который избегает использования корневого уровня, если он / она не нуждается в этом намеренно, вы, скорее всего, вошли в систему, расположенную в / home / some-user, или если вы вошли в систему как root, вы находятся в корневом каталоге. Допустим, ваш in / root. когда вы выполняете команду

# tar -xvf /tmp/myarchive.tar

вы закончите с

/root/etc/hosts
/root/etc/profile
/root/etc/passwd
/root/etc/group

без вреда, без фола. затем

# mv /root/etc/hosts /etc/hosts

Вуаля. Вы добились своей цели.

Я использую это:

tar --create --directory a_dir $(ls --almost-all a_dir) > archive.tar

Это будет список всех файлов и каталогов (кроме . и ..) каталога a_dir и добавляем их в архив. В --directory options устанавливает корень, с которого tar будет искать файлы.