I have script for finding files of certain type and compress them to a single tar archive and put in to other place. But now, there is a change in requirement, that I need to find files of certain type, list it and compress each of them to a tar archive and put it to other place. Currently I'm using the script

cd /to/top/of/dir/structure
tar -cf /path/to/tarfile.tar --files-from /dev/null # trick to create empty tar file
find . -type f ! -name '*.log' -print0 | xargs -0 tar -uvf /path/to/tarfile.tar

which I have taken from this post : https://superuser.com/questions/436441/copy-every-file-with-a-certain-extension-recursive

So, the above script find certain file type and then archive it as single tar file and then place it to another location. But my question is, I need to find files of certain type, list them, tar each of the listed files and put them into other location.

  • What do you mean by list it? – user9517 Jan 23 '13 at 12:51
  • Like, finding the files of certain types and list them using stdout in console or store it in a file. – FELDAP Jan 23 '13 at 12:53
  • so you want to make a list of the files that you have put in the tar file ? – user9517 Jan 23 '13 at 12:57
  • No, after finding the files of certain type, I would like to list it and then tar each of the listed files to a certain location. – FELDAP Jan 23 '13 at 12:59
  • 4
    A tar of each file doesn't make any sense. If you want to compress the files, use gzip instead of tar. – Sven Jan 23 '13 at 13:12

I'm going with...

cd /to/top/of/dir/structure
find . -type f ! -iname '*.log' -exec gzip -c {} \> /path/to/gzips/\`basename {}\`.gz \;

...but I haven't tested it.

And I'm really dubious it will be what you really need...


I can get it as far as...

find /path/to/top-level -iname "*.log" -printf "gzip -c %p > /path/to/gzips/%f.gz\n"

...to output the commands you would want to run.

I'm still working on executing those commands, short of -fprinting to a temp file, chmod +x and executing that.

Not to mention dealing with any issues escaping awkward characters in filenames.

Edit #2

OK, I can't get it down to one line (which was my challenge, not yours), but I can get it into a fairly simple script:


function compress_file {
  BASENAME=`/bin/basename "$1"`;
  /bin/gzip -c "$1" > /path/to/gzips/$BASENAME.gz;

export -f compress_file;
/bin/find /path/to/top-level -iname "*.log" -exec /bin/bash -c 'compress_file "$0"' {} \;
export -fn compress_file;
  • Thanks. But its not working. It produces some strange outputs in console in weird characters. – FELDAP Jan 23 '13 at 13:50
  • This should work touch {file1,file2,file3,file4}.txt file10.log; find . ! -name '*.log' -type f -print0 | xargs -0 tar cvf tarr.tar {} \; 2>/dev/null – Valentin Bajrami Jan 23 '13 at 14:26
  • That satisfies the Ops original goal. However after reading the dozens of comments on the OP it is clear that there is a new goal: bzipped copies of the log. (one file per log, not one big tar). – Hennes Jan 23 '13 at 14:28
  • Edited answer... – jimbobmcgee Jan 23 '13 at 14:43
  • 1
    OK, edited again... – jimbobmcgee Jan 24 '13 at 11:59

Without a pipe (or xargs), creating several tar files instead of just one, and deleting the non-compressed files, here is how you can do it:

find /path/to/files -name "*.ext" -type f -exec tar -czf {}.tar.z {} \; -exec rm {} \;
  • Alas! I don't think very many of us speak French very well. I've tried to translate you, though. Feel free to edit it if my French is bad. – Falcon Momot Sep 16 '13 at 10:04
  • I think 'tar.z' be 'tar.gz' since the .gz extension is more common. – spuder Jun 1 '15 at 19:07

Find the files and build a list, tell tar to make an archive from the list....

find /path/to/files -name "*.ext" | tar cJfTP /path/to/archive.txz -

Side note: your example doesn't compress the file, it just archives it.

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service, privacy policy and cookie policy

Not the answer you're looking for? Browse other questions tagged or ask your own question.