this is a modificiation of the original transmission plugin. i am trying to add a few lines to be able to search another torrent site (the one i am talking about above).
the def’s i added are SearchPassthePopcorn, PTPTorrent, and LoginPTP. also i added another InputDirectory Item under def searchTorrents.
i’m really stuck because the Log just gives me an “Internal Error” and i have no idea what it is. i was hoping it was the comma after password but no sir, that didn’t make a difference.
hope this’ll get to work.
btw ignore the “for item in” parsing under def PTPTorrent, that’s not done yet, i first want the search results to appear. there must be something wrong that it just displays an error.
(the plugin still keeps working other than that part i wrote).
<br />
from PMS import *<br />
from PMS.Objects import *<br />
from PMS.Shortcuts import *<br />
from texttime import prettyduration<br />
from textbytes import prettysize<br />
import urllib,urllib2,base64 #temporarily included until HTTP module allows header access<br />
<br />
####################################################################################################<br />
<br />
PLUGIN_PREFIX = "/video/transmission"<br />
PLUGIN_TITLE = "Transmission"<br />
<br />
NAME = L('Title')<br />
<br />
PTPBASE_URL = "http://passthepopcorn.me/"<br />
PTPSEARCH_URL = "http://passthepopcorn.me/torrents.php?searchstr=%s"<br />
ART = 'art-default.jpg'<br />
ICON = 'icon-default.png'<br />
SETTINGS = 'settings-hi.png'<br />
PAUSE = 'pause-hi.png'<br />
RESUME = 'resume-hi.png'<br />
SEARCH = 'search-hi.png'<br />
TV = 'tv-hi.png'<br />
<br />
# Plugin-specific constants<br />
TRANSMISSION_WAITING = 1<br />
TRANSMISSION_CHECKING = 2<br />
TRANSMISSION_DOWNLOADING = 4<br />
TRANSMISSION_SEEDING = 8<br />
TRANSMISSION_PAUSED = 16<br />
<br />
####################################################################################################<br />
<br />
def Start():<br />
Plugin.AddPrefixHandler(PLUGIN_PREFIX, MainMenu, PLUGIN_TITLE, ICON, ART)<br />
<br />
MediaContainer.art = R(ART)<br />
MediaContainer.title1 = NAME<br />
DirectoryItem.thumb = R(ICON)<br />
<br />
def CreatePrefs():<br />
Prefs.Add(id='hostname', type='text', default='127.0.0.1:9091', label='Hostname')<br />
Prefs.Add(id='username', type='text', default='admin', label='Username')<br />
Prefs.Add(id='password', type='text', default='', label='Password', option='hidden')<br />
Prefs.Add(id='PTPusername', type='text', default='', label='PTP Username')<br />
Prefs.Add(id='PTPpassword', type='text', default='', label='PTP Password', option='hidden')<br />
<br />
def ValidatePrefs():<br />
u = Prefs.Get('username')<br />
p = Prefs.Get('password')<br />
h = Prefs.Get('hostname')<br />
## do some checks and return a<br />
## message container<br />
if( h ):<br />
return MessageContainer(<br />
"Success",<br />
"Details have been saved"<br />
)<br />
else:<br />
return MessageContainer(<br />
"Error",<br />
"You need to provide a hostname"<br />
)<br />
<br />
### Transmission plugin proper starts here<br />
# Transmission requires username, password and Session ID to perform actions<br />
# We attempt to make a connection with just username & password so we get the 409 Conflict response<br />
# This will contain a header with our Session ID<br />
def GetSession():<br />
h = Prefs.Get('hostname')<br />
u = Prefs.Get('username')<br />
p = Prefs.Get('password')<br />
url = "http://%s/transmission/rpc/" % h<br />
request = { "method" : "session-get" }<br />
headers = {}<br />
if( u and p and h):<br />
headers["Authorization"] = "Basic %s" % (base64.encodestring("%s:%s" % (u, p))[:-1])<br />
try:<br />
body = urllib2.urlopen(urllib2.Request(url, JSON.StringFromObject(request), headers)).read()<br />
except urllib2.HTTPError, e:<br />
if e.code == 401 or e.code == 403:<br />
return L('ErrorInvalidUsername'), {}<br />
# Otherwise, we've probably received a 409 Conflict which contains the session ID<br />
# Once the HTTP module allows access to returned headers, use these to set global authorization:<br />
# HTTP.SetPassword(h,u,p)<br />
# HTTP.SetHeader('X-Transmission-Session-Id', e.hdrs['X-Transmission-Session-Id'])<br />
return e.hdrs['X-Transmission-Session-Id']<br />
except:<br />
return L('ErrorNotRunning'), {}<br />
<br />
# Remote Transmission Call -<br />
# Use the RPC methods of Transmission to perform all out actions<br />
def RTC(method, arguments = {}, headers = {}):<br />
# Once the HTTP module allows access to returned headers and the HTTP.SetPassword also auths JSON, refactor this<br />
h = Prefs.Get('hostname')<br />
u = Prefs.Get('username')<br />
p = Prefs.Get('password')<br />
url = "http://%s/transmission/rpc/" % h<br />
<br />
session_id = GetSession()<br />
<br />
request = {<br />
"method": method,<br />
"arguments": arguments<br />
}<br />
<br />
# Setup authentication<br />
if( u and p ):<br />
headers["Authorization"] = "Basic %s" % (base64.encodestring("%s:%s" % (u, p))[:-1])<br />
<br />
headers["X-Transmission-Session-Id"] = session_id<br />
<br />
try:<br />
body = urllib2.urlopen(urllib2.Request(url, JSON.StringFromObject(request), headers)).read()<br />
except urllib2.HTTPError, e:<br />
if e.code == 401 or e.code == 403:<br />
return L('ErrorInvalidUsername'), {}<br />
return "Error reading response from Transmission", {}<br />
except urllib2.URLError, e:<br />
return e.reason[1], {}<br />
<br />
result = JSON.ObjectFromString(body)<br />
<br />
if result["result"] == "success":<br />
result["result"] = None<br />
<br />
if result["arguments"] == None:<br />
result["arguments"] = {}<br />
<br />
return result["result"], result["arguments"]<br />
<br />
def MainMenu():<br />
dir = MediaContainer(viewGroup="List")<br />
GetSession()<br />
dir.Append(Function(DirectoryItem(TorrentList,"Torrents",subtitle=None,summary="View torrent progress and control your downloads.",thumb=R(ICON),art=R(ART))))<br />
dir.Append(Function(DirectoryItem(SearchTorrents,"Search for a torrent",subtitle=None,summary="Browse the TV shows directory or search for files to download.",thumb=R(SEARCH),art=R(ART))))<br />
dir.Append(PrefsItem(title="Preferences",subtitle="Set Transmission access details",summary="Make sure Transmission is running and 'Remote access' is enabled then enter the access details here.",thumb=R(SETTINGS)))<br />
return dir<br />
<br />
def TorrentList(sender):<br />
error, result = RTC("torrent-get",<br />
{ "fields": [<br />
"hashString","name","status",<br />
"eta","errorString",<br />
"totalSize","leftUntilDone","sizeWhenDone",<br />
"peersGettingFromUs", "peersSendingToUs", "peersConnected",<br />
"rateDownload", "rateUpload",<br />
"downloadedEver", "uploadedEver"<br />
] }<br />
)<br />
if error != None:<br />
if error != "Connection refused":<br />
return MessageContainer(<br />
"Transmission unavailable",<br />
"There was an unknown error."<br />
)<br />
else:<br />
return MessageContainer(<br />
"Transmission unavailable",<br />
"Please make sure Transmission is running with Remote access enabled. For more information please see http://wiki.plexapp.com/index.php/Transmission"<br />
)<br />
elif result["torrents"] != None:<br />
dir = MediaContainer()<br />
progress = 100;<br />
for torrent in result["torrents"]:<br />
summary = ""<br />
<br />
if torrent["errorString"]:<br />
summary += "Error: %s
" % (torrent["errorString"])<br />
<br />
if torrent["leftUntilDone"] > 0 and torrent["status"] != TRANSMISSION_SEEDING:<br />
# Display progress "12.3 MB of 45.6 GB (0%)"<br />
progress = ((torrent["sizeWhenDone"] - torrent["leftUntilDone"]) /<br />
(torrent["sizeWhenDone"] / 100))<br />
<br />
summary += "%s of %s (%d%%)
" % (<br />
prettysize(torrent["sizeWhenDone"] - torrent["leftUntilDone"]),<br />
prettysize(torrent["sizeWhenDone"]), progress<br />
)<br />
<br />
# Display an ETA; "3 days remaining"<br />
if torrent["eta"] > 0 and torrent["status"] != TRANSMISSION_PAUSED:<br />
summary += prettyduration(torrent["eta"]) + " remaining
"<br />
else:<br />
summary += "Remaining time unknown
"<br />
<br />
if torrent["status"] == TRANSMISSION_DOWNLOADING:<br />
# Display download status "Downloading from 3 of 6 peers"<br />
summary += "Downloading from %d of %d peers
" % (<br />
torrent["peersSendingToUs"],<br />
torrent["peersConnected"]<br />
)<br />
<br />
# Display download and upload rates<br />
summary += "Downloading at %s/s
Uploading at %s/s
" % (<br />
prettysize(torrent["rateDownload"]),<br />
prettysize(torrent["rateUpload"])<br />
)<br />
else:<br />
# Display torrent status<br />
summary += TorrentStatus(torrent)<br />
else:<br />
if torrent["status"] == TRANSMISSION_SEEDING:<br />
summary += "Complete
"<br />
progress=100<br />
# else:<br />
# Log("torrent status is: %d" % torrent["status"], True)<br />
<br />
if torrent["downloadedEver"] == 0:<br />
torrent["downloadedEver"] = 1<br />
<br />
summary += "%s, uploaded %s (Ratio %.2f)
" % (<br />
prettysize(torrent["totalSize"]),<br />
prettysize(torrent["uploadedEver"]),<br />
float(torrent["uploadedEver"]) / float(torrent["downloadedEver"])<br />
)<br />
<br />
if torrent["status"] == TRANSMISSION_SEEDING:<br />
summary += "Seeding to %d of %d peers
" % (<br />
torrent["peersGettingFromUs"],<br />
torrent["peersConnected"]<br />
)<br />
summary += "Uploading at %s/s
" % (<br />
prettysize(torrent["rateUpload"])<br />
)<br />
# This is so that we don't bloat the plugin with 101 images.<br />
# It might change later if PIL is included into the framework<br />
nearest = int(round(progress/10)*10)<br />
<br />
# The summary has been built, add the item:<br />
dir.Append(<br />
Function(<br />
PopupDirectoryItem(<br />
TorrentInfo,<br />
torrent["name"],<br />
summary=summary,<br />
thumb=R("%s.png" % nearest)<br />
),<br />
name = torrent["name"],<br />
status = torrent["status"],<br />
hash = torrent["hashString"]<br />
)<br />
)<br />
<br />
# Add "Pause all torrents" menu item<br />
dir.Append(Function(DirectoryItem(PauseTorrent,L('MenuPauseAll'),subtitle=None,summary=None,thumb=R(PAUSE),art=R(ART)), hash='all'))<br />
<br />
# Add "Resume all torrents" menu item<br />
dir.Append(Function(DirectoryItem(ResumeTorrent,L('MenuResumeAll'),subtitle=None,summary=None,thumb=R(RESUME),art=R(ART)), hash='all'))<br />
<br />
return dir<br />
<br />
def TorrentInfo(sender, name, status, hash):<br />
# Display an action menu for this torrent<br />
# #######################################<br />
dir = MediaContainer()<br />
dir.Append(Function(DirectoryItem(ViewFiles, L('MenuViewFiles'), subtitle=None,summary=None,thumb=R(ICON),art=R(ART)), hash=hash))<br />
if status == TRANSMISSION_PAUSED:<br />
dir.Append(Function(DirectoryItem(ResumeTorrent,L('MenuResume'), subtitle=None,summary=None,thumb=R(ICON),art=R(ART)), hash=hash))<br />
else:<br />
dir.Append(Function(DirectoryItem(PauseTorrent, L('MenuPause'), subtitle=None,summary=None,thumb=R(ICON),art=R(ART)), hash=hash))<br />
dir.Append(Function(DirectoryItem(RemoveTorrent, L('MenuRemove'), subtitle=None,summary=None,thumb=R(ICON),art=R(ART)), hash=hash))<br />
dir.Append(Function(DirectoryItem(DeleteTorrent, L('MenuDelete'), subtitle=None,summary=None,thumb=R(ICON),art=R(ART)), hash=hash))<br />
<br />
return dir<br />
<br />
def TorrentStatus(torrent):<br />
if torrent == None or torrent["status"] == None:<br />
return L('TorrentStatusUnknown')<br />
elif torrent["status"] == TRANSMISSION_WAITING:<br />
return L('TorrentStatusWaiting')<br />
elif torrent["status"] == TRANSMISSION_CHECKING:<br />
return L('TorrentStatusVerifying')<br />
elif torrent["status"] == TRANSMISSION_PAUSED:<br />
return L('TorrentStatusPaused')<br />
elif torrent["status"] == TRANSMISSION_DOWNLOADING:<br />
return L('TorrentStatusDownloading')<br />
elif torrent["status"] == TRANSMISSION_SEEDING:<br />
return L('TorrentStatusSeeding')<br />
else:<br />
return L('TorrentStatusUnknown')<br />
<br />
def ViewFiles(sender, hash):<br />
# Display the contents of a torrent<br />
# #################################<br />
# Log("Need details for: %s" % hash, True)<br />
<br />
error, result = RTC("torrent-get",<br />
{ "ids": [ hash ], "fields": [ "hashString", "files", "wanted" ] })<br />
<br />
if error != None:<br />
return MessageContainer(<br />
"Transmission error",<br />
"Unable to list files."<br />
)<br />
<br />
dir = MediaContainer()<br />
for torrent in result["torrents"]:<br />
if torrent["hashString"] != hash:<br />
continue<br />
<br />
for i in range(0, len(torrent["files"])):<br />
file = torrent["files"]*<br />
<br />
Log("Name: %s" % (file["name"]), True)<br />
<br />
if torrent["wanted"]* == 1:<br />
if file["bytesCompleted"] == file["length"]:<br />
summary = "Complete"<br />
else:<br />
# Display progress "12.3 MB of 45.6 GB (0%)"<br />
summary = "%s of %s (%s%%)
" % (<br />
prettysize(file["bytesCompleted"]),<br />
prettysize(file["length"]),<br />
(file["bytesCompleted"]) / (file["length"] / 100)<br />
)<br />
else:<br />
summary = "Not Downloading"<br />
<br />
dir.Append(PopupDirectoryItem("%d" % i, file["name"], summary=summary))<br />
<br />
return dir<br />
<br />
<br />
def ResumeTorrent(sender, hash):<br />
# The following several functions could have<br />
# been bundled together but I decided to keep them separate<br />
# #######################################<br />
action = "torrent-start"<br />
arguments = { "ids" : hash }<br />
error, result = RTC(action, arguments)<br />
if error != None:<br />
return MessageContainer("Error", error)<br />
else:<br />
return MessageContainer("Transmission", L('ActionTorrentResumed'))<br />
<br />
def PauseTorrent(sender, hash):<br />
action = "torrent-stop"<br />
arguments = { "ids" : hash }<br />
error, result = RTC(action, arguments)<br />
if error != None:<br />
return MessageContainer("Error", error)<br />
else:<br />
return MessageContainer("Transmission", L('ActionTorrentPaused'))<br />
<br />
def RemoveTorrent(sender, hash):<br />
action = "torrent-remove"<br />
arguments = { "ids" : hash }<br />
error, result = RTC(action, arguments)<br />
if error != None:<br />
return MessageContainer("Error", error)<br />
else:<br />
return MessageContainer("Transmission", L('ActionTorrentRemoved'))<br />
<br />
def DeleteTorrent(sender, hash):<br />
action = "torrent-remove"<br />
arguments = { "ids" : hash, "delete-local-data": True}<br />
error, result = RTC(action, arguments)<br />
if error != None:<br />
return MessageContainer("Error", error)<br />
else:<br />
return MessageContainer("Transmission", L('ActionTorrentDeleted'))<br />
<br />
def AddTorrent(sender, torrentUrl):<br />
action = "torrent-add"<br />
arguments = { "filename" : torrentUrl}<br />
Log(torrentUrl, True)<br />
error, result = RTC(action, arguments)<br />
if error != None:<br />
return MessageContainer("Error", error)<br />
else:<br />
return MessageContainer("Transmission", L('ActionTorrentAdded'))<br />
<br />
# These next few extremely handy functions are based on work done in the uTorrent Plugin.<br />
# The first one would list all shows mentioned on http://ezrss.it/shows/<br />
# This is a long list so it isn't used<br />
def TVShowList(sender):<br />
<br />
dir = MediaContainer()<br />
<br />
showsPage = XML.ElementFromURL('http://ezrss.it/shows/', isHTML=True, errors='ignore')<br />
<br />
#Assign to blocks, and remove the first block (A, B, C, etc...)<br />
blocks = showsPage.xpath('//div[@class="block"]')<br />
blocks.pop(0)<br />
<br />
for block in blocks:<br />
for href in block.xpath('.//a'):<br />
if href.text != "# Top":<br />
requestUrl = "http://ezrss.it" + href.get("href") + "&mode=rss"<br />
dir.Append(Function(DirectoryItem(TVEpisodeList,href.text,subtitle=None,summary=None,thumb=R(ICON),art=R(ART)),name=href.text,url=requestUrl))<br />
<br />
return dir<br />
<br />
# This grabs a list of all first letters used on that page<br />
def TVShowListFolders(sender):<br />
<br />
dir = MediaContainer()<br />
<br />
showsPage = XML.ElementFromURL('http://ezrss.it/shows/', isHTML=True, errors='ignore')<br />
<br />
#Assign to blocks, and remove the first block (A, B, C, etc...)<br />
blocks = showsPage.xpath('//div[@class="block"]')<br />
blocks.pop(0)<br />
<br />
for block in blocks:<br />
letter = block.xpath("h2")[0].text<br />
dir.Append(Function(DirectoryItem(TVShowListSubfolders,letter,subtitle=None,summary=None,thumb=R(ICON),art=R(ART)),letter=letter))<br />
return dir<br />
<br />
# This returns only shows within that subsection<br />
def TVShowListSubfolders(sender, letter):<br />
<br />
dir = MediaContainer()<br />
<br />
showsPage = XML.ElementFromURL('http://ezrss.it/shows/', isHTML=True, errors='ignore')<br />
<br />
#Assign to blocks, and remove the first block (A, B, C, etc...)<br />
blocks = showsPage.xpath('//div[@class="block" and h2 = "%s"]' % letter)<br />
<br />
for block in blocks:<br />
for href in block.xpath('.//a'):<br />
if href.text != "# Top":<br />
requestUrl = "http://ezrss.it" + href.get("href") + "&mode=rss"<br />
dir.Append(Function(DirectoryItem(TVEpisodeList,href.text,subtitle=None,summary=None,thumb=R(ICON),art=R(ART)),name=href.text,url=requestUrl))<br />
<br />
return dir<br />
<br />
# This lists all available torrents for the chosen show<br />
def TVEpisodeList(sender, name, url):<br />
<br />
dir = MediaContainer()<br />
<br />
feed = XML.ElementFromURL(url, isHTML=False, errors='ignore').xpath("//item")<br />
<br />
for element in feed:<br />
title = element.xpath("title")[0].text<br />
link = element.xpath("link")[0].text<br />
dir.Append(Function(DirectoryItem(AddTorrent,title,subtitle=None,summary=None,thumb=R(ICON),art=R(ART)),torrentUrl=link))<br />
<br />
return dir<br />
<br />
# There's a minor bug in the InputDirectoryItem in that it doesn't<br />
# like it when subtitle is passed as a named argument. Just saying.<br />
def SearchTorrents(sender):<br />
dir = MediaContainer(viewGroup="List")<br />
dir.Append(Function(DirectoryItem( TVShowListFolders, L('MenuBrowseTV'), subtitle="Browse the TV shows directory", summary=None,thumb=R(TV),art=R(ART))))<br />
dir.Append(Function(InputDirectoryItem( SearchEZTV, L('MenuSearchTV'), "Search the TV shows directory", summary="This will use EZTV to search.",thumb=R(SEARCH),art=R(ART))))<br />
dir.Append(Function(DirectoryItem( SearchIsoHunt, L('MenuSearchOther'), subtitle="Search for other torrents", summary="This will use IsoHunt to search.",thumb=R(SEARCH),art=R(ART))))<br />
dir.Append(Function(SearchDirectoryItem( SearchPassthePopcorn, L('Search PassthePopcorn'), "Search PassThePopcorn", summary="This will use PassthePopcorn to search.",thumb=R(SEARCH),art=R(ART))))<br />
return dir<br />
<br />
# I might drop IsoHunt from the next version as it returns a lot of...ahem...adult results regardless of search terms.<br />
def SearchIsoHunt(sender):<br />
dir = MediaContainer()<br />
dir.Append(Function(InputDirectoryItem(SearchIsoHuntCategory,"Search all categories","",summary="",thumb=R(ICON),art=R(ART)),category=99))<br />
dir.Append(Function(InputDirectoryItem(SearchIsoHuntCategory,"Movies","",summary=None,thumb=R(ICON),art=R(ART)),category=1))<br />
dir.Append(Function(InputDirectoryItem(SearchIsoHuntCategory,"Audio","",summary=None,thumb=R(ICON),art=R(ART)),category=2))<br />
dir.Append(Function(InputDirectoryItem(SearchIsoHuntCategory,"TV Shows","",summary=None,thumb=R(ICON),art=R(ART)),category=3))<br />
dir.Append(Function(InputDirectoryItem(SearchIsoHuntCategory,"Games","",summary=None,thumb=R(ICON),art=R(ART)),category=4))<br />
dir.Append(Function(InputDirectoryItem(SearchIsoHuntCategory,"Music Video","",summary=None,thumb=R(ICON),art=R(ART)),category=10))<br />
dir.Append(Function(InputDirectoryItem(SearchIsoHuntCategory,"Applications","",summary=None,thumb=R(ICON),art=R(ART)),category=5))<br />
dir.Append(Function(InputDirectoryItem(SearchIsoHuntCategory,"Pictures","",summary=None,thumb=R(ICON),art=R(ART)),category=7))<br />
dir.Append(Function(InputDirectoryItem(SearchIsoHuntCategory,"Comics","",summary=None,thumb=R(ICON),art=R(ART)),category=8))<br />
dir.Append(Function(InputDirectoryItem(SearchIsoHuntCategory,"Books","",summary=None,thumb=R(ICON),art=R(ART)),category=9))<br />
dir.Append(Function(InputDirectoryItem(SearchIsoHuntCategory,"Miscellaneous","",summary=None,thumb=R(ICON),art=R(ART)),category=0))<br />
dir.Append(Function(InputDirectoryItem(SearchIsoHuntCategory,"Unclassified","",summary=None,thumb=R(ICON),art=R(ART)),category=11))<br />
return dir<br />
<br />
def SearchIsoHuntCategory(sender, query=None, category=99):<br />
dir = MediaContainer()<br />
url = "http://isohunt.com/js/rss"<br />
if query != None:<br />
url += "/%s" % query<br />
if category != 99:<br />
url += "?iht=%d" % category<br />
Log(url, True)<br />
feed = XML.ElementFromURL(url, isHTML=False, errors='ignore').xpath("//item")<br />
if feed == None:<br />
return MessageContainer("Error", "Search returned no results")<br />
if len(feed) == 0:<br />
return MessageContainer("Error", "No results").ToXML()<br />
for element in feed:<br />
title = element.xpath("title")[0].text<br />
category = element.xpath("category")[0].text<br />
link = element.find("enclosure").get("url")<br />
size = prettysize(int(element.find("enclosure").get("length")))<br />
dir.Append(Function(DirectoryItem(AddTorrent,title,subtitle=None,summary="Category: %s
Size: %s" % (category,size),thumb=R(ICON),art=R(ART)),torrentUrl=link))<br />
return dir<br />
<br />
def SearchPassthePopcorn(sender, query=None):<br />
dir = MediaContainer()<br />
LoginPTP()<br />
Log("Success!")<br />
pageUrl2 = PTPSEARCH_URL % (String.Quote(query, usePlus=True))<br />
Log("Success!")<br />
content1=XML.ElementFromURL(pageUrl2, isHTML=False, errors='ignore')<br />
for item in content1.xpath('//td[contains(@id,"large_groupid")]'):<br />
Log(item)<br />
title = item.xpath('./img')[0].get('title')<br />
titleUrl = item.xpath('./a')[0].get('href')<br />
thumb = item.xpath('./img')[0].get('src')<br />
dir.Append(Function(DirectoryItem(PTPTorrent,title=title, titleUrl=titleUrl)))<br />
return dir<br />
<br />
def PTPTorrent(sender, titleUrl):<br />
dir = MediaContainer()<br />
pageUrl = PTPBASE_URL + titleUrl<br />
Log("Success!")<br />
content2=XML.ElementFromURL(pageUrl, isHTML=True, errors='ignore')<br />
for item in content2.xpath('//td[contains(@id,"large_groupid")]'):<br />
Log(item)<br />
title = item.xpath('./img')[0].get('title')<br />
titleUrl = item.xpath('./a')[0].get('href')<br />
thumb = item.xpath('./img')[0].get('src')<br />
dir.Append(Function(DirectoryItem(AddTorrent,title,subtitle=None,thumb=R(ICON),art=R(ART)),torrentUrl=titleUrl))<br />
return dir<br />
<br />
def LoginPTP():<br />
values = {<br />
'username' : Prefs.Get("PTPusername"),<br />
'password' : Prefs.Get("PTPpassword")}<br />
x = HTTP.Request('http://passthepopcorn.me/login.php', values)<br />
<br />
# This function was a lot longer in the previous version of the<br />
# Framework. It was so much simpler this time round.<br />
def SearchEZTV(sender, query=None):<br />
dir = MediaContainer()<br />
url = "http://ezrss.it/search/index.php?simple&mode=rss&show_name="<br />
if query != None:<br />
url += "%s" % query<br />
Log(url, True)<br />
feed = XML.ElementFromURL(url, isHTML=False, errors='ignore').xpath("//item")<br />
if feed == None:<br />
return MessageContainer("Error", "Search failed")<br />
if len(feed) == 0:<br />
return MessageContainer("Error", "No results")<br />
for element in feed:<br />
title = element.xpath("title")[0].text<br />
category = element.xpath("category")[0].text<br />
link = element.find("enclosure").get("url")<br />
size = prettysize(int(element.find("enclosure").get("length")))<br />
dir.Append(Function(DirectoryItem(AddTorrent,title,subtitle=None,summary="Category: %s
Size: %s" % (category,size),thumb=R(ICON),art=R(ART)),torrentUrl=link))<br />
return dir<br />
<br />
# This is currently unused due to issues between PIL and Framework v1<br />
# re-enable it later if PIL gets included in the framework by sticking this at the top:<br />
# from icon import TorrentIconCached<br />
# and the rest in a file called icon.py:<br />
# from PMS import *<br />
# from PMS.Objects import *<br />
# from PMS.Shortcuts import *<br />
# from PIL import Image, ImageFont, ImageDraw<br />
# import cStringIO<br />
#<br />
# LargeFont = ImageFont.truetype("/Library/Fonts/Arial Bold.ttf", 100)<br />
# SmallFont = ImageFont.truetype("/Library/Fonts/Arial Bold.ttf", 30)<br />
#<br />
# def TorrentIcon(name, status, progress=100):<br />
# result = cStringIO.StringIO()<br />
# image = Image.new("RGBA", (304, 450), (0, 0, 0, 0))<br />
# draw = ImageDraw.Draw(image)<br />
#<br />
# Log("name: %s, status: %s" % (name, status), True)<br />
# draw.text((1, 1), status, font=LargeFont, fill="black")<br />
# draw.text((0, 0), status, font=LargeFont, fill="white")<br />
# draw.text((1, 131), name, font=SmallFont, fill="black")<br />
# draw.text((0, 130), name, font=SmallFont, fill="white")<br />
#<br />
# if progress >= 0:<br />
# draw.rectangle( ( 0, 170, 3 * progress, 200 ), fill="white", outline="black")<br />
# draw.rectangle( ( 3 * progress, 170, 300, 200 ), fill="#444", outline="black")<br />
#<br />
# image.save(result, "PNG")<br />
# imagedata=result.getvalue()<br />
# return DataObject(data = result.getvalue(), contentType="image/png")<br />
#<br />
# def TorrentIconCached(name, status, progress=100):<br />
# # TorrentIconCached(torrent["name"],"%d%%" % progress,progress)<br />
# if Data.Exists("%s.png" % progress):<br />
# return DataObject(data = Data.Load("%s.png" % progress), contentType="image/png")<br />
# else:<br />
# return TorrentIcon(name, status, progress)<br />