Take the 2-minute tour ×
Unix & Linux Stack Exchange is a question and answer site for users of Linux, FreeBSD and other Un*x-like operating systems.. It's 100% free, no registration required.

I have a lot of zip files. Some are not downloaded correctly and are corrupted. I want to remove them.

Is there a way to find the corrupted archives in bash?

share|improve this question
add comment

2 Answers 2

up vote 3 down vote accepted

With GNU (for -readable and -iname) find:

find . -iname '*.zip' -type f -readable ! -exec unzip -t {} \; -exec rm -i {} \;
share|improve this answer
    
Thanks for your answer. a question: what does \! do? –  Omid Nov 12 '12 at 16:00
1  
@Nima It's a logical not operator, ie. if unzip -t {} fails, exec rm -i {}. It has to be escaped because by default ! is used for history expansion in bash. –  Chris Down Nov 12 '12 at 16:02
2  
@ChrisDown Is there actually a shell that doesn't treat ! literally when it's followed by a space? I have the habit of writing \! too, but I thought it was out of habit (because ! has to be quoted in so many places in bash), not out of necessity. –  Gilles Nov 12 '12 at 23:35
    
@Gilles - Good point! I don't know of any. I guess this goes also to the manual pages saying that {} needs escaping... –  Chris Down Nov 13 '12 at 2:21
    
maybe @Nima wants to remove the files manualy then using -print0 instead of exec rm -i {} \; will display the files that are corrupted without deleting them. –  miracle173 Nov 13 '12 at 3:06
show 1 more comment

The following will print the name of all corrupted zip files in the current directory and its subdirectories:

#!/bin/bash
shopt -s dotglob nullglob globstar
for file in ./**/*.zip; do
    [[ -r $file ]] || continue
    unzip -t "$file" >/dev/null 2>&1 || printf '%s\n' "$file"
done

If you wish to remove them, simply replace printf '%s\n' "$file" with rm -f "$file".

share|improve this answer
1  
Beware though that it's not the same permissions that apply to read a file and to delete it, so you may end up deleting a file just because you don't have the right to read it. Also note that bash recursive globbing (contrary to other shells) descends into symlinks to directories which is generally not what you want. Also, you may want to write it ./**/*.zip to avoid problems with file/dir names starting with "-". –  Stéphane Chazelas Nov 12 '12 at 15:21
    
@StephaneChazelas - Good point, added in a read check. –  Chris Down Nov 12 '12 at 15:24
add comment

Your Answer

 
discard

By posting your answer, you agree to the privacy policy and terms of service.

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