-
Notifications
You must be signed in to change notification settings - Fork 11
/
librarian.py
177 lines (130 loc) · 5.03 KB
/
librarian.py
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
#!/bin/python
# -*- coding: utf-8 -*-
"""
Traktor Librarian v2.0
"""
import argparse
import os
import sys
import subprocess
import logging
import re
from glob import glob
from conf import *
from clean import Cleaner
from export import Exporter
from library import Library
from logger import get_logger
logger = get_logger(__name__)
def main():
try:
lib = Library(conf.library_dir)
logger.debug("Starting")
if conf.action == "clean":
cleaner = Cleaner(lib)
print("Removing duplicates..."),
cleaner.remove_duplicates()
print("DONE")
cleaner.report()
if not conf.test:
lib.flush()
print("\nTraktor library updated.")
else:
print("\nTest run. No changes made to the library.")
elif conf.action == "export":
exporter = Exporter(lib, conf.export_dir)
exporter.export()
except Exception as e:
logger.error(e, exc_info=False)
#sys.exit(1)
def is_traktor_running():
if sys.platform == "darwin":
try:
subprocess.check_output(['pgrep', '^Traktor$'])
return True
except subprocess.CalledProcessError as e:
return False
elif sys.platform == "win32":
output = subprocess.check_output(['tasklist', '/FI', "IMAGENAME eq Traktor.exe"]).decode("ascii", "ignore")
if output.find("Traktor.exe") != -1:
return True
else:
return False
def natural_sort(l):
convert = lambda text: int(text) if text.isdigit() else text.lower()
alphanum_key = lambda key: [ convert(c) for c in re.split('([0-9]+)', key) ]
return sorted(l, key = alphanum_key)
def get_traktor_dir():
base_dir = os.path.expanduser("~")
if sys.platform == "darwin":
base_dir = os.path.join(base_dir, u"Documents")
elif sys.platform == "win32":
base_dir = os.path.join(base_dir, u"My Documents")
traktor_path = os.path.join(base_dir, u"Native Instruments", u"Traktor*")
traktor_path = glob(traktor_path)
if traktor_path:
# if the Traktor directory exists, then we get the last entry
sorted_paths = natural_sort(traktor_path)
return sorted_paths[-1]
return ""
def library_exists(directory):
collection_path = os.path.join(directory, u"collection.nml")
if not os.path.exists(collection_path):
logger.error(u"Traktor library not found: {}".format(collection_path))
return False
else:
return True
def parse_arguments():
# Parse arguments
parser = argparse.ArgumentParser(description=("Traktor Librarian. Cleans up and fixes incostistencies in Traktor"
" library"))
parser.add_argument('-l', '--library', help='Path to Traktor Library directory. If not provided the default location is used',
type=str)
parser.add_argument('-v', '--verbose', help='Increase output verbosity', action='store_true')
subparsers = parser.add_subparsers(help='Available actions are:')
clean_parser = subparsers.add_parser('clean', help='Clean Traktor Library from duplicates')
clean_parser.add_argument('-t', '--test', help='Do a test run without making any changes to the library',
action='store_true')
clean_parser.set_defaults(func=parse_clean)
export_parser = subparsers.add_parser('export', help='Export the entire Traktor Library to a given location')
export_parser.add_argument("destination", metavar="<Volume>", nargs="?",
help="Volume name the collection will be exported to. Used with export argument.")
export_parser.add_argument('-r', '--remove', action='store_true',
help='Remove files from the destination not longer present in the Traktor library')
export_parser.set_defaults(func=parse_export)
args = parser.parse_args()
if args.library:
conf.library_dir = args.library
else:
conf.library_dir = get_traktor_dir()
if library_exists(conf.library_dir):
print(u"Using Traktor library found in {}\n".format(conf.library_dir))
else:
logger.error(u"Traktor library not found in : {}".format(conf.library_dir))
return False
if args.verbose:
conf.verbose = logging.INFO
# Check that Traktor is not running. Quit if it does.
if is_traktor_running():
logger.error(u"Traktor is running. Please quit Traktor first.")
#return False
return args.func(args)
def parse_clean(args):
conf.action = "clean"
conf.test = args.test
return True
def parse_export(args):
if not args.destination:
logger.error(u"Please specify destination")
return False
conf.action = "export"
conf.export_dir = args.destination
conf.remove_orphans = args.remove
return True
if __name__ == '__main__':
conf.filelog = True
conf.is_console = True
if parse_arguments():
main()
else:
sys.exit(1)