I have hundreds of directories, each containing several zip files. I would like to iterate over each directory and unzip all zip files, placing the contents of the zip files into the same directory as the zip files themselves (without creating new sub-directories). Here's the bash script I have:
#!/bin/bash
src="/path/to/directories"
for dir in `ls "$src/"`
do
unzip "$src/$dir/*"
done
This script does the unzipping, but it creates thousands of sub-directories and dumps them on my desktop! How can I get the desired behavior? I'm on Mac OSX if that makes a difference.
#!/bin/bash
src=/path/to/directories
for dir in "$src"/*
do
(cd "$dir" && unzip '*')
done
Related
In OS X, double click X.tgz will generate a folder namedX, putting all files into the folder (the folder name follows the .tgz file's name).
I want to do the same thing in the terminal.
However, tar -xvzf /pathtofile/X.tgz will extract all files and put them in /pathtofile/.
And by tar -xvzf /pathtofile/X.tgz -C /newpath/ the newpath does not automatically follows the .tgz file name(i.e. in this case a folder named "X").
Does anyone know if there is a simple way to do this?
Use the strip-component flag in tar:
tar --strip-components=1
This bash function does what you asked to do, which is basically just creating the directory using the filename without the ".tgz"
extract_to_dir () {
filename=$1
dirname="${filename%.*}"
mkdir ./$dirname
tar -xvzf $filename -C $dirname
}
Usage would be:
extract_to_dir filename.tgz
I want a shell script to move multiple folders to a new folder and zip or compress that folder. Can anybody please help me out?
I have a file called dirfile where directory names are stored which are to be moved to a new directory.
#!/bin/usr/sh
while read line; do
Unix_Array[$counter]=$line;
let counter=counter+1;
echo $counter;
done < dirfile
echo {Unix_Array[0]}
for line in [Unix_Array]
do
tar -czvf "$x.tar.gz" "$x"
done
The code you have looks more or less OK (though I wonder why you need two loops--it seems you could do it all at once without the intermediate array). But you're using tar -c when you should be using tar -r to add content to the file rather than creating a new tar file each time.
I'm trying to make a bash script that monitors a folder and it's subfolders.
Basicly I have other app that makes subfolders and adds files to them.
I want to add the files that come into these subfolders into a zip named after the subfolder. Upon which the file in the subfolder is to be deleted.
I'm new to linux and bash scripts, so I'm sorta flunking it :s
#!/bin/bash
inotifywait -mr -e create /home/user/files |
while read filename eventlist eventfile
do
IFS='/' array=($eventfile)
zip /home/user/zips/$(array[1]) $(array[2])
done
So I have a folder /home/usr/files/ in which the app creates subfolders for isntance ...files/files1/. After which the app places the files in the files1 subfolder.
I want those files to be zipped in a folder called files1.zip.
I don't want to have the subfolder in there as well, just the files.
Is also possible to zip to another extension (ofc still being zipped) by simply adding the extension to the zip command?
There are several problems in your script. For one, you should access array elements with ${array[1]} and not $(array[1]). I did a few modifications, and this seems to work on my system:
#!/bin/bash
inotifywait -mr -e create files |
while read -r path eventlist eventfile
do
[[ $eventlist == *ISDIR* ]] && continue;
folder=$(basename "$path")
zip -j "$folder.zip" "$path/$eventfile"
done
I have a folder that after an rsync will have a zip in it. I want to unzip it to its own folder(if the zip is L155.zip, to unzip its content to L155 folder). The problem is that I dont know it's name beforehand(although i know it will be "letter-number-number-number"), so I have to unzip an uknown file to its unknown folder and this to be done automatically.
The command “unzip *”(or unzip *.zip) works in terminal, but not in a script.
These are the commands that have worked through terminal one by one, but dont work in a script.
#!/bin/bash
unzip * #also tried .zip and /path/to/file/* when script is on different folder
i=$(ls | head -1)
y=${i:0:4}
mkdir $y
unzip * -d $y
First I unzip the file, then I read the name of the first extracted file through ls and save it in a variable.I take the first 4 chars and make a directory with it and then again unzip the files to that specific folder.
The whole procedure after first unzip is done, is because the files inside .zip, all start with a name that the zip already has, so if L155.ZIP is the zip, the files inside with be L155***.txt.
The zip file is at /path/to/file/NAME.zip.
When I run the script I get errors like the following:
unzip: cannot find or open /path/to/file/*.ZIP
unzip: cannot find or open /path/to/file//*.ZIP.zip
unzip: cannot find or open /path/to/file//*.ZIP.ZIP. No zipfiles found.
mkdir: cannot create directory 'data': File exists data
unzip: cannot find or open data, data.zip or data.ZIP.
Original answer
Supposing that foo.zip contains a folder foo, you could simply run
#!/bin/bash
unzip \*.zip \*
And then run it as bash auto-unzip.sh.
If you want to have these files extracted into a different folder, then I would modify the above as
#!/bin/bash
cp *.zip /home/user
cd /home/user
unzip \*.zip \*
rm *.zip
This, of course, you would run from the folder where all the zip files are stored.
Another answer
Another "simple" fix is to get dtrx (also available in the Ubuntu repos, possibly for other distros). This will extract each of your *.zip files into its own folder. So if you want the data in a different folder, I'd follow the second example and change it thusly:
#!/bin/bash
cp *.zip /home/user
cd /home/user
dtrx *.zip
rm *.zip
I would try the following.
for i in *.[Zz][Ii][Pp]; do
DIRECTORY=$(basename "$i" .zip)
DIRECTORY=$(basename "$DIRECTORY" .ZIP)
unzip "$i" -d "$DIRECTORY"
done
As noted, the basename program removes the indicated suffix .zip from the filename provided.
I have edited it to be case-insensitive. Both .zip and .ZIP will be recognized.
for zfile in $(find . -maxdepth 1 -type f -name "*.zip")
do
fn=$(echo ${zfile:2:4}) # this will give you the filename without .zip extension
mkdir -p "$fn"
unzip "$zfile" -d "$fn"
done
If the folder has only file file with the extension .zip, you can extract the name without an extension with the basename tool:
BASE=$(basename *.zip .zip)
This will produce an error message if there is more than one file matching *.zip.
Just to be clear about the issue here, the assumption is that the zip file does not contain a folder structure. If it did, there would be no problem; you could simply extract it into the subfolders with unzip. The following is only needed if your zipfile contains loose files, and you want to extract them into a subfolder.
With that caveat, the following should work:
#!/bin/bash
DIR=${1:-.}
BASE=$(basename "$DIR/"*.zip .zip 2>/dev/null) ||
{ echo More than one zipfile >> /dev/stderr; exit 1; }
if [[ $BASE = "*" ]]; then
echo No zipfile found >> /dev/stderr
exit 1
fi
mkdir -p "$DIR/$BASE" ||
{ echo Could not create $DIR/$BASE >> /dev/stderr; exit 1; }
unzip "$DIR/$BASE.zip" -d "$DIR/$BASE"
Put it in a file (anywhere), call it something like unzipper.sh, and chmod a+x it. Then you can call it like this:
/path/to/unzipper.sh /path/to/data_directory
simple one liner I use all the time
$ for file in `ls *.zip`; do unzip $file -d `echo $file | cut -d . -f 1`; done
I have a folder full of zipped files (about 200). I would like to transform this into a folder consisting only of unzipped files. What would be the easiest and quickest way to do this?
Please note that I would like to remove the zipped file from the folder once it us unzipped.
Also, I'm on a Mac.
Thanks!
You can do something like:
for file in `ls *.zip`; do unzip -f $file; rm $file; done
We are looping through all the zip files in the directory, unzipping it and then deleting it.
Note that the -f option of zip will overwrite any file without prompting if it finds a duplicate.
You need to run the above one-line command on the command line from the directory that has the all the zip files. That one line is equivalent to:
for file in `ls *.zip` # ls *.zip gets the list of all zip file..iterate through that list one by one.
do # for each file in the list do the following:
unzip -f $file # unzip the file.
rm $file # delete it.
done
I found this answer which is a simple one liner to gunzip all .gz compressed files within a folder.
Basically you cd to the folder and then run
gunzip *.gz
If you want to only unzip files with a certain prefix you put that before the *
gunzip example*.gz
Easy as cake!