linux - Using "find … -delete" to remove image files only from special subdirectories -


i need clean subdirectories inside music collection unwanted images. i’m using ubuntu 14.04 and/or linux mint 17.2 , bash shell script using find command.

the directory structure (minimal example) follows:

tagged   artist #1     artist #1 - album       artist #1 - track.flac       cover.jpg       something.png     artist #1 - [compilations]       artist #1 - track.flac       cover.jpg       something.png   artist #2     artist #2 - album       artist #2 - track.mp3       cover.jpg 

only in subfolders ending "[compilations]", want delete kind of jpeg and/or png images (because tagging software erroneously puts them there). images happen in normal "album" folders wish keep.

with directory structure, folders "[compilations]" in name can happen below "artist" folders, repectively; maximum of 2 levels deep.

i came following find command:

$ cd tagged $ find . -maxdepth 2 -type d -name '*\[compilations\]' -exec find {} -type f -iname '*.jp*g' -or -iname '*.png' -delete \; 

this seems , takes while, files "./artist #1/artist #1 - [compilations]/cover.jpg" , "./artist #1/artist #1 - [compilations]/something.png" still there (and other image files).

being quite new linux, assume make dumb mistake using find's -delete option, because following command (without -delete) shows files correctly:

$ find . -maxdepth 2 -type d -name '*\[compilations\]' -exec find {} -type f -iname '*.jp*g' -or -iname '*.png' \; ./artist #1/artist #1 - [compilations]/cover.jpg ./artist #1/artist #1 - [compilations]/something.png 

so here questions:

  • why -delete not work?
  • is command safe regarding "extravaganza" whitespace, glob characters , foreign characters in paths , filenames?
  • how have rewrite above command, still using bash , find?
  • could command optimized (re speed, safety, nested finds)?

in actual collection, command must traverse 16899 folders, of them contain whitespace , foreign characters (like czech, russian, japanese, greek, german …), must robust.

thanks in advance insights , enlightenment!

your -delete predicate applies the

-iname '*.png' 

predicate, because missed groupings: when give find following:

-type f -iname '*.jp*g' -or -iname '*.png' -delete 

because of precedence of boolean operators, find understands:

\( -type f -iname '*.jp*g' \) -or \( -iname '*.png' -delete \) 

to fix this, use:

-type f \( -iname '*.jp*g' -or -iname '*.png' \) -delete 

i'd suggest experiment replace -delete -print: you'll see -delete applies to!

now, regarding nested find: because of structure of directory tree (your files in depth 3), should able 1 instance of find:

find -maxdepth 3 -path '*/*\[compilations\]/*' \( -iname '*.jp*g' -o -iname '*.png' \) -type f -print 

(i put -print instead of -delete can check command before executing -delete).


Comments

Popular posts from this blog

1111. appearing after print sequence - php -

java - WARN : org.springframework.web.servlet.PageNotFound - No mapping found for HTTP request with URI [/board/] in DispatcherServlet with name 'appServlet' -

Ruby on Rails, ActiveRecord, Postgres, UTF-8 and ASCII-8BIT encodings -