Skip to content

Commit

Permalink
Fix for issue #142
Browse files Browse the repository at this point in the history
  • Loading branch information
dagalufh committed Apr 10, 2016
1 parent 2de175d commit a661d9b
Show file tree
Hide file tree
Showing 6 changed files with 228 additions and 36 deletions.
Binary file modified Contents/Code/Docs/webtools-README_DEVS.odt
Binary file not shown.
6 changes: 3 additions & 3 deletions Contents/Code/findMedia.py
Original file line number Diff line number Diff line change
Expand Up @@ -102,7 +102,7 @@ def reqprocessPost(self, req):

# Set settings
def setSetting(self, req):
print 'Ged'
# print 'Ged'
try:
key = req.get_argument('key', 'missing')
if key == 'missing':
Expand All @@ -119,7 +119,7 @@ def setSetting(self, req):
req.set_status(412)
req.finish("Missing value parameter")

print 'Ged2', value
# print 'Ged2', value

Dict['findMedia'][key] = value
Dict.Save()
Expand Down Expand Up @@ -215,7 +215,7 @@ def scanMedias(sectionNumber, sectionLocations, sectionType, req):
global statusMsg
global retMsg

print 'Ged Type', sectionType
# print 'Ged Type', sectionType
if sectionType == 'movie':
scanMovieDb(sectionNumber=sectionNumber)
elif sectionType == 'show':
Expand Down
138 changes: 108 additions & 30 deletions Contents/Code/git.py
Original file line number Diff line number Diff line change
Expand Up @@ -12,6 +12,7 @@
import io, os, shutil
import plistlib
import pms
import tempfile

class git(object):
# Defaults used by the rest of the class
Expand Down Expand Up @@ -480,15 +481,24 @@ def install(self, req):
''' Grap bundle name '''
def grapBundleName(url):
gitName = url.rsplit('/', 1)[-1]

# Forgot to name git to end with .bundle?
if not gitName.endswith('.bundle'):
gitName = gitName + '.bundle'
bundleInfo = Dict['PMS-AllBundleInfo'].get(url, {})

if bundleInfo.get('bundle'):
# Use bundle name from plugin details
gitName = bundleInfo['bundle']
else:
# Fallback to just appending ".bundle" to the repository name
gitName = gitName + '.bundle'

gitName = Core.storage.join_path(self.PLUGIN_DIR, gitName)
Log.Debug('Bundle directory name digested as: %s' %(gitName))
return gitName

''' Save Install info to the dict '''
def saveInstallInfo(url, bundleName):
def saveInstallInfo(url, bundleName, branch):
# If this is WebTools itself, then don't save
if 'WebTools.bundle' in bundleName:
return
Expand All @@ -510,6 +520,7 @@ def saveInstallInfo(url, bundleName):
if url.upper() == git['repo'].upper():
key = git['repo']
del git['repo']
git['branch'] = branch
git['date'] = datetime.datetime.now().strftime("%Y-%m-%d %H:%M:%S")
Dict['installed'][key] = git
bNotInUAS = False
Expand All @@ -523,10 +534,10 @@ def saveInstallInfo(url, bundleName):
pFile = Core.storage.join_path(self.PLUGIN_DIR, bundleName, 'Contents', 'Info.plist')
pl = plistlib.readPlist(pFile)
git = {}
git['title'] = bundleName[bundleName.rfind("/"):][1:][:-7]
git['title'] = os.path.basename(bundleName)[:-7]
git['description'] = ''
git['branch'] = ''
git['bundle'] = bundleName[bundleName.rfind("/"):][1:]
git['branch'] = branch
git['bundle'] = os.path.basename(bundleName)
git['identifier'] = pl['CFBundleIdentifier']
git['type'] = ['Unknown']
git['icon'] = ''
Expand Down Expand Up @@ -575,11 +586,8 @@ def removeEmptyFolders(path, removeRoot=True):
# Make sure it's actually a bundle channel
bError = True
bUpgrade = False
instFiles = []
try:
for filename in zipfile:
# Make a list of all files and dirs in the zip
instFiles.append(filename)
if '/Contents/Info.plist' in filename:
pos = filename.find('/Contents/')
cutStr = filename[:pos]
Expand Down Expand Up @@ -621,53 +629,110 @@ def removeEmptyFolders(path, removeRoot=True):
shutil.rmtree(DataDir)
else:
Log.Info('Keeping the Data directory ' + DataDir)
# It's an upgrade, so we need to store a list of files that we install here
newFiles = []
for fileName in instFiles:
newFiles.append(fileName.replace(cutStr, ''))

if bError:
Core.storage.remove_tree(Core.storage.join_path(self.PLUGIN_DIR, bundleName))
Log.Debug('The bundle downloaded is not a Plex Channel bundle!')
raise ValueError('The bundle downloaded is not a Plex Channel bundle!')
bError = False
if not bUpgrade:
presentFiles = []
presentFiles = []

# Create temporary directory
tempDir = tempfile.mkdtemp(prefix='wt-')
extractDir = os.path.join(tempDir, os.path.basename(bundleName))

Log.Info('Extracting plugin to: %r', extractDir)

# Extract archive into temporary directory
for filename in zipfile:
# Walk contents of the zip, and extract as needed
data = zipfile[filename]

if not str(filename).endswith('/'):
if cutStr not in filename:
continue

# Pure file, so save it
path = self.getSavePath(bundleName, filename.replace(cutStr, ''))
Log.Debug('Extracting file' + path)
path = extractDir + filename.replace(cutStr, '')
Log.Debug('Extracting file: ' + path)
try:
Core.storage.save(path, data)
except Exception, e:
bError = True
Log.Critical('Exception happend in downloadBundle2tmp: ' + str(e))
else:
if cutStr not in filename:
continue

# We got a directory here
Log.Debug(filename.split('/')[-2])
if not str(filename.split('/')[-2]).startswith('.'):
# Not hidden, so let's create it
path = self.getSavePath(bundleName, filename.replace(cutStr, ''))
Log.Debug('Extracting folder ' + path)
path = extractDir + filename.replace(cutStr, '')
Log.Debug('Extracting folder: ' + path)
try:
Core.storage.ensure_dirs(path)
except Exception, e:
bError = True
Log.Critical('Exception happend in downloadBundle2tmp: ' + str(e))
if bUpgrade:
# Now we need to nuke files that should no longer be there!
for root, dirs, files in os.walk(bundleName):
for fname in files:
if Core.storage.join_path(root, fname).replace(bundleName, '') not in newFiles:
Log.Debug('Removing not needed file: ' + Core.storage.join_path(root, fname))
os.remove(Core.storage.join_path(root, fname))
# And now time to swipe empty directories
removeEmptyFolders(bundleName)

if not bError and bUpgrade:
# Copy files that should be kept between upgrades ("keepFiles")
keepFiles = Dict['PMS-AllBundleInfo'].get(url, {}).get('keepFiles', [])

for filename in keepFiles:
sourcePath = bundleName + filename

if not os.path.exists(sourcePath):
Log.Debug('File does not exist: %r', sourcePath)
continue

destPath = extractDir + filename

Log.Debug('Copying %r to %r', sourcePath, destPath)

# Ensure directories exist
destDir = os.path.dirname(destPath)

try:
Core.storage.ensure_dirs(destDir)
except Exception, e:
Log.Warn('Unable to create directory: %r - %s', destDir, e)
continue

# Copy file into temporary directory
try:
shutil.copy2(sourcePath, destPath)
except Exception, e:
Log.Warn('Unable to copy file to: %r - %s', destPath, e)
continue

# Remove any empty directories in plugin
removeEmptyFolders(extractDir)

if not bError:
try:
# Delete current plugin
if os.path.exists(bundleName):
Log.Info('Deleting %r', bundleName)
shutil.rmtree(bundleName)

# Move updated bundle into "Plug-ins" directory
Log.Info('Moving %r to %r', extractDir, bundleName)
shutil.move(extractDir, bundleName)
except Exception, e:
bError = True
Log.Critical('Unable to update plugin: ' + str(e))

# Delete temporary directory
try:
shutil.rmtree(tempDir)
except Exception, e:
Log.Warn('Unable to delete temporary directory: %r - %s', tempDir, e)

if not bError:
# Install went okay, so save info
saveInstallInfo(url, bundleName)
saveInstallInfo(url, bundleName, branch)
# Install went okay, so let's make sure it get's registred
if bUpgrade:
try:
Expand Down Expand Up @@ -730,9 +795,22 @@ def getLastUpdateTime(self, req, UAS=False, url=''):
req.clear()
req.set_status(404)
req.finish("<html><body>Missing url of git</body></html>")
return req
return req

# Retrieve current branch name
if Dict['installed'].get(url, {}).get('branch'):
# Use installed branch name
branch = Dict['installed'][url]['branch']
elif Dict['PMS-AllBundleInfo'].get(url, {}).get('branch'):
# Use branch name from bundle info
branch = Dict['PMS-AllBundleInfo'][url]['branch']
else:
# Otherwise fallback to the "master" branch
branch = 'master'

# Check for updates
try:
url += '/commits/master.atom'
url += '/commits/%s.atom' % branch
Log.Debug('URL is: ' + url)
response = Datetime.ParseDate(HTML.ElementFromURL(url).xpath('//entry')[0].xpath('./updated')[0].text).strftime("%Y-%m-%d %H:%M:%S")
Log.Debug('Last update for: ' + url + ' is: ' + str(response))
Expand Down
108 changes: 108 additions & 0 deletions Contents/Code/pms.py
Original file line number Diff line number Diff line change
Expand Up @@ -68,8 +68,10 @@ def updateInstallDict():
Log.Info('Checking unknown bundle: ' + installedBundle + ' to see if it is part of UAS now')
if installedBundle in uasBundles:
# Get the installed date of the bundle formerly known as unknown :-)
installedBranch = Dict['installed'][installedBundle]['branch']
installedDate = Dict['installed'][installedBundle]['date']
# Add updated stuff to the dicts
Dict['PMS-AllBundleInfo'][uasBundles[installedBundle]]['branch'] = installedBranch
Dict['PMS-AllBundleInfo'][uasBundles[installedBundle]]['date'] = installedDate
Dict['installed'][uasBundles[installedBundle]] = Dict['PMS-AllBundleInfo'][uasBundles[installedBundle]]
# Remove old stuff from the Ditcs
Expand All @@ -93,15 +95,24 @@ def updateInstallDict():
for git in gits:
# Rearrange data
key = git['repo']
installBranch = ''
# Check if already present, and if an install date also is there
installDate = ""
if key in Dict['PMS-AllBundleInfo']:
jsonPMSAllBundleInfo = Dict['PMS-AllBundleInfo'][key]
if 'branch' in jsonPMSAllBundleInfo:
installBranch = Dict['PMS-AllBundleInfo'][key]['branch']



Log.Debug('Ged1: ' + installBranch)

if 'date' in jsonPMSAllBundleInfo:
installDate = Dict['PMS-AllBundleInfo'][key]['date']
del git['repo']
# Add/Update our Dict
Dict['PMS-AllBundleInfo'][key] = git
Dict['PMS-AllBundleInfo'][key]['branch'] = installBranch
Dict['PMS-AllBundleInfo'][key]['date'] = installDate
except Exception, e:
Log.Critical('Critical error in updateInstallDict while walking the gits: ' + str(e))
Expand Down Expand Up @@ -142,6 +153,10 @@ def reqprocess(self, req):
return self.getAllBundleInfo(req)
elif function == 'getParts':
return self.getParts(req)
elif function == 'getSectionLetterList':
return self.getSectionLetterList(req)
elif function == 'getSectionByLetter':
return self.getSectionByLetter(req)
else:
req.clear()
req.set_status(412)
Expand Down Expand Up @@ -777,6 +792,99 @@ def getSubtitles(self, req, mediaKey=''):
req.set_header('Content-Type', 'application/json; charset=utf-8')
req.finish('Fatal error happened in getSubtitles')

''' get section letter-list '''
def getSectionLetterList(self, req):
Log.Debug('Section requested')
try:
key = req.get_argument('key', 'missing')
Log.Debug('Section key is %s' %(key))
if key == 'missing':
req.clear()
req.set_status(412)
req.finish('Missing key of section')
return req
# Got all the needed params, so lets grap the list
myURL = 'http://127.0.0.1:32400/library/sections/' + key + '/firstCharacter'
resultJson = { }
sectionLetterList = XML.ElementFromURL(myURL).xpath('//Directory')
for sectionLetter in sectionLetterList:
resultJson[sectionLetter.get('title')] = {
'key' : sectionLetter.get('key'), 'size': sectionLetter.get('size')}
Log.Debug('Returning %s' %(resultJson))
req.clear()
req.set_status(200)
req.set_header('Content-Type', 'application/json; charset=utf-8')
req.finish(json.dumps(resultJson, sort_keys=True))
except Exception, e:
Log.Debug('Fatal error happened in getSectionLetterList ' + str(e))
req.clear()
req.set_status(500)
req.set_header('Content-Type', 'application/json; charset=utf-8')
req.finish('Fatal error happened in getSectionLetterList: ' + str(e))

''' get getSectionByLetter '''
def getSectionByLetter(self,req):
Log.Debug('getSectionByLetter requested')
try:
key = req.get_argument('key', 'missing')
Log.Debug('Section key is %s' %(key))
if key == 'missing':
req.clear()
req.set_status(412)
req.finish('Missing key of section')
return req
start = req.get_argument('start', 'missing')
Log.Debug('Section start is %s' %(start))
if start == 'missing':
req.clear()
req.set_status(412)
req.finish('Missing start of section')
return req
size = req.get_argument('size', 'missing')
Log.Debug('Section size is %s' %(size))
if size == 'missing':
req.clear()
req.set_status(412)
req.finish('Missing size of section')
return req
letterKey = req.get_argument('letterKey', 'missing')
Log.Debug('letterKey is %s' %(letterKey))
if letterKey == 'missing':
req.clear()
req.set_status(412)
req.finish('Missing letterKey')
return req
getSubs = req.get_argument('getSubs', 'missing')
# Got all the needed params, so lets grap the contents
try:
myURL = 'http://127.0.0.1:32400/library/sections/' + key + '/firstCharacter/' + letterKey + '?X-Plex-Container-Start=' + start + '&X-Plex-Container-Size=' + size
rawSection = XML.ElementFromURL(myURL)
Section=[]
for media in rawSection:
if getSubs != 'true':
media = {'key':media.get('ratingKey'), 'title':media.get('title')}
else:
subtitles = self.getSubtitles(req, mediaKey=media.get('ratingKey'))
media = {'key':media.get('ratingKey'), 'title':media.get('title'), 'subtitles':subtitles}
Section.append(media)
Log.Debug('Returning %s' %(Section))
req.clear()
req.set_status(200)
req.set_header('Content-Type', 'application/json; charset=utf-8')
req.finish(json.dumps(Section))
except Exception, e:
Log.Debug('Fatal error happened in getSectionByLetter: ' + str(e))
req.clear()
req.set_status(500)
req.set_header('Content-Type', 'application/json; charset=utf-8')
req.finish('Fatal error happened in getSectionByLetter: ' + str(e))
except Exception, e:
Log.Debug('Fatal error happened in getSectionByLetter: ' + str(e))
req.clear()
req.set_status(500)
req.set_header('Content-Type', 'application/json; charset=utf-8')
req.finish('Fatal error happened in getSectionByLetter: ' + str(e))

''' get section '''
def getSection(self,req):
Log.Debug('Section requested')
Expand Down
Loading

0 comments on commit a661d9b

Please sign in to comment.