Использование терминала для заархивирования неизвестного количества пакетов с динамическими именами

Если вы не хотите, чтобы find спускался дальше определенного совпадения, вам следует использовать -prune, а не e. -path или фильтровать вывод find с помощью grep -v

Для проверки сделайте окружение с некоторыми дополнительными файлами и поддиректориями, чтобы вы могли проверить свой find не отображать нежелательный материал:

mkdir -p tmp/2/abc/def
touch tmp/2/abc/def/file1
mkdir -p tmp/2/abc/9876/xyz
touch tmp/2/abc/9876/xyz/file2
tree tmp/

gives:

tmp
└── 2
    └── abc
        ├── 9876
        │   └── xyz
        │       └── file2
        └── def
            └── file1

Если вы сделаете find tmp/2/abc \! -path "*[0-9]*", как предложил @terdon, вывод будет пустым, потому что -path учитывает не только каталоги, начинающиеся ниже abc, но и весь путь, который включает 2. Так что это не то, что вам нужно.

Если вы сделаете find tmp/2/abc -type d | grep -vE '/[0-9-]+(/|$)', как предложил @cas, вы обнаружите, что он тоже ничего не выводит, опять же потому, что он сопоставляет не только файлы вниз от места поиска, но и каталог с именем 2. Кроме того, это потребует от find сначала пройтись по всему дереву под 9876, а если там несколько сотен тысяч элементов, то хождение (и фильтрация) займет заметное время.

Если вы сделаете:

find tmp/2/abc -type d -name '[!0-9]*' -print 

вы обнаружите, что вывод включает путь tmp/2/abc/9876/xyz. Чтобы избавиться от отрезать то, что вам не нужно с помощью -prune:

find tmp/2/abc -type d -name '[!0-9]*' -print -o -name '[0-9]*' -prune

что дает:

tmp/2/abc
tmp/2/abc/def

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

1
16.03.2019, 16:27
1 ответ

Начиная с каталога MyProject/packages/custom-modules, этот вкладыш -может выполнять эту работу:

for module in * ; do cd "$module/ios/" && zip -qr "$module.zip" src/ && cd - &> /dev/null ; done

Идея заключается в том, чтобы получить все имена каталогов модулей с помощью подстановочного знака/glob. Затем для каждого каталога перейдите в подкаталог «ios» и запустите команду zip. Команду zipможно выполнить напрямую, но это будет включать в себя расширенный путь в архиве, который вам может не понадобиться. Ну наконец то,вернуться в родительский каталог и продолжить следующую итерацию.

Вот демо. Это исходная структура каталогов:

[haxiel@testvm1 custom-modules]$ tree
.
├── Module1
│   └── ios
│       └── src
│           ├── file1
│           └── file2
└── Module2
    └── ios
        └── src
            ├── file1
            └── file2

6 directories, 4 files

А теперь запускаем команду:

[haxiel@testvm1 custom-modules]$ for module in * ; do cd "$module/ios/" && zip -qr "$module.zip" src/ && cd - &> /dev/null ; done

Результирующая структура каталогов такова:

[haxiel@testvm1 custom-modules]$ tree
.
├── Module1
│   └── ios
│       ├── Module1.zip
│       └── src
│           ├── file1
│           └── file2
└── Module2
    └── ios
        ├── Module2.zip
        └── src
            ├── file1
            └── file2

6 directories, 6 files

А вот пример ZIP-файла с его содержимым:

[haxiel@testvm1 custom-modules]$ unzip -l Module1/ios/Module1.zip
Archive:  Module1/ios/Module1.zip
  Length      Date    Time    Name
---------  ---------- -----   ----
        0  03-16-2019 20:42   src/
        0  03-16-2019 20:42   src/file1
        0  03-16-2019 20:42   src/file2
---------                     -------
        0                     3 files
2
27.01.2020, 23:30

Теги

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