mirror of
https://github.com/rembo10/headphones.git
synced 2026-05-15 16:19:28 +01:00
Merge pull request #2032 from jmullan/feature/cleanup
Fix some linting and other errors
This commit is contained in:
@@ -169,7 +169,7 @@ def initialize(config_file):
|
||||
fp.write(CURRENT_VERSION)
|
||||
except IOError as e:
|
||||
logger.error("Unable to write current version to file '%s': %s",
|
||||
version_lock_file, e)
|
||||
version_lock_file, e)
|
||||
|
||||
# Check for new versions
|
||||
if CONFIG.CHECK_GITHUB_ON_STARTUP:
|
||||
@@ -297,8 +297,8 @@ def initialize_scheduler():
|
||||
# Remove Torrent + data if Post Processed and finished Seeding
|
||||
if CONFIG.TORRENT_REMOVAL_INTERVAL > 0:
|
||||
SCHED.add_job(torrentfinished.checkTorrentFinished,
|
||||
trigger=IntervalTrigger(
|
||||
minutes=CONFIG.TORRENT_REMOVAL_INTERVAL))
|
||||
trigger=IntervalTrigger(
|
||||
minutes=CONFIG.TORRENT_REMOVAL_INTERVAL))
|
||||
|
||||
# Start scheduler
|
||||
logger.info("(Re-)Scheduling background tasks")
|
||||
|
||||
@@ -424,7 +424,7 @@ class CueFile(File):
|
||||
elif t >= 1:
|
||||
t_index = self.tracks[t]['index']
|
||||
content += t_index[1]
|
||||
if (t < len(self.tracks) - 1):
|
||||
if t < (len(self.tracks) - 1):
|
||||
content += '\n'
|
||||
return content
|
||||
|
||||
|
||||
@@ -96,11 +96,16 @@ class DBConnection:
|
||||
|
||||
genParams = lambda myDict: [x + " = ?" for x in myDict.keys()]
|
||||
|
||||
query = "UPDATE " + tableName + " SET " + ", ".join(genParams(valueDict)) + " WHERE " + " AND ".join(genParams(keyDict))
|
||||
update_query = "UPDATE " + tableName + " SET " + ", ".join(genParams(valueDict)) + " WHERE " + " AND ".join(genParams(keyDict))
|
||||
|
||||
self.action(query, valueDict.values() + keyDict.values())
|
||||
self.action(update_query, valueDict.values() + keyDict.values())
|
||||
|
||||
if self.connection.total_changes == changesBefore:
|
||||
query = "INSERT INTO " + tableName + " (" + ", ".join(valueDict.keys() + keyDict.keys()) + ")" + \
|
||||
" VALUES (" + ", ".join(["?"] * len(valueDict.keys() + keyDict.keys())) + ")"
|
||||
self.action(query, valueDict.values() + keyDict.values())
|
||||
insert_query = (
|
||||
"INSERT INTO " + tableName + " (" + ", ".join(valueDict.keys() + keyDict.keys()) + ")" +
|
||||
" VALUES (" + ", ".join(["?"] * len(valueDict.keys() + keyDict.keys())) + ")"
|
||||
)
|
||||
try:
|
||||
self.action(insert_query, valueDict.values() + keyDict.values())
|
||||
except sqlite3.IntegrityError:
|
||||
logger.info('Queries failed: %s and %s', update_query, insert_query)
|
||||
|
||||
@@ -65,7 +65,8 @@ def latinToAscii(unicrap):
|
||||
"""
|
||||
From couch potato
|
||||
"""
|
||||
xlate = {0xc0: 'A', 0xc1: 'A', 0xc2: 'A', 0xc3: 'A', 0xc4: 'A', 0xc5: 'A',
|
||||
xlate = {
|
||||
0xc0: 'A', 0xc1: 'A', 0xc2: 'A', 0xc3: 'A', 0xc4: 'A', 0xc5: 'A',
|
||||
0xc6: 'Ae', 0xc7: 'C',
|
||||
0xc8: 'E', 0xc9: 'E', 0xca: 'E', 0xcb: 'E', 0x86: 'e',
|
||||
0xcc: 'I', 0xcd: 'I', 0xce: 'I', 0xcf: 'I',
|
||||
@@ -90,7 +91,7 @@ def latinToAscii(unicrap):
|
||||
0xb9: '{^1}', 0xba: '{^o}', 0xbb: '>>',
|
||||
0xbc: '{1/4}', 0xbd: '{1/2}', 0xbe: '{3/4}', 0xbf: '?',
|
||||
0xd7: '*', 0xf7: '/'
|
||||
}
|
||||
}
|
||||
|
||||
r = ''
|
||||
for i in unicrap:
|
||||
|
||||
@@ -48,7 +48,7 @@ def artistlist_to_mbids(artistlist, forced=False):
|
||||
|
||||
for artist in artistlist:
|
||||
|
||||
if not artist and not (artist == ' '):
|
||||
if not artist and artist != ' ':
|
||||
continue
|
||||
|
||||
# If adding artists through Manage New Artists, they're coming through as non-unicode (utf-8?)
|
||||
@@ -466,7 +466,7 @@ def addArtisttoDB(artistid, extrasonly=False, forcefull=False):
|
||||
myDB.action('UPDATE albums SET Status=? WHERE AlbumID=?', ['Downloaded', rg['id']])
|
||||
marked_as_downloaded = True
|
||||
else:
|
||||
if ((have_track_count / float(total_track_count)) >= (headphones.CONFIG.ALBUM_COMPLETION_PCT / 100.0)):
|
||||
if (have_track_count / float(total_track_count)) >= (headphones.CONFIG.ALBUM_COMPLETION_PCT / 100.0):
|
||||
myDB.action('UPDATE albums SET Status=? WHERE AlbumID=?', ['Downloaded', rg['id']])
|
||||
marked_as_downloaded = True
|
||||
|
||||
|
||||
@@ -2,6 +2,7 @@
|
||||
Locking-related classes
|
||||
"""
|
||||
|
||||
import headphones.logger
|
||||
import time
|
||||
import threading
|
||||
import Queue
|
||||
@@ -38,10 +39,12 @@ class TimedLock(object):
|
||||
sleep_amount = self.minimum_delta - delta
|
||||
if sleep_amount >= 0:
|
||||
# zero sleeps give the cpu a chance to task-switch
|
||||
headphones.logger.info('Sleeping %s (interval)', sleep_amount)
|
||||
time.sleep(sleep_amount)
|
||||
while not self.queue.empty():
|
||||
try:
|
||||
seconds = self.queue.get(False)
|
||||
headphones.logger.info('Sleeping %s (queued)', seconds)
|
||||
time.sleep(seconds)
|
||||
except Queue.Empty:
|
||||
continue
|
||||
@@ -63,6 +66,7 @@ class TimedLock(object):
|
||||
"""
|
||||
# we use a queue so that we don't have to synchronize
|
||||
# across threads and with or without locks
|
||||
headphones.logger.info('Adding %s to queue', seconds)
|
||||
self.queue.add(seconds)
|
||||
|
||||
|
||||
|
||||
@@ -66,7 +66,7 @@ def encode(albumPath):
|
||||
xldInfoMusic = MediaFile(xldMusicFile)
|
||||
encoderFormat = xldFormat
|
||||
|
||||
if (headphones.CONFIG.ENCODERLOSSLESS):
|
||||
if headphones.CONFIG.ENCODERLOSSLESS:
|
||||
ext = os.path.normpath(os.path.splitext(music)[1].lstrip(".")).lower()
|
||||
if not use_xld and ext == 'flac' or use_xld and (ext != xldFormat and (xldInfoMusic.bitrate / 1000 > 400)):
|
||||
musicFiles.append(os.path.join(r, music))
|
||||
@@ -118,7 +118,7 @@ def encode(albumPath):
|
||||
if not any(music.decode(headphones.SYS_ENCODING, 'replace').lower().endswith('.' + x) for x in ["mp3", "wav"]):
|
||||
logger.warn('Lame cannot encode %s format for %s, use ffmpeg', os.path.splitext(music)[1], music)
|
||||
else:
|
||||
if (music.decode(headphones.SYS_ENCODING, 'replace').lower().endswith('.mp3') and (int(infoMusic.bitrate / 1000) <= headphones.CONFIG.BITRATE)):
|
||||
if music.decode(headphones.SYS_ENCODING, 'replace').lower().endswith('.mp3') and (int(infoMusic.bitrate / 1000) <= headphones.CONFIG.BITRATE):
|
||||
logger.info('%s has bitrate <= %skb, will not be re-encoded', music, headphones.CONFIG.BITRATE)
|
||||
else:
|
||||
encode = True
|
||||
@@ -128,8 +128,8 @@ def encode(albumPath):
|
||||
logger.warn('Cannot re-encode .ogg %s', music.decode(headphones.SYS_ENCODING, 'replace'))
|
||||
else:
|
||||
encode = True
|
||||
elif (headphones.CONFIG.ENCODEROUTPUTFORMAT == 'mp3' or headphones.CONFIG.ENCODEROUTPUTFORMAT == 'm4a'):
|
||||
if (music.decode(headphones.SYS_ENCODING, 'replace').lower().endswith('.' + headphones.CONFIG.ENCODEROUTPUTFORMAT) and (int(infoMusic.bitrate / 1000) <= headphones.CONFIG.BITRATE)):
|
||||
elif headphones.CONFIG.ENCODEROUTPUTFORMAT == 'mp3' or headphones.CONFIG.ENCODEROUTPUTFORMAT == 'm4a':
|
||||
if music.decode(headphones.SYS_ENCODING, 'replace').lower().endswith('.' + headphones.CONFIG.ENCODEROUTPUTFORMAT) and (int(infoMusic.bitrate / 1000) <= headphones.CONFIG.BITRATE):
|
||||
logger.info('%s has bitrate <= %skb, will not be re-encoded', music, headphones.CONFIG.BITRATE)
|
||||
else:
|
||||
encode = True
|
||||
|
||||
@@ -59,7 +59,7 @@ def sendNZB(nzb):
|
||||
return False
|
||||
|
||||
except xmlrpclib.ProtocolError, e:
|
||||
if (e.errmsg == "Unauthorized"):
|
||||
if e.errmsg == "Unauthorized":
|
||||
logger.error(u"NZBget password is incorrect.")
|
||||
else:
|
||||
logger.error(u"Protocol Error: " + e.errmsg)
|
||||
|
||||
@@ -68,8 +68,9 @@ def request_response(url, method="get", auto_raise=True,
|
||||
try:
|
||||
response.raise_for_status()
|
||||
except:
|
||||
logger.debug("Response status code %d is not white " \
|
||||
"listed, raised exception", response.status_code)
|
||||
logger.debug(
|
||||
"Response status code %d is not white "
|
||||
"listed, raised exception", response.status_code)
|
||||
raise
|
||||
elif auto_raise:
|
||||
response.raise_for_status()
|
||||
@@ -85,7 +86,7 @@ def request_response(url, method="get", auto_raise=True,
|
||||
"host is up and running.")
|
||||
except requests.Timeout:
|
||||
logger.error(
|
||||
"Request timed out. The remote host did not respeond timely.")
|
||||
"Request timed out. The remote host did not respond timely.")
|
||||
except requests.HTTPError as e:
|
||||
if e.response is not None:
|
||||
if e.response.status_code >= 500:
|
||||
|
||||
@@ -593,7 +593,7 @@ def searchNZB(album, new=False, losslessOnly=False, albumlength=None):
|
||||
logger.info("Album type is audiobook/spokenword. Using audiobook category")
|
||||
|
||||
# Request results
|
||||
logger.info('Parsing results from nzbs.org')
|
||||
logger.info('Requesting from nzbs.org')
|
||||
|
||||
headers = {'User-Agent': USER_AGENT}
|
||||
params = {
|
||||
@@ -606,9 +606,11 @@ def searchNZB(album, new=False, losslessOnly=False, albumlength=None):
|
||||
|
||||
data = request.request_feed(
|
||||
url='http://beta.nzbs.org/api',
|
||||
params=params, headers=headers
|
||||
params=params, headers=headers,
|
||||
timeout=5
|
||||
)
|
||||
|
||||
logger.info('Parsing results from nzbs.org')
|
||||
# Process feed
|
||||
if data:
|
||||
if not len(data.entries):
|
||||
|
||||
@@ -215,7 +215,7 @@ def dirTorrent(hash, cacheid=None, return_name=None):
|
||||
cacheid = torrentList['torrentc']
|
||||
|
||||
for torrent in torrents:
|
||||
if (torrent[0].lower() == hash):
|
||||
if torrent[0].lower() == hash:
|
||||
if not return_name:
|
||||
return torrent[26], cacheid
|
||||
else:
|
||||
|
||||
@@ -23,13 +23,15 @@ from mako import exceptions
|
||||
|
||||
from operator import itemgetter
|
||||
|
||||
import cherrypy
|
||||
import headphones
|
||||
import json
|
||||
import os
|
||||
import sys
|
||||
import json
|
||||
import time
|
||||
import cherrypy
|
||||
import urllib
|
||||
import urllib2
|
||||
import threading
|
||||
import headphones
|
||||
|
||||
try:
|
||||
# pylint:disable=E0611
|
||||
@@ -70,23 +72,21 @@ class WebInterface(object):
|
||||
def artistPage(self, ArtistID):
|
||||
myDB = db.DBConnection()
|
||||
artist = myDB.action('SELECT * FROM artists WHERE ArtistID=?', [ArtistID]).fetchone()
|
||||
albums = myDB.select('SELECT * from albums WHERE ArtistID=? order by ReleaseDate DESC', [ArtistID])
|
||||
|
||||
# Don't redirect to the artist page until it has the bare minimum info inserted
|
||||
# Redirect to the home page if we still can't get it after 5 seconds
|
||||
retry = 0
|
||||
|
||||
while retry < 5:
|
||||
if not artist:
|
||||
time.sleep(1)
|
||||
artist = myDB.action('SELECT * FROM artists WHERE ArtistID=?', [ArtistID]).fetchone()
|
||||
retry += 1
|
||||
else:
|
||||
break
|
||||
while not artist and retry < 5:
|
||||
time.sleep(1)
|
||||
artist = myDB.action('SELECT * FROM artists WHERE ArtistID=?', [ArtistID]).fetchone()
|
||||
retry += 1
|
||||
|
||||
if not artist:
|
||||
raise cherrypy.HTTPRedirect("home")
|
||||
|
||||
albums = myDB.select('SELECT * from albums WHERE ArtistID=? order by ReleaseDate DESC', [ArtistID])
|
||||
|
||||
# Serve the extras up as a dict to make things easier for new templates (append new extras to the end)
|
||||
extras_list = headphones.POSSIBLE_EXTRAS
|
||||
if artist['Extras']:
|
||||
@@ -110,8 +110,6 @@ class WebInterface(object):
|
||||
def albumPage(self, AlbumID):
|
||||
myDB = db.DBConnection()
|
||||
album = myDB.action('SELECT * from albums WHERE AlbumID=?', [AlbumID]).fetchone()
|
||||
tracks = myDB.select('SELECT * from tracks WHERE AlbumID=? ORDER BY CAST(TrackNumber AS INTEGER)', [AlbumID])
|
||||
description = myDB.action('SELECT * from descriptions WHERE ReleaseGroupID=?', [AlbumID]).fetchone()
|
||||
|
||||
retry = 0
|
||||
while retry < 5:
|
||||
@@ -125,6 +123,9 @@ class WebInterface(object):
|
||||
if not album:
|
||||
raise cherrypy.HTTPRedirect("home")
|
||||
|
||||
tracks = myDB.select('SELECT * from tracks WHERE AlbumID=? ORDER BY CAST(TrackNumber AS INTEGER)', [AlbumID])
|
||||
description = myDB.action('SELECT * from descriptions WHERE ReleaseGroupID=?', [AlbumID]).fetchone()
|
||||
|
||||
if not album['ArtistName']:
|
||||
title = ' - '
|
||||
else:
|
||||
@@ -147,7 +148,9 @@ class WebInterface(object):
|
||||
search.exposed = True
|
||||
|
||||
def addArtist(self, artistid):
|
||||
threading.Thread(target=importer.addArtisttoDB, args=[artistid]).start()
|
||||
thread = threading.Thread(target=importer.addArtisttoDB, args=[artistid])
|
||||
thread.start()
|
||||
thread.join(1)
|
||||
raise cherrypy.HTTPRedirect("artistPage?ArtistID=%s" % artistid)
|
||||
addArtist.exposed = True
|
||||
|
||||
@@ -172,7 +175,9 @@ class WebInterface(object):
|
||||
newValueDict = {'IncludeExtras': 1,
|
||||
'Extras': extras}
|
||||
myDB.upsert("artists", newValueDict, controlValueDict)
|
||||
threading.Thread(target=importer.addArtisttoDB, args=[ArtistID, True, False]).start()
|
||||
thread = threading.Thread(target=importer.addArtisttoDB, args=[ArtistID, True, False])
|
||||
thread.start()
|
||||
thread.join(1)
|
||||
raise cherrypy.HTTPRedirect("artistPage?ArtistID=%s" % ArtistID)
|
||||
getExtras.exposed = True
|
||||
|
||||
@@ -256,7 +261,9 @@ class WebInterface(object):
|
||||
deleteEmptyArtists.exposed = True
|
||||
|
||||
def refreshArtist(self, ArtistID):
|
||||
threading.Thread(target=importer.addArtisttoDB, args=[ArtistID, False, True]).start()
|
||||
thread = threading.Thread(target=importer.addArtisttoDB, args=[ArtistID, False, True])
|
||||
thread.start()
|
||||
thread.join(1)
|
||||
raise cherrypy.HTTPRedirect("artistPage?ArtistID=%s" % ArtistID)
|
||||
refreshArtist.exposed = True
|
||||
|
||||
@@ -312,9 +319,8 @@ class WebInterface(object):
|
||||
myDB.upsert("albums", newValueDict, controlValueDict)
|
||||
searcher.searchforalbum(AlbumID, new)
|
||||
if ArtistID:
|
||||
raise cherrypy.HTTPRedirect("artistPage?ArtistID=%s" % ArtistID)
|
||||
else:
|
||||
raise cherrypy.HTTPRedirect(redirect)
|
||||
redirect = "artistPage?ArtistID=%s" % ArtistID
|
||||
raise cherrypy.HTTPRedirect(redirect)
|
||||
queueAlbum.exposed = True
|
||||
|
||||
def choose_specific_download(self, AlbumID):
|
||||
@@ -332,7 +338,6 @@ class WebInterface(object):
|
||||
'kind': result[4]
|
||||
}
|
||||
results_as_dicts.append(result_dict)
|
||||
|
||||
s = json.dumps(results_as_dicts)
|
||||
cherrypy.response.headers['Content-type'] = 'application/json'
|
||||
return s
|
||||
@@ -340,13 +345,9 @@ class WebInterface(object):
|
||||
choose_specific_download.exposed = True
|
||||
|
||||
def download_specific_release(self, AlbumID, title, size, url, provider, kind, **kwargs):
|
||||
|
||||
# Handle situations where the torrent url contains arguments that are parsed
|
||||
if kwargs:
|
||||
import urllib
|
||||
import urllib2
|
||||
url = urllib2.quote(url, safe=":?/=&") + '&' + urllib.urlencode(kwargs)
|
||||
|
||||
try:
|
||||
result = [(title, int(size), url, provider, kind)]
|
||||
except ValueError:
|
||||
@@ -376,8 +377,9 @@ class WebInterface(object):
|
||||
myDB = db.DBConnection()
|
||||
|
||||
myDB.action('DELETE from have WHERE Matched=?', [AlbumID])
|
||||
album = myDB.action('SELECT ArtistName, AlbumTitle from albums where AlbumID=?', [AlbumID]).fetchone()
|
||||
album = myDB.action('SELECT ArtistID, ArtistName, AlbumTitle from albums where AlbumID=?', [AlbumID]).fetchone()
|
||||
if album:
|
||||
ArtistID = album['ArtistID']
|
||||
myDB.action('DELETE from have WHERE ArtistName=? AND AlbumTitle=?', [album['ArtistName'], album['AlbumTitle']])
|
||||
|
||||
myDB.action('DELETE from albums WHERE AlbumID=?', [AlbumID])
|
||||
@@ -398,9 +400,10 @@ class WebInterface(object):
|
||||
deleteAlbum.exposed = True
|
||||
|
||||
def switchAlbum(self, AlbumID, ReleaseID):
|
||||
'''
|
||||
Take the values from allalbums/alltracks (based on the ReleaseID) and swap it into the album & track tables
|
||||
'''
|
||||
"""
|
||||
Take the values from allalbums/alltracks (based on the ReleaseID) and
|
||||
swap it into the album & track tables
|
||||
"""
|
||||
from headphones import albumswitcher
|
||||
albumswitcher.switch(AlbumID, ReleaseID)
|
||||
raise cherrypy.HTTPRedirect("albumPage?AlbumID=%s" % AlbumID)
|
||||
|
||||
5
pylintrc
5
pylintrc
@@ -38,9 +38,6 @@ load-plugins=
|
||||
# --enable=similarities". If you want to run only the classes checker, but have
|
||||
# no Warning level messages displayed, use"--disable=all --enable=classes
|
||||
# --disable=W"
|
||||
#C0303 whitespace between the end of a line and the newline.
|
||||
#C0325 a single item in parentheses follows an if, for, or other keyword
|
||||
#C0326 wrong number of spaces is used around an operator, bracket or block opener
|
||||
#I0011 an inline option disables a pylint message or a messages category
|
||||
#R0801 a set of similar lines has been detected among multiple file
|
||||
#W0142 a function or method is called using *args or **kwargs to dispatch argument
|
||||
@@ -49,7 +46,7 @@ load-plugins=
|
||||
# C0330(bad-continuation)
|
||||
# E1205(logging-too-many-args)
|
||||
|
||||
disable=C0303,C0325,C0326,I0011,R0801,W0142,C0103,C0111,C0301,C0302,C0304,C0321,C1001,E0101,E0203,E0602,E1101,E1123,R0201,R0401,R0911,R0912,R0914,R0915,R0923,W0102,W0109,W0120,W0141,W0201,W0212,W0231,W0232,W0233,W0301,W0311,W0401,W0403,W0404,W0511,W0601,W0602,W0603,W0611,W0612,W0613,W0621,W0622,W0633,W0702,W0703,W1401,W1201,C0330
|
||||
disable=I0011,R0801,W0142,C0103,C0111,C0301,C0302,C0304,C0321,C1001,E0101,E0203,E0602,E1101,E1123,R0201,R0401,R0911,R0912,R0914,R0915,R0923,W0102,W0109,W0120,W0141,W0201,W0212,W0231,W0232,W0233,W0301,W0311,W0401,W0403,W0404,W0511,W0601,W0602,W0603,W0611,W0612,W0613,W0621,W0622,W0633,W0702,W0703,W1401,W1201,C0330
|
||||
|
||||
[REPORTS]
|
||||
|
||||
|
||||
Reference in New Issue
Block a user