Tar: извлекать только файлы (не подкаталоги)

Как мне извлечь только файлов из каталога в tar-архиве? Мне нужно извлечь все файлы в каталоге, а не конкретные файлы. Например, с tar-архивом такой структуры:

wordpress
 --wp-admin
 --wp-content
 --wp-includes
 --index.php
 --license.txt
 --readme.html

Я хочу извлечь только 3 (или более) файла из каталога wordpress, а не из подкаталогов.

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

0
12.06.2017, 22:57
4 ответа

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

Рассмотрим 370358.tarс таким содержанием

wordpress/
wordpress/index.php
wordpress/license.txt
wordpress/readme.html
wordpress/wp-admin/
wordpress/wp-admin/admin.php
wordpress/wp-content/
wordpress/wp-content/2021/
wordpress/wp-content/2021/01/
wordpress/wp-content/2021/01/19/
wordpress/wp-content/2021/01/19/today.txt
wordpress/wp-content/content.txt
wordpress/wp-content/here.txt
wordpress/wp-content/some.txt
wordpress/wp-includes/

Вы можете извлечь файлы, соответствующие wordpress/*, следующим образом

tar xf /tmp/370358.tar --wildcards --exclude '*/*/*' && rmdir */* 2>/dev/null

ls -R wordpress
wordpress:
index.php  license.txt  readme.html

Обратите внимание на замыкающий rmdir. Мы не можем сказать tarпропустить создание каталога, даже если результирующие каталоги будут пустыми, поэтому мы просто удаляем их впоследствии.

Если вы не хотите, чтобы каталог wordpressвключался в извлечение,

tar xf /tmp/370358.tar --strip-components 1 --wildcards --exclude '*/*/*' && rmdir * 2>/dev/null

ls -R
.:
index.php  license.txt  readme.html
0
19.01.2021, 08:28

Это извлечет все файлы из каталога в tar-файл, не заходя в подкаталоги:

tar --wildcards --no-wildcards-match-slash -xvf file.tar.gz directory_in_tar/*.*
-1
28.01.2020, 05:05

Я мог видеть, что на этот вопрос уже был дан ответ/опубликовано по следующей ссылке:

https://stackoverflow.com/questions/14295771/how-do-i-extract-files-without-folder-structure-using-tar

0
28.01.2020, 05:05

Предполагая, что GNU tar, вы можете извлечь архив с помощью короткого bashскрипта:

tar -x -f archive.tar --to-command=./script.sh

... где script.sh— исполняемый скрипт

#!/bin/bash

if [ "$TAR_FILETYPE" = f ] &&
   [[ $TAR_FILENAME == wordpress/* ]] &&
   [[ $TAR_FILENAME != wordpress/*/* ]]
then
    mkdir -p "${TAR_FILENAME%/*}" &&
    cat >"$TAR_FILENAME" &&
    chmod "$TAR_MODE" "$TAR_FILENAME" &&
    chown "$TAR_UNAME:$TAR_GNAME" "$TAR_FILENAME" || true
else
    cat >/dev/null
fi

Используемые здесь TAR_*переменные устанавливаются GNU tarв среде скрипта, а данные извлекаемого в данный момент файла поступают через стандартный ввод.

Тесты, используемые в сценарии, должны убедиться, что

  1. Файл, который мы извлекаем, является обычным файлом, и
  2. Файл находится в каталоге wordpressи больше нигде.

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

Очевидно, вы также можете указать скрипт в строке -в командной строке tar:

tar -x -f archive.tar --to-command='bash -c "
    if [ \"\$TAR_FILETYPE\" = f ] &&
       [[ \$TAR_FILENAME == wordpress/* ]] &&
       [[ \$TAR_FILENAME != wordpress/*/* ]]
    then
        mkdir -p \"\${TAR_FILENAME%/*}\" &&
        cat >\"\$TAR_FILENAME\" &&
        chmod \"\$TAR_MODE\" \"\$TAR_FILENAME\" &&
        chown \"\$TAR_UNAME:\$TAR_GNAME\" \"\$TAR_FILENAME\" || true
    else
        cat >/dev/null
    fi"'
0
19.01.2021, 08:37

Теги

Похожие вопросы