7 from optparse
import OptionParser
, OptionGroup
8 from tag_wrapper
import tag
10 ACCEPTEXTS
= [".ogg", ".mp3"] # Keep it simple for now
12 def issupportedfile(name
):
13 for ext
in ACCEPTEXTS
:
14 if os
.path
.splitext(name
)[1] == ext
:
20 if not os
.path
.isdir(newdir
):
24 def newpath(file, pattern
):
25 # Create the tokens dictionary
28 # TODO: add tracknumber, disknumber and possibily compilation
29 for t
in ["title", "artist", "album artist", "album", "composer", "genre", "date"]:
34 # %album artist% is %artist% if nothing can be found in the tags
35 if tokens
["album artist"] == None:
36 tokens
["album artist"] = tokens
["artist"]
38 # Now replace all tokens by their values
42 pattern
= pattern
.replace(repl
, tokens
[i
][0])
44 # Add the extension and return the new path
45 return pattern
+ os
.path
.splitext(file)[1]
48 def safeprint(string
):
50 Print string first trying to normally encode it, sending it to the
51 console in "raw" UTF-8 if it fails.
53 This is a workaround for Windows's broken console
57 except UnicodeEncodeError:
58 print string
.encode("utf-8")
61 def files_to_move(base_dir
, pattern
, recursive
=False):
63 Figure out which files to move where
65 basepath
= path(base_dir
)
67 files
= basepath
.walkfiles()
69 files
= basepath
.files()
71 # This list will later contain all the (origin, destination) tuples
75 if issupportedfile(file):
76 t
= [ file, newpath(file, pattern
) ]
77 files_return
.append(t
)
82 # Pseudo-enum for actions
88 usage
= "Usage: %prog [options] directory pattern"
89 parser
= OptionParser(usage
=usage
)
90 parser
.add_option("-r", "--recursive", action
="store_true",
91 dest
="recursive", help="also move/copy files from sub-directories", default
=False)
93 actions
= OptionGroup(parser
, "Possible actions")
94 actions
.add_option("--preview", "-p", action
="store_const",
95 const
=PREVIEW
, dest
="action", help="preview, don't make any changes (default)")
96 actions
.add_option("--copy", "-c", action
="store_const",
97 const
=COPY
, dest
="action", help="copy files")
98 actions
.add_option("--move", "-m", action
="store_const",
99 const
=MOVE
, dest
="action", help="move files")
100 parser
.add_option_group(actions
)
101 (options
, args
) = parser
.parse_args()
106 print "You must specify a directory"
112 print "You must specify a pattern"
115 for i
in files_to_move(base_dir
=base
,
116 pattern
=pattern
, recursive
=options
.recursive
):
117 if options
.action
== MOVE
:
118 mkdir(os
.path
.split(i
[1])[0])
119 shutil
.move(i
[0], i
[1])
120 elif options
.action
== COPY
:
121 mkdir(os
.path
.split(i
[1])[0])
122 shutil
.copy2(i
[0], i
[1])
124 safeprint (i
[0] + " --> " + i
[1])
127 if __name__
== "__main__":