2

I'm looking for a single line command or a script that archives 5 folders into .tar files (no gzip/bzip needed) in a certain directory and deletes the folders after a successful compression. It has to use the original folder name as file name for the archive too.

So far I've used the current command, which only does one directory per time:

tar -c directory > directory.tar && rm -rf directory

Thanks in advance.

John Gardeniers
  • 27,458
  • 12
  • 55
  • 109
aardbol
  • 1,473
  • 4
  • 17
  • 26

3 Answers3

1

it's a bit lengthy but:

for i in dir1 dir2 dir3; do tar -cf $i.tar $i; if [ $? -eq 0 ]; then rm -rf $i; fi; done

edit; tar -cf dir.tar dir is a little more concise than tar -c dir > dir.tar

example script:

#!/bin/sh
DIR=$1
tar -cf $DIR.tar $DIR/
if [ $? -eq 0 ]; then
  rm -rf $DIR
fi

you can plop that into script.sh, chmod 755 script.sh and then run it like script.sh directory

however, you could add a lot more to it, to get a list of directories from your main directory, and even use a file to keep track of the last time directory was archived, so you can set your maximum, etc.

cpbills
  • 2,720
  • 18
  • 12
  • What does the `if [ $? -eq 0 ];` check for? – aardbol May 14 '10 at 18:23
  • 1
    `$?` is the return value for the `tar` command, 0 is successful – cpbills May 14 '10 at 18:24
  • Won't `$i` contain a slash? If so the script won't create the archives. – aardbol May 14 '10 at 18:32
  • 1
    `$i` may contain a slash if you're doing `for i in *` but you could remove it with `sed`, but again, we're getting pretty complicated, and this might work better as a multi-line script, for clarity; edit: doing a quick check, trailing slash is not printed with `for i in *; do echo $i; done` – cpbills May 14 '10 at 18:39
1

This will process the first five directories under the directory passed as an argument to the script.

#!/bin/bash
c=1
for directory in $1/*
do
    if [[ -d "$directory" ]]
    then
        tar -cf "${directory}.tar" "$directory" && rm -rf "$directory"
        if (( c++ > 5 ))
        then
            break
        fi
    fi
done

I'm curious about the reason for the limit.

Dennis Williamson
  • 62,149
  • 16
  • 116
  • 151
  • The limit is simply to avoid folder that shouldn't be from being archived – aardbol May 14 '10 at 19:14
  • `tar -cf "${directory}.tar" "$directory" && rm -rf "directory"` should be `tar -cf "${directory}.tar" "$directory" && rm -rf "$directory"`, right? – aardbol May 14 '10 at 19:24
  • 1
    @EarthMind: Yes, that was a typo. I've fixed it. Wouldn't it be better to specify which *particular* directories (by name or other criteria) you want archived or to *exclude* particular directories (by name, etc.) rather than just saying "archive the first five"? – Dennis Williamson May 14 '10 at 22:08
  • Yes, that would be a much better way indeed. I just wanted to keep it simple at first. – aardbol May 21 '10 at 10:41
0
for dir in dir1 dir2 dir3 dir4 dir5 ; do tar -c "$dir" > "$dir".tar && rm -rf "$dir" ; done
Ignacio Vazquez-Abrams
  • 45,939
  • 6
  • 79
  • 84
  • Is there an alternative without hardcoding the directory names? – aardbol May 14 '10 at 18:22
  • if all the directories are in one directory, you can do `for i in /directory/*` – cpbills May 14 '10 at 18:23
  • They are in the same directory but I need to set a maximum so that it doesn't archive all the directories. – aardbol May 14 '10 at 18:31
  • 1
    a maximum? this is one line to fit into a `crontab`, i presume? as you get more complicated, you might want to think about writing this out to a script file, and then calling that script in the crontab... that'd be much cleaner. – cpbills May 14 '10 at 18:37
  • A script would be nice too. One that would allow me to execute it this way: script.sh directory – aardbol May 14 '10 at 18:42
  • `for dir in "$@" ; do tar -c "$dir" > "$dir".tar && rm -rf "$dir" ; done` – Ignacio Vazquez-Abrams May 14 '10 at 21:09