Merge pull request #1 from labrys/code-cleanup-autoprocess

Code cleanup autoprocess
This commit is contained in:
Labrys of Knossos 2016-05-31 19:19:48 -04:00
commit 63314a1f73
5 changed files with 294 additions and 386 deletions

View file

@ -1,81 +1,68 @@
# coding=utf-8
import os import os
import time
import core import core
import requests import requests
import time
from core.nzbToMediaUtil import convert_to_ascii, remoteDir, server_responding from core.nzbToMediaUtil import convert_to_ascii, remoteDir, server_responding
from core.nzbToMediaSceneExceptions import process_all_exceptions
from core import logger from core import logger
requests.packages.urllib3.disable_warnings() requests.packages.urllib3.disable_warnings()
class autoProcessComics:
class autoProcessComics(object):
def processEpisode(self, section, dirName, inputName=None, status=0, clientAgent='manual', inputCategory=None): def processEpisode(self, section, dirName, inputName=None, status=0, clientAgent='manual', inputCategory=None):
if int(status) != 0: if int(status) != 0:
logger.warning("FAILED DOWNLOAD DETECTED, nothing to process.",section) logger.warning("FAILED DOWNLOAD DETECTED, nothing to process.", section)
return [1, "%s: Failed to post-process. %s does not support failed downloads" % (section, section) ] return [1, "{0}: Failed to post-process. {1} does not support failed downloads".format(section, section)]
host = core.CFG[section][inputCategory]["host"] host = core.CFG[section][inputCategory]["host"]
port = core.CFG[section][inputCategory]["port"] port = core.CFG[section][inputCategory]["port"]
username = core.CFG[section][inputCategory]["username"] username = core.CFG[section][inputCategory]["username"]
password = core.CFG[section][inputCategory]["password"] password = core.CFG[section][inputCategory]["password"]
try: ssl = int(core.CFG[section][inputCategory].get("ssl", 0))
ssl = int(core.CFG[section][inputCategory]["ssl"]) web_root = core.CFG[section][inputCategory].get("web_root", "")
except: remote_path = int(core.CFG[section][inputCategory].get("remote_path"), 0)
ssl = 0 protocol = "https://" if ssl else "http://"
try:
web_root = core.CFG[section][inputCategory]["web_root"]
except:
web_root = ""
try:
remote_path = int(core.CFG[section][inputCategory]["remote_path"])
except:
remote_path = 0
if ssl: url = "{0}{1}:{2}{3}/post_process".format(protocol, host, port, web_root)
protocol = "https://"
else:
protocol = "http://"
url = "%s%s:%s%s/post_process" % (protocol, host, port, web_root)
if not server_responding(url): if not server_responding(url):
logger.error("Server did not respond. Exiting", section) logger.error("Server did not respond. Exiting", section)
return [1, "%s: Failed to post-process - %s did not respond." % (section, section) ] return [1, "{0}: Failed to post-process - {1} did not respond.".format(section, section)]
inputName, dirName = convert_to_ascii(inputName, dirName) inputName, dirName = convert_to_ascii(inputName, dirName)
clean_name, ext = os.path.splitext(inputName) clean_name, ext = os.path.splitext(inputName)
if len(ext) == 4: # we assume this was a standrard extension. if len(ext) == 4: # we assume this was a standard extension.
inputName = clean_name inputName = clean_name
params = {} params = {
params['nzb_folder'] = dirName 'nzb_folder': remoteDir(dirName) if remote_path else dirName,
}
if remote_path: if inputName is not None:
params['nzb_folder'] = remoteDir(dirName)
if inputName != None:
params['nzb_name'] = inputName params['nzb_name'] = inputName
success = False success = False
logger.debug("Opening URL: %s" % (url), section) logger.debug("Opening URL: {0}".format(url), section)
try: try:
r = requests.get(url, auth=(username, password), params=params, stream=True, verify=False, timeout=(30, 300)) r = requests.get(url, auth=(username, password), params=params, stream=True, verify=False, timeout=(30, 300))
except requests.ConnectionError: except requests.ConnectionError:
logger.error("Unable to open URL", section) logger.error("Unable to open URL", section)
return [1, "%s: Failed to post-process - Unable to connect to %s" % (section, section) ] return [1, "{0}: Failed to post-process - Unable to connect to {1}".format(section, section)]
for line in r.iter_lines(): for line in r.iter_lines():
if line: logger.postprocess("%s" % (line), section) if line:
if ("Post Processing SUCCESSFUL!" or "Post Processing SUCCESSFULL!")in line: success = True logger.postprocess("{0}".format(line), section)
if "Post Processing SUCCESSFUL" in line:
success = True
if not r.status_code in [requests.codes.ok, requests.codes.created, requests.codes.accepted]: if r.status_code not in [requests.codes.ok, requests.codes.created, requests.codes.accepted]:
logger.error("Server returned status %s" % (str(r.status_code)), section) logger.error("Server returned status {0}".format(r.status_code), section)
return [1, "%s: Failed to post-process - Server returned status %s" % (section, str(r.status_code)) ] return [1, "{0}: Failed to post-process - Server returned status {1}".format(section, r.status_code)]
if success: if success:
logger.postprocess("SUCCESS: This issue has been processed successfully",section) logger.postprocess("SUCCESS: This issue has been processed successfully", section)
return [0, "%s: Successfully post-processed %s" % (section, inputName) ] return [0, "{0}: Successfully post-processed {1}".format(section, inputName)]
else: else:
logger.warning("The issue does not appear to have successfully processed. Please check your Logs",section) logger.warning("The issue does not appear to have successfully processed. Please check your Logs", section)
return [1, "%s: Failed to post-process - Returned log from %s was not as expected." % (section, section) ] return [1, "{0}: Failed to post-process - Returned log from {1} was not as expected.".format(section, section)]

View file

@ -1,86 +1,75 @@
# coding=utf-8
import os
import core import core
import requests import requests
import shutil import shutil
from core.nzbToMediaUtil import convert_to_ascii, server_responding from core.nzbToMediaUtil import convert_to_ascii, server_responding
from core.nzbToMediaSceneExceptions import process_all_exceptions
from core import logger from core import logger
requests.packages.urllib3.disable_warnings() requests.packages.urllib3.disable_warnings()
class autoProcessGames:
class autoProcessGames(object):
def process(self, section, dirName, inputName=None, status=0, clientAgent='manual', inputCategory=None): def process(self, section, dirName, inputName=None, status=0, clientAgent='manual', inputCategory=None):
status = int(status) status = int(status)
host = core.CFG[section][inputCategory]["host"] host = core.CFG[section][inputCategory]["host"]
port = core.CFG[section][inputCategory]["port"] port = core.CFG[section][inputCategory]["port"]
apikey = core.CFG[section][inputCategory]["apikey"] apikey = core.CFG[section][inputCategory]["apikey"]
try: library = core.CFG[section][inputCategory].get("library")
library = core.CFG[section][inputCategory]["library"] ssl = int(core.CFG[section][inputCategory].get("ssl", 0))
except: web_root = core.CFG[section][inputCategory].get("web_root", "")
library = None protocol = "https://" if ssl else "http://"
try:
ssl = int(core.CFG[section][inputCategory]["ssl"])
except:
ssl = 0
try:
web_root = core.CFG[section][inputCategory]["web_root"]
except:
web_root = ""
if ssl: url = "{0}{1}:{2}{3}/api".format(protocol, host, port, web_root)
protocol = "https://"
else:
protocol = "http://"
url = "%s%s:%s%s/api" % (protocol, host, port, web_root)
if not server_responding(url): if not server_responding(url):
logger.error("Server did not respond. Exiting", section) logger.error("Server did not respond. Exiting", section)
return [1, "%s: Failed to post-process - %s did not respond." % (section, section) ] return [1, "{0}: Failed to post-process - {1} did not respond.".format(section, section)]
inputName, dirName = convert_to_ascii(inputName, dirName) inputName, dirName = convert_to_ascii(inputName, dirName)
fields = inputName.split("-") fields = inputName.split("-")
gamezID = fields[0].replace("[","").replace("]","").replace(" ","") gamezID = fields[0].replace("[", "").replace("]", "").replace(" ", "")
downloadStatus = 'Wanted' downloadStatus = 'Downloaded' if status == 0 else 'Wanted'
if status == 0:
downloadStatus = 'Downloaded'
params = {} params = {
params['api_key'] = apikey 'api_key': apikey,
params['mode'] = 'UPDATEREQUESTEDSTATUS' 'mode': 'UPDATEREQUESTEDSTATUS',
params['db_id'] = gamezID 'db_id': gamezID,
params['status'] = downloadStatus 'status': downloadStatus
}
logger.debug("Opening URL: %s" % (url),section) logger.debug("Opening URL: {0}".format(url), section)
try: try:
r = requests.get(url, params=params, verify=False, timeout=(30, 300)) r = requests.get(url, params=params, verify=False, timeout=(30, 300))
except requests.ConnectionError: except requests.ConnectionError:
logger.error("Unable to open URL") logger.error("Unable to open URL")
return [1, "%s: Failed to post-process - Unable to connect to %s" % (section, section) ] return [1, "{0}: Failed to post-process - Unable to connect to {1}".format(section, section)]
result = r.json() result = r.json()
logger.postprocess("%s" % (result),section) logger.postprocess("{0}".format(result), section)
if library: if library:
logger.postprocess("moving files to library: %s" % (library),section) logger.postprocess("moving files to library: {0}".format(library), section)
try: try:
shutil.move(dirName, os.path.join(library, inputName)) shutil.move(dirName, os.path.join(library, inputName))
except: except:
logger.error("Unable to move %s to %s" % (dirName, os.path.join(library, inputName)), section) logger.error("Unable to move {0} to {1}".format(dirName, os.path.join(library, inputName)), section)
return [1, "%s: Failed to post-process - Unable to move files" % (section) ] return [1, "{0}: Failed to post-process - Unable to move files".format(section)]
else: else:
logger.error("No library specified to move files to. Please edit your configuration.", section) logger.error("No library specified to move files to. Please edit your configuration.", section)
return [1, "%s: Failed to post-process - No library defined in %s" % (section, section) ] return [1, "{0}: Failed to post-process - No library defined in {1}".format(section, section)]
if not r.status_code in [requests.codes.ok, requests.codes.created, requests.codes.accepted]: if r.status_code not in [requests.codes.ok, requests.codes.created, requests.codes.accepted]:
logger.error("Server returned status %s" % (str(r.status_code)), section) logger.error("Server returned status {0}".format(r.status_code), section)
return [1, "%s: Failed to post-process - Server returned status %s" % (section, str(r.status_code)) ] return [1, "{0}: Failed to post-process - Server returned status {1}".format(section, r.status_code)]
elif result['success']: elif result['success']:
logger.postprocess("SUCCESS: Status for %s has been set to %s in Gamez" % (gamezID, downloadStatus),section) logger.postprocess("SUCCESS: Status for {0} has been set to {1} in Gamez".format(gamezID, downloadStatus), section)
return [0, "%s: Successfully post-processed %s" % (section, inputName) ] return [0, "{0}: Successfully post-processed {1}".format(section, inputName)]
else: else:
logger.error("FAILED: Status for %s has NOT been updated in Gamez" % (gamezID),section) logger.error("FAILED: Status for {0} has NOT been updated in Gamez".format(gamezID), section)
return [1, "%s: Failed to post-process - Returned log from %s was not as expected." % (section, section) ] return [1, "{0}: Failed to post-process - Returned log from {1} was not as expected.".format(section, section)]

View file

@ -1,3 +1,5 @@
# coding=utf-8
import os import os
import time import time
import requests import requests
@ -10,12 +12,13 @@ from core.transcoder import transcoder
requests.packages.urllib3.disable_warnings() requests.packages.urllib3.disable_warnings()
class autoProcessMovie:
class autoProcessMovie(object):
def get_release(self, baseURL, imdbid=None, download_id=None, release_id=None): def get_release(self, baseURL, imdbid=None, download_id=None, release_id=None):
results = {} results = {}
params = {} params = {}
# determin cmd and params to send to CouchPotato to get our results # determine cmd and params to send to CouchPotato to get our results
section = 'movies' section = 'movies'
cmd = "/media.list" cmd = "/media.list"
if release_id or imdbid: if release_id or imdbid:
@ -24,27 +27,28 @@ class autoProcessMovie:
params['id'] = release_id or imdbid params['id'] = release_id or imdbid
url = baseURL + cmd url = baseURL + cmd
logger.debug("Opening URL: %s with PARAMS: %s" % (url, params)) logger.debug("Opening URL: {0} with PARAMS: {1}".format(url, params))
try: try:
r = requests.get(url, params=params, verify=False, timeout=(30, 60)) r = requests.get(url, params=params, verify=False, timeout=(30, 60))
except requests.ConnectionError: except requests.ConnectionError:
logger.error("Unable to open URL %s" % url) logger.error("Unable to open URL {0}".format(url))
return results return results
try: try:
result = r.json() result = r.json()
except: except ValueError:
# ValueError catches simplejson's JSONDecodeError and json's ValueError
logger.error("CouchPotato returned the following non-json data") logger.error("CouchPotato returned the following non-json data")
for line in r.iter_lines(): for line in r.iter_lines():
logger.error("%s" %(line)) logger.error("{0}".format(line))
return results return results
if not result['success']: if not result['success']:
if 'error' in result: if 'error' in result:
logger.error(str(result['error'])) logger.error(str(result['error']))
else: else:
logger.error("no media found for id %s" % (params['id'])) logger.error("no media found for id {0}".format(params['id']))
return results return results
# Gather release info and return it back, no need to narrow results # Gather release info and return it back, no need to narrow results
@ -53,7 +57,8 @@ class autoProcessMovie:
id = result[section]['_id'] id = result[section]['_id']
results[id] = result[section] results[id] = result[section]
return results return results
except:pass except:
pass
# Gather release info and proceed with trying to narrow results to one release choice # Gather release info and proceed with trying to narrow results to one release choice
@ -106,33 +111,16 @@ class autoProcessMovie:
method = core.CFG[section][inputCategory]["method"] method = core.CFG[section][inputCategory]["method"]
delete_failed = int(core.CFG[section][inputCategory]["delete_failed"]) delete_failed = int(core.CFG[section][inputCategory]["delete_failed"])
wait_for = int(core.CFG[section][inputCategory]["wait_for"]) wait_for = int(core.CFG[section][inputCategory]["wait_for"])
ssl = int(core.CFG[section][inputCategory].get("ssl", 0))
web_root = core.CFG[section][inputCategory].get("web_root", "")
remote_path = int(core.CFG[section][inputCategory].get("remote_path", 0))
extract = int(section[inputCategory].get("extract", 0))
protocol = "https://" if ssl else "http://"
try: baseURL = "{0}{1}:{2}{3}/api/{4}".format(protocol, host, port, web_root, apikey)
ssl = int(core.CFG[section][inputCategory]["ssl"])
except:
ssl = 0
try:
web_root = core.CFG[section][inputCategory]["web_root"]
except:
web_root = ""
try:
remote_path = int(core.CFG[section][inputCategory]["remote_path"])
except:
remote_path = 0
try:
extract = int(section[inputCategory]["extract"])
except:
extract = 0
if ssl:
protocol = "https://"
else:
protocol = "http://"
baseURL = "%s%s:%s%s/api/%s" % (protocol, host, port, web_root, apikey)
if not server_responding(baseURL): if not server_responding(baseURL):
logger.error("Server did not respond. Exiting", section) logger.error("Server did not respond. Exiting", section)
return [1, "%s: Failed to post-process - %s did not respond." % (section, section) ] return [1, "{0}: Failed to post-process - {1} did not respond.".format(section, section)]
imdbid = find_imdbid(dirName, inputName) imdbid = find_imdbid(dirName, inputName)
release = self.get_release(baseURL, imdbid, download_id) release = self.get_release(baseURL, imdbid, download_id)
@ -166,7 +154,7 @@ class autoProcessMovie:
inputName, dirName = convert_to_ascii(inputName, dirName) inputName, dirName = convert_to_ascii(inputName, dirName)
if not listMediaFiles(dirName, media=True, audio=False, meta=False, archives=False) and listMediaFiles(dirName, media=False, audio=False, meta=False, archives=True) and extract: if not listMediaFiles(dirName, media=True, audio=False, meta=False, archives=False) and listMediaFiles(dirName, media=False, audio=False, meta=False, archives=True) and extract:
logger.debug('Checking for archives to extract in directory: %s' % (dirName)) logger.debug('Checking for archives to extract in directory: {0}'.format(dirName))
core.extractFiles(dirName) core.extractFiles(dirName)
inputName, dirName = convert_to_ascii(inputName, dirName) inputName, dirName = convert_to_ascii(inputName, dirName)
@ -181,39 +169,39 @@ class autoProcessMovie:
good_files += 1 good_files += 1
if num_files > 0 and good_files == num_files: if num_files > 0 and good_files == num_files:
if status: if status:
logger.info("Status shown as failed from Downloader, but %s valid video files found. Setting as success." % (str(good_files)), section) logger.info("Status shown as failed from Downloader, but {0} valid video files found. Setting as success.".format(good_files), section)
status = 0 status = 0
elif num_files > 0 and good_files < num_files: elif num_files > 0 and good_files < num_files:
logger.info("Status shown as success from Downloader, but corrupt video files found. Setting as failed.", section) logger.info("Status shown as success from Downloader, but corrupt video files found. Setting as failed.", section)
if os.environ.has_key('NZBOP_VERSION') and os.environ['NZBOP_VERSION'][0:5] >= '14.0': if 'NZBOP_VERSION' in os.environ and os.environ['NZBOP_VERSION'][0:5] >= '14.0':
print('[NZB] MARK=BAD') print('[NZB] MARK=BAD')
if failureLink: if failureLink:
failureLink = failureLink + '&corrupt=true' failureLink += '&corrupt=true'
status = 1 status = 1
elif clientAgent == "manual": elif clientAgent == "manual":
logger.warning("No media files found in directory %s to manually process." % (dirName), section) logger.warning("No media files found in directory {0} to manually process.".format(dirName), section)
return [0, ""] # Success (as far as this script is concerned) return [0, ""] # Success (as far as this script is concerned)
else: else:
logger.warning("No media files found in directory %s. Processing this as a failed download" % (dirName), section) logger.warning("No media files found in directory {0}. Processing this as a failed download".format(dirName), section)
status = 1 status = 1
if os.environ.has_key('NZBOP_VERSION') and os.environ['NZBOP_VERSION'][0:5] >= '14.0': if 'NZBOP_VERSION' in os.environ and os.environ['NZBOP_VERSION'][0:5] >= '14.0':
print('[NZB] MARK=BAD') print('[NZB] MARK=BAD')
if status == 0: if status == 0:
if core.TRANSCODE == 1: if core.TRANSCODE == 1:
result, newDirName = transcoder.Transcode_directory(dirName) result, newDirName = transcoder.Transcode_directory(dirName)
if result == 0: if result == 0:
logger.debug("Transcoding succeeded for files in %s" % (dirName), section) logger.debug("Transcoding succeeded for files in {0}".format(dirName), section)
dirName = newDirName dirName = newDirName
else: else:
logger.error("Transcoding failed for files in %s" % (dirName), section) logger.error("Transcoding failed for files in {0}".format(dirName), section)
return [1, "%s: Failed to post-process - Transcoding failed" % (section) ] return [1, "{0}: Failed to post-process - Transcoding failed".format(section)]
for video in listMediaFiles(dirName, media=True, audio=False, meta=False, archives=False): for video in listMediaFiles(dirName, media=True, audio=False, meta=False, archives=False):
if not release and not ".cp(tt" in video and imdbid: if not release and ".cp(tt" not in video and imdbid:
videoName, videoExt = os.path.splitext(video) videoName, videoExt = os.path.splitext(video)
video2 = "%s.cp(%s)%s" % (videoName, imdbid, videoExt) video2 = "{0}.cp({1}){2}".format(videoName, imdbid, videoExt)
if not (clientAgent in [core.TORRENT_CLIENTAGENT, 'manual'] and core.USELINK == 'move-sym'): if not (clientAgent in [core.TORRENT_CLIENTAGENT, 'manual'] and core.USELINK == 'move-sym'):
logger.debug('Renaming: %s to: %s' % (video, video2)) logger.debug('Renaming: {0} to: {1}'.format(video, video2))
os.rename(video, video2) os.rename(video, video2)
params = {} params = {}
@ -221,9 +209,7 @@ class autoProcessMovie:
params['downloader'] = downloader or clientAgent params['downloader'] = downloader or clientAgent
params['download_id'] = download_id params['download_id'] = download_id
params['media_folder'] = dirName params['media_folder'] = remoteDir(dirName) if remote_path else dirName
if remote_path:
params['media_folder'] = remoteDir(dirName)
if method == "manage": if method == "manage":
command = "/manage.update" command = "/manage.update"
@ -231,129 +217,129 @@ class autoProcessMovie:
else: else:
command = "/renamer.scan" command = "/renamer.scan"
url = "%s%s" % (baseURL, command) url = "{0}{1}".format(baseURL, command)
logger.debug("Opening URL: %s with PARAMS: %s" % (url, params), section) logger.debug("Opening URL: {0} with PARAMS: {1}".format(url, params), section)
logger.postprocess("Starting %s scan for %s" % (method, inputName), section) logger.postprocess("Starting {0} scan for {1}".format(method, inputName), section)
try: try:
r = requests.get(url, params=params, verify=False, timeout=(30, 1800)) r = requests.get(url, params=params, verify=False, timeout=(30, 1800))
except requests.ConnectionError: except requests.ConnectionError:
logger.error("Unable to open URL", section) logger.error("Unable to open URL", section)
return [1, "%s: Failed to post-process - Unable to connect to %s" % (section, section) ] return [1, "{0}: Failed to post-process - Unable to connect to {1}".format(section, section)]
result = r.json() result = r.json()
if not r.status_code in [requests.codes.ok, requests.codes.created, requests.codes.accepted]: if r.status_code not in [requests.codes.ok, requests.codes.created, requests.codes.accepted]:
logger.error("Server returned status %s" % (str(r.status_code)), section) logger.error("Server returned status {0}".format(r.status_code), section)
return [1, "%s: Failed to post-process - Server returned status %s" % (section, str(r.status_code)) ] return [1, "{0}: Failed to post-process - Server returned status {1}".format(section, r.status_code)]
elif result['success']: elif result['success']:
logger.postprocess("SUCCESS: Finished %s scan for folder %s" % (method, dirName), section) logger.postprocess("SUCCESS: Finished {0} scan for folder {1}".format(method, dirName), section)
if method == "manage": if method == "manage":
return [0, "%s: Successfully post-processed %s" % (section, inputName) ] return [0, "{0}: Successfully post-processed {1}".format(section, inputName)]
else: else:
logger.error("FAILED: %s scan was unable to finish for folder %s. exiting!" % (method, dirName), logger.error("FAILED: {0} scan was unable to finish for folder {1}. exiting!".format(method, dirName),
section) section)
return [1, "%s: Failed to post-process - Server did not return success" % (section) ] return [1, "{0}: Failed to post-process - Server did not return success".format(section)]
else: else:
core.FAILED = True core.FAILED = True
logger.postprocess("FAILED DOWNLOAD DETECTED FOR %s" % (inputName), section) logger.postprocess("FAILED DOWNLOAD DETECTED FOR {0}".format(inputName), section)
if failureLink: if failureLink:
reportNzb(failureLink, clientAgent) reportNzb(failureLink, clientAgent)
if delete_failed and os.path.isdir(dirName) and not os.path.dirname(dirName) == dirName: if delete_failed and os.path.isdir(dirName) and not os.path.dirname(dirName) == dirName:
logger.postprocess("Deleting failed files and folder %s" % dirName, section) logger.postprocess("Deleting failed files and folder {0}".format(dirName), section)
rmDir(dirName) rmDir(dirName)
if not release_id and not media_id: if not release_id and not media_id:
logger.error("Could not find a downloaded movie in the database matching %s, exiting!" % inputName, logger.error("Could not find a downloaded movie in the database matching {0}, exiting!".format(inputName),
section) section)
return [1, "%s: Failed to post-process - Failed download not found in %s" % (section, section) ] return [1, "{0}: Failed to post-process - Failed download not found in {1}".format(section, section)]
if release_id: if release_id:
logger.postprocess("Setting failed release %s to ignored ..." % (inputName), section) logger.postprocess("Setting failed release {0} to ignored ...".format(inputName), section)
url = baseURL + "/release.ignore" url = baseURL + "/release.ignore"
params = {'id': release_id} params = {'id': release_id}
logger.debug("Opening URL: %s with PARAMS: %s" % (url, params), section) logger.debug("Opening URL: {0} with PARAMS: {1}".format(url, params), section)
try: try:
r = requests.get(url, params=params, verify=False, timeout=(30, 120)) r = requests.get(url, params=params, verify=False, timeout=(30, 120))
except requests.ConnectionError: except requests.ConnectionError:
logger.error("Unable to open URL %s" % (url), section) logger.error("Unable to open URL {0}".format(url), section)
return [1, "%s: Failed to post-process - Unable to connect to %s" % (section, section) ] return [1, "{0}: Failed to post-process - Unable to connect to {1}".format(section, section)]
result = r.json() result = r.json()
if not r.status_code in [requests.codes.ok, requests.codes.created, requests.codes.accepted]: if r.status_code not in [requests.codes.ok, requests.codes.created, requests.codes.accepted]:
logger.error("Server returned status %s" % (str(r.status_code)), section) logger.error("Server returned status {0}".format(r.status_code), section)
return [1, "%s: Failed to post-process - Server returned status %s" % (section, str(r.status_code)) ] return [1, "{0}: Failed to post-process - Server returned status {1}".format(section, r.status_code)]
elif result['success']: elif result['success']:
logger.postprocess("SUCCESS: %s has been set to ignored ..." % (inputName), section) logger.postprocess("SUCCESS: {0} has been set to ignored ...".format(inputName), section)
else: else:
logger.warning("FAILED: Unable to set %s to ignored!" % (inputName), section) logger.warning("FAILED: Unable to set {0} to ignored!".format(inputName), section)
return [1, "%s: Failed to post-process - Unable to set %s to ignored" % (section, inputName) ] return [1, "{0}: Failed to post-process - Unable to set {1} to ignored".format(section, inputName)]
logger.postprocess("Trying to snatch the next highest ranked release.", section) logger.postprocess("Trying to snatch the next highest ranked release.", section)
url = "%s/movie.searcher.try_next" % (baseURL) url = "{0}/movie.searcher.try_next".format(baseURL)
logger.debug("Opening URL: %s" % (url), section) logger.debug("Opening URL: {0}".format(url), section)
try: try:
r = requests.get(url, params={'media_id': media_id}, verify=False, timeout=(30, 600)) r = requests.get(url, params={'media_id': media_id}, verify=False, timeout=(30, 600))
except requests.ConnectionError: except requests.ConnectionError:
logger.error("Unable to open URL %s" % (url), section) logger.error("Unable to open URL {0}".format(url), section)
return [1, "%s: Failed to post-process - Unable to connect to %s" % (section, section) ] return [1, "{0}: Failed to post-process - Unable to connect to {1}".format(section, section)]
result = r.json() result = r.json()
if not r.status_code in [requests.codes.ok, requests.codes.created, requests.codes.accepted]: if r.status_code not in [requests.codes.ok, requests.codes.created, requests.codes.accepted]:
logger.error("Server returned status %s" % (str(r.status_code)), section) logger.error("Server returned status {0}".format(r.status_code), section)
return [1, "%s: Failed to post-process - Server returned status %s" % (section, str(r.status_code)) ] return [1, "{0}: Failed to post-process - Server returned status {1}".format(section, r.status_code)]
elif result['success']: elif result['success']:
logger.postprocess("SUCCESS: Snatched the next highest release ...", section) logger.postprocess("SUCCESS: Snatched the next highest release ...", section)
return [0, "%s: Successfully snatched next highest release" % (section) ] return [0, "{0}: Successfully snatched next highest release".format(section)]
else: else:
logger.postprocess("SUCCESS: Unable to find a new release to snatch now. CP will keep searching!", section) logger.postprocess("SUCCESS: Unable to find a new release to snatch now. CP will keep searching!", section)
return [0, "%s: No new release found now. %s will keep searching" % (section, section) ] return [0, "{0}: No new release found now. {1} will keep searching".format(section, section)]
# Added a releease that was not in the wanted list so confirm rename successful by finding this movie media.list. # Added a release that was not in the wanted list so confirm rename successful by finding this movie media.list.
if not release: if not release:
download_id = None # we don't want to filter new releases based on this. download_id = None # we don't want to filter new releases based on this.
# we will now check to see if CPS has finished renaming before returning to TorrentToMedia and unpausing. # we will now check to see if CPS has finished renaming before returning to TorrentToMedia and unpausing.
timeout = time.time() + 60 * wait_for timeout = time.time() + 60 * wait_for
while (time.time() < timeout): # only wait 2 (default) minutes, then return. while time.time() < timeout: # only wait 2 (default) minutes, then return.
logger.postprocess("Checking for status change, please stand by ...", section) logger.postprocess("Checking for status change, please stand by ...", section)
release = self.get_release(baseURL, imdbid, download_id, release_id) release = self.get_release(baseURL, imdbid, download_id, release_id)
if release: if release:
try: try:
if release_id is None and release_status_old is None: # we didn't have a release before, but now we do. if release_id is None and release_status_old is None: # we didn't have a release before, but now we do.
logger.postprocess("SUCCESS: Movie %s has now been added to CouchPotato" % (imdbid), section) logger.postprocess("SUCCESS: Movie {0} has now been added to CouchPotato".format(imdbid), section)
return [0, "%s: Successfully post-processed %s" % (section, inputName) ] return [0, "{0}: Successfully post-processed {1}".format(section, inputName)]
release_status_new = release[release_id]['status'] release_status_new = release[release_id]['status']
if release_status_new != release_status_old: if release_status_new != release_status_old:
logger.postprocess("SUCCESS: Release %s has now been marked with a status of [%s]" % ( logger.postprocess("SUCCESS: Release {0} has now been marked with a status of [{1}]".format(
inputName, str(release_status_new).upper()), section) inputName, str(release_status_new).upper()), section)
return [0, "%s: Successfully post-processed %s" % (section, inputName) ] return [0, "{0}: Successfully post-processed {1}".format(section, inputName)]
except: except:
pass pass
if not os.path.isdir(dirName): if not os.path.isdir(dirName):
logger.postprocess("SUCCESS: Input Directory [%s] has been processed and removed" % ( logger.postprocess("SUCCESS: Input Directory [{0}] has been processed and removed".format(
dirName), section) dirName), section)
return [0, "%s: Successfully post-processed %s" % (section, inputName) ] return [0, "{0}: Successfully post-processed {1}".format(section, inputName)]
elif not listMediaFiles(dirName, media=True, audio=False, meta=False, archives=True): elif not listMediaFiles(dirName, media=True, audio=False, meta=False, archives=True):
logger.postprocess("SUCCESS: Input Directory [%s] has no remaining media files. This has been fully processed." % ( logger.postprocess("SUCCESS: Input Directory [{0}] has no remaining media files. This has been fully processed.".format(
dirName), section) dirName), section)
return [0, "%s: Successfully post-processed %s" % (section, inputName) ] return [0, "{0}: Successfully post-processed {1}".format(section, inputName)]
# pause and let CouchPotatoServer catch its breath # pause and let CouchPotatoServer catch its breath
time.sleep(10 * wait_for) time.sleep(10 * wait_for)
# The status hasn't changed. we have waited 2 minutes which is more than enough. uTorrent can resule seeding now. # The status hasn't changed. we have waited 2 minutes which is more than enough. uTorrent can resume seeding now.
logger.warning( logger.warning(
"%s does not appear to have changed status after %s minutes, Please check your logs." % (inputName, wait_for), "{0} does not appear to have changed status after {1} minutes, Please check your logs.".format(inputName, wait_for),
section) section)
return [1, "%s: Failed to post-process - No change in status" % (section) ] return [1, "{0}: Failed to post-process - No change in status".format(section)]

View file

@ -1,3 +1,5 @@
# coding=utf-8
import os import os
import time import time
import requests import requests
@ -9,29 +11,33 @@ from core import logger
requests.packages.urllib3.disable_warnings() requests.packages.urllib3.disable_warnings()
class autoProcessMusic:
class autoProcessMusic(object):
def get_status(self, url, apikey, dirName): def get_status(self, url, apikey, dirName):
logger.debug("Attempting to get current status for release:%s" % (os.path.basename(dirName))) logger.debug("Attempting to get current status for release:{0}".format(os.path.basename(dirName)))
params = {} params = {
params['apikey'] = apikey 'apikey': apikey,
params['cmd'] = "getHistory" 'cmd': "getHistory"
}
logger.debug("Opening URL: %s with PARAMS: %s" % (url, params)) logger.debug("Opening URL: {0} with PARAMS: {1}".format(url, params))
try: try:
r = requests.get(url, params=params, verify=False, timeout=(30, 120)) r = requests.get(url, params=params, verify=False, timeout=(30, 120))
except Exception, e: except requests.RequestException:
logger.error("Unable to open URL") logger.error("Unable to open URL")
return None return None
try: try:
result = r.json() result = r.json()
except ValueError:
# ValueError catches simplejson's JSONDecodeError and json's ValueError
return None
for album in result: for album in result:
if os.path.basename(dirName) == album['FolderName']: if os.path.basename(dirName) == album['FolderName']:
return album["Status"].lower() return album["Status"].lower()
except:
return None
def process(self, section, dirName, inputName=None, status=0, clientAgent="manual", inputCategory=None): def process(self, section, dirName, inputName=None, status=0, clientAgent="manual", inputCategory=None):
status = int(status) status = int(status)
@ -40,34 +46,16 @@ class autoProcessMusic:
port = core.CFG[section][inputCategory]["port"] port = core.CFG[section][inputCategory]["port"]
apikey = core.CFG[section][inputCategory]["apikey"] apikey = core.CFG[section][inputCategory]["apikey"]
wait_for = int(core.CFG[section][inputCategory]["wait_for"]) wait_for = int(core.CFG[section][inputCategory]["wait_for"])
ssl = int(core.CFG[section][inputCategory].get("ssl", 0))
web_root = core.CFG[section][inputCategory].get("web_root", "")
remote_path = int(core.CFG[section][inputCategory].get("remote_path", 0))
extract = int(section[inputCategory].get("extract", 0))
protocol = "https://" if ssl else "http://"
try: url = "{0}{1}:{2}{3}/api".format(protocol, host, port, web_root)
ssl = int(core.CFG[section][inputCategory]["ssl"])
except:
ssl = 0
try:
web_root = core.CFG[section][inputCategory]["web_root"]
except:
web_root = ""
try:
remote_path = int(core.CFG[section][inputCategory]["remote_path"])
except:
remote_path = 0
try:
extract = int(section[inputCategory]["extract"])
except:
extract = 0
if ssl:
protocol = "https://"
else:
protocol = "http://"
url = "%s%s:%s%s/api" % (protocol,host,port,web_root)
if not server_responding(url): if not server_responding(url):
logger.error("Server did not respond. Exiting", section) logger.error("Server did not respond. Exiting", section)
return [1, "%s: Failed to post-process - %s did not respond." % (section, section) ] return [1, "{0}: Failed to post-process - {1} did not respond.".format(section, section)]
if not os.path.isdir(dirName) and os.path.isfile(dirName): # If the input directory is a file, assume single file download and split dir/name. if not os.path.isdir(dirName) and os.path.isfile(dirName): # If the input directory is a file, assume single file download and split dir/name.
dirName = os.path.split(os.path.normpath(dirName))[0] dirName = os.path.split(os.path.normpath(dirName))[0]
@ -83,63 +71,61 @@ class autoProcessMusic:
inputName, dirName = convert_to_ascii(inputName, dirName) inputName, dirName = convert_to_ascii(inputName, dirName)
if not listMediaFiles(dirName, media=False, audio=True, meta=False, archives=False) and listMediaFiles(dirName, media=False, audio=False, meta=False, archives=True) and extract: if not listMediaFiles(dirName, media=False, audio=True, meta=False, archives=False) and listMediaFiles(dirName, media=False, audio=False, meta=False, archives=True) and extract:
logger.debug('Checking for archives to extract in directory: %s' % (dirName)) logger.debug('Checking for archives to extract in directory: {0}'.format(dirName))
core.extractFiles(dirName) core.extractFiles(dirName)
inputName, dirName = convert_to_ascii(inputName, dirName) inputName, dirName = convert_to_ascii(inputName, dirName)
if listMediaFiles(dirName, media=False, audio=True, meta=False, archives=False) and status: if listMediaFiles(dirName, media=False, audio=True, meta=False, archives=False) and status:
logger.info("Status shown as failed from Downloader, but %s valid video files found. Setting as successful." % (str(good_files)), section) logger.info("Status shown as failed from Downloader, but valid video files found. Setting as successful.", section)
status = 0 status = 0
if status == 0: if status == 0:
params = {} params = {
params['apikey'] = apikey 'apikey': apikey,
params['cmd'] = "forceProcess" 'cmd': "forceProcess",
'dir': remoteDir(os.path.dirname(dirName)) if remote_path else os.path.dirname(dirName)
params['dir'] = os.path.dirname(dirName) }
if remote_path:
params['dir'] = remoteDir(os.path.dirname(dirName))
release_status = self.get_status(url, apikey, dirName) release_status = self.get_status(url, apikey, dirName)
if not release_status: if not release_status:
logger.error("Could not find a status for %s, is it in the wanted list ?" % (inputName),section) logger.error("Could not find a status for {0}, is it in the wanted list ?".format(inputName), section)
logger.debug("Opening URL: %s with PARAMS: %s" % (url, params), section) logger.debug("Opening URL: {0} with PARAMS: {1}".format(url, params), section)
try: try:
r = requests.get(url, params=params, verify=False, timeout=(30, 300)) r = requests.get(url, params=params, verify=False, timeout=(30, 300))
except requests.ConnectionError: except requests.ConnectionError:
logger.error("Unable to open URL %s" % (url) ,section) logger.error("Unable to open URL {0}".format(url), section)
return [1, "%s: Failed to post-process - Unable to connect to %s" % (section, section) ] return [1, "{0}: Failed to post-process - Unable to connect to {1}".format(section, section)]
logger.debug("Result: %s" % (r.text),section) logger.debug("Result: {0}".format(r.text), section)
if not r.status_code in [requests.codes.ok, requests.codes.created, requests.codes.accepted]: if r.status_code not in [requests.codes.ok, requests.codes.created, requests.codes.accepted]:
logger.error("Server returned status %s" % (str(r.status_code)), section) logger.error("Server returned status {0}".format(r.status_code), section)
return [1, "%s: Failed to post-process - Server returned status %s" % (section, str(r.status_code)) ] return [1, "{0}: Failed to post-process - Server returned status {1}".format(section, r.status_code)]
elif r.text == "OK": elif r.text == "OK":
logger.postprocess("SUCCESS: Post-Processing started for %s in folder %s ..." % (inputName, dirName),section) logger.postprocess("SUCCESS: Post-Processing started for {0} in folder {1} ...".format(inputName, dirName), section)
else: else:
logger.error("FAILED: Post-Processing has NOT started for %s in folder %s. exiting!" % (inputName, dirName),section) logger.error("FAILED: Post-Processing has NOT started for {0} in folder {1}. exiting!".format(inputName, dirName), section)
return [1, "%s: Failed to post-process - Returned log from %s was not as expected." % (section, section) ] return [1, "{0}: Failed to post-process - Returned log from {1} was not as expected.".format(section, section)]
else: else:
logger.warning("FAILED DOWNLOAD DETECTED", section) logger.warning("FAILED DOWNLOAD DETECTED", section)
return [1, "%s: Failed to post-process. %s does not support failed downloads" % (section, section) ] return [1, "{0}: Failed to post-process. {1} does not support failed downloads".format(section, section)]
# we will now wait for this album to be processed before returning to TorrentToMedia and unpausing. # we will now wait for this album to be processed before returning to TorrentToMedia and unpausing.
timeout = time.time() + 60 * wait_for timeout = time.time() + 60 * wait_for
while (time.time() < timeout): while time.time() < timeout:
current_status = self.get_status(url, apikey, dirName) current_status = self.get_status(url, apikey, dirName)
if current_status is not None and current_status != release_status: # Something has changed. CPS must have processed this movie. if current_status is not None and current_status != release_status: # Something has changed. CPS must have processed this movie.
logger.postprocess("SUCCESS: This release is now marked as status [%s]" % (current_status),section) logger.postprocess("SUCCESS: This release is now marked as status [{0}]".format(current_status), section)
return [0, "%s: Successfully post-processed %s" % (section, inputName) ] return [0, "{0}: Successfully post-processed {1}".format(section, inputName)]
if not os.path.isdir(dirName): if not os.path.isdir(dirName):
logger.postprocess("SUCCESS: The input directory %s has been removed Processing must have finished." % (dirName),section) logger.postprocess("SUCCESS: The input directory {0} has been removed Processing must have finished.".format(dirName), section)
return [0, "%s: Successfully post-processed %s" % (section, inputName) ] return [0, "{0}: Successfully post-processed {1}".format(section, inputName)]
time.sleep(10 * wait_for) time.sleep(10 * wait_for)
# The status hasn't changed. uTorrent can resume seeding now. # The status hasn't changed. uTorrent can resume seeding now.
logger.warning("The music album does not appear to have changed status after %s minutes. Please check your Logs" % (wait_for),section) logger.warning("The music album does not appear to have changed status after {0} minutes. Please check your Logs".format(wait_for), section)
return [1, "%s: Failed to post-process - No change in wanted status" % (section) ] return [1, "{0}: Failed to post-process - No change in wanted status".format(section)]

View file

@ -1,3 +1,5 @@
# coding=utf-8
import copy import copy
import os import os
import time import time
@ -14,106 +16,66 @@ from core.transcoder import transcoder
requests.packages.urllib3.disable_warnings() requests.packages.urllib3.disable_warnings()
class autoProcessTV:
class autoProcessTV(object):
def command_complete(self, url, params, headers, section): def command_complete(self, url, params, headers, section):
r = None
try: try:
r = requests.get(url, params=params, headers=headers, stream=True, verify=False, timeout=(30, 60)) r = requests.get(url, params=params, headers=headers, stream=True, verify=False, timeout=(30, 60))
except requests.ConnectionError: except requests.ConnectionError:
logger.error("Unable to open URL: %s" % (url1), section) logger.error("Unable to open URL: {0}".format(url), section)
return None return None
if not r.status_code in [requests.codes.ok, requests.codes.created, requests.codes.accepted]: if r.status_code not in [requests.codes.ok, requests.codes.created, requests.codes.accepted]:
logger.error("Server returned status %s" % (str(r.status_code)), section) logger.error("Server returned status {0}".format(r.status_code), section)
return None return None
else: else:
try: try:
res = json.loads(r.content) return r.json()['state']
return res['state'] except (ValueError, KeyError):
except: # ValueError catches simplejson's JSONDecodeError and json's ValueError
logger.error("%s did not return expected json data." % section, section) logger.error("{0} did not return expected json data.".format(section), section)
return None return None
def CDH(self, url2, headers): def CDH(self, url2, headers, section="MAIN"):
r = None
try: try:
r = requests.get(url2, params={}, headers=headers, stream=True, verify=False, timeout=(30, 60)) r = requests.get(url2, params={}, headers=headers, stream=True, verify=False, timeout=(30, 60))
except requests.ConnectionError: except requests.ConnectionError:
logger.error("Unable to open URL: %s" % (url2), section) logger.error("Unable to open URL: {0}".format(url2), section)
return False return False
if not r.status_code in [requests.codes.ok, requests.codes.created, requests.codes.accepted]: if r.status_code not in [requests.codes.ok, requests.codes.created, requests.codes.accepted]:
logger.error("Server returned status %s" % (str(r.status_code)), section) logger.error("Server returned status {0}".format(r.status_code), section)
return False return False
else: else:
try: try:
res = json.loads(r.content) return r.json().get("enableCompletedDownloadHandling", False)
return res["enableCompletedDownloadHandling"] except ValueError:
except: # ValueError catches simplejson's JSONDecodeError and json's ValueError
return False return False
def processEpisode(self, section, dirName, inputName=None, failed=False, clientAgent = "manual", download_id=None, inputCategory=None, failureLink=None): def processEpisode(self, section, dirName, inputName=None, failed=False, clientAgent="manual", download_id=None, inputCategory=None, failureLink=None):
host = core.CFG[section][inputCategory]["host"] host = core.CFG[section][inputCategory]["host"]
port = core.CFG[section][inputCategory]["port"] port = core.CFG[section][inputCategory]["port"]
try: ssl = int(core.CFG[section][inputCategory].get("ssl", 0))
ssl = int(core.CFG[section][inputCategory]["ssl"]) web_root = core.CFG[section][inputCategory].get("web_root", "")
except: protocol = "https://" if ssl else "http://"
ssl = 0
if ssl: if not server_responding("{0}{1}:{2}{3}".format(protocol, host, port, web_root)):
protocol = "https://"
else:
protocol = "http://"
try:
web_root = core.CFG[section][inputCategory]["web_root"]
except:
web_root = ""
if not server_responding("%s%s:%s%s" % (protocol,host,port,web_root)):
logger.error("Server did not respond. Exiting", section) logger.error("Server did not respond. Exiting", section)
return [1, "%s: Failed to post-process - %s did not respond." % (section, section) ] return [1, "{0}: Failed to post-process - {1} did not respond.".format(section, section)]
# auto-detect correct fork # auto-detect correct fork
fork, fork_params = autoFork(section, inputCategory) fork, fork_params = autoFork(section, inputCategory)
try: username = core.CFG[section][inputCategory].get("username", "")
username = core.CFG[section][inputCategory]["username"] password = core.CFG[section][inputCategory].get("password", "")
password = core.CFG[section][inputCategory]["password"] apikey = core.CFG[section][inputCategory].get("apikey", "")
except: delete_failed = int(core.CFG[section][inputCategory].get("delete_failed", 0))
username = "" nzbExtractionBy = core.CFG[section][inputCategory].get("nzbExtractionBy", "Downloader")
password = "" process_method = core.CFG[section][inputCategory].get("process_method")
try: remote_path = int(core.CFG[section][inputCategory].get("remote_path", 0))
apikey = core.CFG[section][inputCategory]["apikey"] wait_for = int(core.CFG[section][inputCategory].get("wait_for", 2))
except: force = int(core.CFG[section][inputCategory].get("force", 0))
apikey = "" delete_on = int(core.CFG[section][inputCategory].get("delete_on", 0))
try: extract = int(section[inputCategory].get("extract", 0))
delete_failed = int(core.CFG[section][inputCategory]["delete_failed"])
except:
delete_failed = 0
try:
nzbExtractionBy = core.CFG[section][inputCategory]["nzbExtractionBy"]
except:
nzbExtractionBy = "Downloader"
try:
process_method = core.CFG[section][inputCategory]["process_method"]
except:
process_method = None
try:
remote_path = int(core.CFG[section][inputCategory]["remote_path"])
except:
remote_path = 0
try:
wait_for = int(core.CFG[section][inputCategory]["wait_for"])
except:
wait_for = 2
try:
force = int(core.CFG[section][inputCategory]["force"])
except:
force = 0
try:
delete_on = int(core.CFG[section][inputCategory]["delete_on"])
except:
delete_on = 0
try:
extract = int(section[inputCategory]["extract"])
except:
extract = 0
if not os.path.isdir(dirName) and os.path.isfile(dirName): # If the input directory is a file, assume single file download and split dir/name. if not os.path.isdir(dirName) and os.path.isfile(dirName): # If the input directory is a file, assume single file download and split dir/name.
dirName = os.path.split(os.path.normpath(dirName))[0] dirName = os.path.split(os.path.normpath(dirName))[0]
@ -130,12 +92,12 @@ class autoProcessTV:
# won't process the directory because it doesn't exist. # won't process the directory because it doesn't exist.
try: try:
os.makedirs(dirName) # Attempt to create the directory os.makedirs(dirName) # Attempt to create the directory
except OSError, e: except OSError as e:
# Re-raise the error if it wasn't about the directory not existing # Re-raise the error if it wasn't about the directory not existing
if e.errno != errno.EEXIST: if e.errno != errno.EEXIST:
raise raise
if not 'process_method' in fork_params or (clientAgent in ['nzbget','sabnzbd'] and nzbExtractionBy != "Destination"): if 'process_method' not in fork_params or (clientAgent in ['nzbget', 'sabnzbd'] and nzbExtractionBy != "Destination"):
if inputName: if inputName:
process_all_exceptions(inputName, dirName) process_all_exceptions(inputName, dirName)
inputName, dirName = convert_to_ascii(inputName, dirName) inputName, dirName = convert_to_ascii(inputName, dirName)
@ -143,7 +105,7 @@ class autoProcessTV:
# Now check if tv files exist in destination. # Now check if tv files exist in destination.
if not listMediaFiles(dirName, media=True, audio=False, meta=False, archives=False): if not listMediaFiles(dirName, media=True, audio=False, meta=False, archives=False):
if listMediaFiles(dirName, media=False, audio=False, meta=False, archives=True) and extract: if listMediaFiles(dirName, media=False, audio=False, meta=False, archives=True) and extract:
logger.debug('Checking for archives to extract in directory: %s' % (dirName)) logger.debug('Checking for archives to extract in directory: {0}'.format(dirName))
core.extractFiles(dirName) core.extractFiles(dirName)
inputName, dirName = convert_to_ascii(inputName, dirName) inputName, dirName = convert_to_ascii(inputName, dirName)
@ -168,12 +130,12 @@ class autoProcessTV:
logger.info('Found corrupt videos. Setting status Failed') logger.info('Found corrupt videos. Setting status Failed')
status = 1 status = 1
failed = 1 failed = 1
if os.environ.has_key('NZBOP_VERSION') and os.environ['NZBOP_VERSION'][0:5] >= '14.0': if 'NZBOP_VERSION' in os.environ and os.environ['NZBOP_VERSION'][0:5] >= '14.0':
print('[NZB] MARK=BAD') print('[NZB] MARK=BAD')
if failureLink: if failureLink:
failureLink = failureLink + '&corrupt=true' failureLink += '&corrupt=true'
elif clientAgent == "manual": elif clientAgent == "manual":
logger.warning("No media files found in directory %s to manually process." % (dirName), section) logger.warning("No media files found in directory {0} to manually process.".format(dirName), section)
return [0, ""] # Success (as far as this script is concerned) return [0, ""] # Success (as far as this script is concerned)
elif nzbExtractionBy == "Destination": elif nzbExtractionBy == "Destination":
logger.info("Check for media files ignored because nzbExtractionBy is set to Destination.") logger.info("Check for media files ignored because nzbExtractionBy is set to Destination.")
@ -186,20 +148,20 @@ class autoProcessTV:
status = 1 status = 1
failed = 1 failed = 1
else: else:
logger.warning("No media files found in directory %s. Processing this as a failed download" % (dirName), section) logger.warning("No media files found in directory {0}. Processing this as a failed download".format(dirName), section)
status = 1 status = 1
failed = 1 failed = 1
if os.environ.has_key('NZBOP_VERSION') and os.environ['NZBOP_VERSION'][0:5] >= '14.0': if 'NZBOP_VERSION' in os.environ and os.environ['NZBOP_VERSION'][0:5] >= '14.0':
print('[NZB] MARK=BAD') print('[NZB] MARK=BAD')
if status == 0 and core.TRANSCODE == 1: # only transcode successful downloads if status == 0 and core.TRANSCODE == 1: # only transcode successful downloads
result, newDirName = transcoder.Transcode_directory(dirName) result, newDirName = transcoder.Transcode_directory(dirName)
if result == 0: if result == 0:
logger.debug("SUCCESS: Transcoding succeeded for files in %s" % (dirName), section) logger.debug("SUCCESS: Transcoding succeeded for files in {0}".format(dirName), section)
dirName = newDirName dirName = newDirName
else: else:
logger.error("FAILED: Transcoding failed for files in %s" % (dirName), section) logger.error("FAILED: Transcoding failed for files in {0}".format(dirName), section)
return [1, "%s: Failed to post-process - Transcoding failed" % (section) ] return [1, "{0}: Failed to post-process - Transcoding failed".format(section)]
# configure SB params to pass # configure SB params to pass
fork_params['quiet'] = 1 fork_params['quiet'] = 1
@ -234,7 +196,7 @@ class autoProcessTV:
del fork_params[param] del fork_params[param]
# delete any unused params so we don't pass them to SB by mistake # delete any unused params so we don't pass them to SB by mistake
[fork_params.pop(k) for k,v in fork_params.items() if v is None] [fork_params.pop(k) for k, v in fork_params.items() if v is None]
if status == 0: if status == 0:
logger.postprocess("SUCCESS: The download succeeded, sending a post-process request", section) logger.postprocess("SUCCESS: The download succeeded, sending a post-process request", section)
@ -243,30 +205,30 @@ class autoProcessTV:
if failureLink: if failureLink:
reportNzb(failureLink, clientAgent) reportNzb(failureLink, clientAgent)
if 'failed' in fork_params: if 'failed' in fork_params:
logger.postprocess("FAILED: The download failed. Sending 'failed' process request to %s branch" % (fork), section) logger.postprocess("FAILED: The download failed. Sending 'failed' process request to {0} branch".format(fork), section)
elif section == "NzbDrone": elif section == "NzbDrone":
logger.postprocess("FAILED: The download failed. Sending failed download to %s for CDH processing" % (fork), section) logger.postprocess("FAILED: The download failed. Sending failed download to {0} for CDH processing".format(fork), section)
return [1, "%s: Downlaod Failed. Sending back to %s" % (section, section) ] # Return as failed to flag this in the downloader. return [1, "{0}: Downlaod Failed. Sending back to {1}".format(section, section)] # Return as failed to flag this in the downloader.
else: else:
logger.postprocess("FAILED: The download failed. %s branch does not handle failed downloads. Nothing to process" % (fork), section) logger.postprocess("FAILED: The download failed. {0} branch does not handle failed downloads. Nothing to process".format(fork), section)
if delete_failed and os.path.isdir(dirName) and not os.path.dirname(dirName) == dirName: if delete_failed and os.path.isdir(dirName) and not os.path.dirname(dirName) == dirName:
logger.postprocess("Deleting failed files and folder %s" % (dirName), section) logger.postprocess("Deleting failed files and folder {0}".format(dirName), section)
rmDir(dirName) rmDir(dirName)
return [1, "%s: Failed to post-process. %s does not support failed downloads" % (section, section) ] # Return as failed to flag this in the downloader. return [1, "{0}: Failed to post-process. {1} does not support failed downloads".format(section, section)] # Return as failed to flag this in the downloader.
url = None url = None
if section == "SickBeard": if section == "SickBeard":
url = "%s%s:%s%s/home/postprocess/processEpisode" % (protocol,host,port,web_root) url = "{0}{1}:{2}{3}/home/postprocess/processEpisode".format(protocol, host, port, web_root)
elif section == "NzbDrone": elif section == "NzbDrone":
url = "%s%s:%s%s/api/command" % (protocol, host, port, web_root) url = "{0}{1}:{2}{3}/api/command".format(protocol, host, port, web_root)
url2 = "%s%s:%s%s/api/config/downloadClient" % (protocol, host, port, web_root) url2 = "{0}{1}:{2}{3}/api/config/downloadClient".format(protocol, host, port, web_root)
headers = {"X-Api-Key": apikey} headers = {"X-Api-Key": apikey}
params = {'sortKey': 'series.title', 'page': 1, 'pageSize': 1, 'sortDir': 'asc'} # params = {'sortKey': 'series.title', 'page': 1, 'pageSize': 1, 'sortDir': 'asc'}
if remote_path: if remote_path:
logger.debug("remote_path: %s" % (remoteDir(dirName)),section) logger.debug("remote_path: {0}".format(remoteDir(dirName)), section)
data = {"name": "DownloadedEpisodesScan", "path": remoteDir(dirName), "downloadClientId": download_id} data = {"name": "DownloadedEpisodesScan", "path": remoteDir(dirName), "downloadClientId": download_id}
else: else:
logger.debug("path: %s" % (dirName),section) logger.debug("path: {0}".format(dirName), section)
data = {"name": "DownloadedEpisodesScan", "path": dirName, "downloadClientId": download_id} data = {"name": "DownloadedEpisodesScan", "path": dirName, "downloadClientId": download_id}
if not download_id: if not download_id:
data.pop("downloadClientId") data.pop("downloadClientId")
@ -274,31 +236,29 @@ class autoProcessTV:
try: try:
if section == "SickBeard": if section == "SickBeard":
logger.debug("Opening URL: %s with params: %s" % (url, str(fork_params)), section) logger.debug("Opening URL: {0} with params: {1}".format(url, fork_params), section)
r = None
s = requests.Session() s = requests.Session()
login = "%s%s:%s%s/login" % (protocol,host,port,web_root) login = "{0}{1}:{2}{3}/login".format(protocol, host, port, web_root)
login_params = {'username': username, 'password': password} login_params = {'username': username, 'password': password}
s.post(login, data=login_params, stream=True, verify=False, timeout=(30, 60)) s.post(login, data=login_params, stream=True, verify=False, timeout=(30, 60))
r = s.get(url, auth=(username, password), params=fork_params, stream=True, verify=False, timeout=(30, 1800)) r = s.get(url, auth=(username, password), params=fork_params, stream=True, verify=False, timeout=(30, 1800))
elif section == "NzbDrone": elif section == "NzbDrone":
logger.debug("Opening URL: %s with data: %s" % (url, str(data)), section) logger.debug("Opening URL: {0} with data: {1}".format(url, data), section)
r = None
r = requests.post(url, data=data, headers=headers, stream=True, verify=False, timeout=(30, 1800)) r = requests.post(url, data=data, headers=headers, stream=True, verify=False, timeout=(30, 1800))
except requests.ConnectionError: except requests.ConnectionError:
logger.error("Unable to open URL: %s" % (url), section) logger.error("Unable to open URL: {0}".format(url), section)
return [1, "%s: Failed to post-process - Unable to connect to %s" % (section, section) ] return [1, "{0}: Failed to post-process - Unable to connect to {1}".format(section, section)]
if not r.status_code in [requests.codes.ok, requests.codes.created, requests.codes.accepted]: if r.status_code not in [requests.codes.ok, requests.codes.created, requests.codes.accepted]:
logger.error("Server returned status %s" % (str(r.status_code)), section) logger.error("Server returned status {0}".format(r.status_code), section)
return [1, "%s: Failed to post-process - Server returned status %s" % (section, str(r.status_code)) ] return [1, "{0}: Failed to post-process - Server returned status {1}".format(section, r.status_code)]
Success = False Success = False
Started = False Started = False
if section == "SickBeard": if section == "SickBeard":
for line in r.iter_lines(): for line in r.iter_lines():
if line: if line:
logger.postprocess("%s" % (line), section) logger.postprocess("{0}".format(line), section)
if "Moving file from" in line: if "Moving file from" in line:
inputName = os.path.split(line)[1] inputName = os.path.split(line)[1]
if "Processing succeeded" in line or "Successfully processed" in line: if "Processing succeeded" in line or "Successfully processed" in line:
@ -307,23 +267,23 @@ class autoProcessTV:
try: try:
res = json.loads(r.content) res = json.loads(r.content)
scan_id = int(res['id']) scan_id = int(res['id'])
logger.debug("Scan started with id: %s" % (str(scan_id)), section) logger.debug("Scan started with id: {0}".format(scan_id), section)
Started = True Started = True
except Exception as e: except Exception as e:
logger.warning("No scan id was returned due to: %s" % (e), section) logger.warning("No scan id was returned due to: {0}".format(e), section)
scan_id = None scan_id = None
Started = False Started = False
if status != 0 and delete_failed and not os.path.dirname(dirName) == dirName: if status != 0 and delete_failed and not os.path.dirname(dirName) == dirName:
logger.postprocess("Deleting failed files and folder %s" % (dirName),section) logger.postprocess("Deleting failed files and folder {0}".format(dirName), section)
rmDir(dirName) rmDir(dirName)
if Success: if Success:
return [0, "%s: Successfully post-processed %s" % (section, inputName) ] return [0, "{0}: Successfully post-processed {1}".format(section, inputName)]
elif section == "NzbDrone" and Started: elif section == "NzbDrone" and Started:
n = 0 n = 0
params = {} params = {}
url = url + "/" + str(scan_id) url = "{0}/{1}".format(url, scan_id)
while n < 6: # set up wait_for minutes to see if command completes.. while n < 6: # set up wait_for minutes to see if command completes..
time.sleep(10 * wait_for) time.sleep(10 * wait_for)
command_status = self.command_complete(url, params, headers, section) command_status = self.command_complete(url, params, headers, section)
@ -331,21 +291,21 @@ class autoProcessTV:
break break
n += 1 n += 1
if command_status: if command_status:
logger.debug("The Scan command return status: %s" % (command_status), section) logger.debug("The Scan command return status: {0}".format(command_status), section)
if not os.path.exists(dirName): if not os.path.exists(dirName):
logger.debug("The directory %s has been removed. Renaming was successful." % (dirName), section) logger.debug("The directory {0} has been removed. Renaming was successful.".format(dirName), section)
return [0, "%s: Successfully post-processed %s" % (section, inputName) ] return [0, "{0}: Successfully post-processed {1}".format(section, inputName)]
elif command_status and command_status in ['completed']: elif command_status and command_status in ['completed']:
logger.debug("The Scan command has completed successfully. Renaming was successful.", section) logger.debug("The Scan command has completed successfully. Renaming was successful.", section)
return [0, "%s: Successfully post-processed %s" % (section, inputName) ] return [0, "{0}: Successfully post-processed {1}".format(section, inputName)]
elif command_status and command_status in ['failed']: elif command_status and command_status in ['failed']:
logger.debug("The Scan command has failed. Renaming was not successful.", section) logger.debug("The Scan command has failed. Renaming was not successful.", section)
#return [1, "%s: Failed to post-process %s" % (section, inputName) ] # return [1, "%s: Failed to post-process %s" % (section, inputName) ]
if self.CDH(url2, headers): if self.CDH(url2, headers, section=section):
logger.debug("The Scan command did not return status completed, but complete Download Handling is enabled. Passing back to %s." % (section), section) logger.debug("The Scan command did not return status completed, but complete Download Handling is enabled. Passing back to {0}.".format(section), section)
return [status, "%s: Complete DownLoad Handling is enabled. Passing back to %s" % (section, section) ] return [status, "{0}: Complete DownLoad Handling is enabled. Passing back to {1}".format(section, section)]
else: else:
logger.warning("The Scan command did not return a valid status. Renaming was not successful.", section) logger.warning("The Scan command did not return a valid status. Renaming was not successful.", section)
return [1, "%s: Failed to post-process %s" % (section, inputName) ] return [1, "{0}: Failed to post-process {1}".format(section, inputName)]
else: else:
return [1, "%s: Failed to post-process - Returned log from %s was not as expected." % (section, section) ] # We did not receive Success confirmation. return [1, "{0}: Failed to post-process - Returned log from {1} was not as expected.".format(section, section)] # We did not receive Success confirmation.