2015-07-18 18:08:05 +10:00
# -- coding: utf-8 --
2015-03-14 08:24:59 +11:00
# API.py
# This class helps translate more complex cases from the MediaBrowser API to the XBMC API
from datetime import datetime
2015-05-07 07:41:44 +10:00
from random import randrange
2015-03-15 05:10:27 +11:00
import xbmc
import xbmcgui
import xbmcaddon
2015-03-14 08:24:59 +11:00
class API ( ) :
def getPeople ( self , item ) :
# Process People
2015-07-18 18:08:05 +10:00
director = [ ]
writer = [ ]
cast = [ ]
try :
people = item [ ' People ' ]
except : pass
else :
2015-03-14 08:24:59 +11:00
for person in people :
2015-07-18 18:08:05 +10:00
type = person [ ' Type ' ]
Name = person [ ' Name ' ]
if " Director " in type :
director . append ( Name )
elif " Writing " in type :
writer . append ( Name )
elif " Writer " in type :
writer . append ( Name )
elif " Actor " in type :
2015-03-15 04:23:45 +11:00
cast . append ( Name )
2015-07-18 18:08:05 +10:00
return {
' Director ' : director ,
' Writer ' : writer ,
' Cast ' : cast
}
2015-03-14 08:24:59 +11:00
def getTimeInfo ( self , item ) :
2015-07-18 18:08:05 +10:00
# Runtime and Resume point
tempRuntime = 0
runtime = 0
resume = 0
2015-03-14 08:24:59 +11:00
2015-07-18 18:08:05 +10:00
try : # Get resume point
userdata = item [ ' UserData ' ]
playbackPosition = userdata [ ' PlaybackPositionTicks ' ]
resume = playbackPosition / 10000000.0
except : pass
try : # Get total runtime
tempRuntime = item [ ' RunTimeTicks ' ]
except :
try : tempRuntime = item [ ' CumulativeRunTimeTicks ' ]
except : pass
finally :
runtime = tempRuntime / 10000000.0
return {
' ResumeTime ' : resume ,
' TotalTime ' : runtime
}
2015-03-14 08:24:59 +11:00
2015-03-15 04:23:45 +11:00
def getStudios ( self , item ) :
2015-03-14 08:24:59 +11:00
# Process Studio
2015-07-18 18:08:05 +10:00
studios = [ ]
try :
studio = item [ ' SeriesStudio ' ]
studios . append ( studio )
except :
try :
studioArray = item [ ' Studios ' ]
for studio in studioArray :
studios . append ( studio [ ' Name ' ] )
except : pass
2015-03-15 04:23:45 +11:00
return studios
2015-03-14 08:24:59 +11:00
2015-07-18 18:08:05 +10:00
def getGenre ( self , item ) :
genre = " "
genres = item . get ( " Genres " )
if genres != None and genres != [ ] :
for genre_string in genres :
if genre == " " : #Just take the first genre
genre = genre_string
else :
genre = genre + " / " + genre_string
elif item . get ( " SeriesGenres " ) != None and item . get ( " SeriesGenres " ) != ' ' :
genres = item . get ( " SeriesGenres " )
if genres != None and genres != [ ] :
for genre_string in genres :
if genre == " " : #Just take the first genre
genre = genre_string
else :
genre = genre + " / " + genre_string
return genre
def getMediaStreams ( self , item , mediaSources = False ) :
videotracks = [ ] # Height, Width, Codec, AspectRatio, AspectFloat, 3D
audiotracks = [ ] # Codec, Channels, language
subtitlelanguages = [ ] # Language
if mediaSources :
try :
MediaStreams = item [ ' MediaSources ' ] [ 0 ] [ ' MediaStreams ' ]
except :
2015-03-14 08:24:59 +11:00
MediaStreams = None
else :
2015-07-18 18:08:05 +10:00
MediaStreams = item . get ( ' MediaStreams ' )
if MediaStreams :
# Sort through the Video, Audio, Subtitle tracks
for mediaStream in MediaStreams :
type = mediaStream . get ( " Type " , " " )
if " Video " in type :
videotrack = { }
2015-07-28 16:43:15 +10:00
videotrack [ ' videocodec ' ] = mediaStream . get ( ' Codec ' , " " ) . lower ( )
container = item [ ' MediaSources ' ] [ 0 ] . get ( ' Container ' , " " ) . lower ( )
if " msmpeg4 " in videotrack [ ' videocodec ' ] :
videotrack [ ' videocodec ' ] = " divx "
elif " mpeg4 " in videotrack [ ' videocodec ' ] :
profile = mediaStream . get ( ' Profile ' , " " ) . lower ( )
2015-07-31 22:51:11 +10:00
if " simple profile " in profile or profile == " " :
2015-07-27 22:22:39 +10:00
videotrack [ ' videocodec ' ] = " xvid "
elif " h264 " in videotrack [ ' videocodec ' ] :
2015-07-28 16:43:15 +10:00
if container in ( " mp4 " , " mov " , " m4v " ) :
2015-07-27 22:22:39 +10:00
videotrack [ ' videocodec ' ] = " avc1 "
2015-07-18 18:08:05 +10:00
videotrack [ ' height ' ] = mediaStream . get ( ' Height ' )
videotrack [ ' width ' ] = mediaStream . get ( ' Width ' )
videotrack [ ' Video3DFormat ' ] = item . get ( ' Video3DFormat ' )
2015-07-28 16:43:15 +10:00
videotrack [ ' aspectratio ' ] = mediaStream . get ( ' AspectRatio ' , " 0 " )
2015-07-18 18:08:05 +10:00
if len ( videotrack [ ' aspectratio ' ] ) > = 3 :
try :
2015-07-27 21:02:10 +10:00
aspectwidth , aspectheight = videotrack [ ' aspectratio ' ] . split ( ' : ' )
videotrack [ ' aspectratio ' ] = round ( float ( aspectwidth ) / float ( aspectheight ) , 6 )
2015-07-18 18:08:05 +10:00
except :
2015-08-01 07:13:32 +10:00
videotrack [ ' aspectratio ' ] = 1.85
2015-07-28 16:43:15 +10:00
else :
2015-08-01 07:13:32 +10:00
try :
videotrack [ ' aspectratio ' ] = round ( float ( videotrack [ ' width ' ] / videotrack [ ' height ' ] ) , 6 )
except : # In the event the aspect ratio is missing and the width and height are missing as well.
videotrack [ ' aspectratio ' ] = 1.85
2015-07-18 18:08:05 +10:00
videotracks . append ( videotrack )
elif " Audio " in type :
audiotrack = { }
2015-07-31 22:51:11 +10:00
audiotrack [ ' audiocodec ' ] = mediaStream . get ( ' Codec ' , " " ) . lower ( )
if " dts-hd ma " in audiotrack [ ' audiocodec ' ] :
audiotrack [ ' audiocodec ' ] = " dts "
2015-07-18 18:08:05 +10:00
audiotrack [ ' channels ' ] = mediaStream . get ( ' Channels ' )
audiotrack [ ' audiolanguage ' ] = mediaStream . get ( ' Language ' )
audiotracks . append ( audiotrack )
elif " Subtitle " in type :
try :
subtitlelanguages . append ( mediaStream [ ' Language ' ] )
except :
subtitlelanguages . append ( " Unknown " )
return {
' videocodec ' : videotracks ,
' audiocodec ' : audiotracks ,
' subtitlelanguage ' : subtitlelanguages
}
2015-05-02 10:26:06 +10:00
def getChecksum ( self , item ) :
2015-05-03 09:46:11 +10:00
# use the etags checksum for this if available
# AND the userdata
2015-05-02 10:26:06 +10:00
checksum = " "
2015-05-03 00:34:59 +10:00
2015-05-03 07:14:04 +10:00
if item . get ( " Etag " ) != None :
checksum = item . get ( " Etag " )
2015-05-08 08:06:49 +10:00
userData = item . get ( " UserData " )
2015-05-03 09:46:11 +10:00
if ( userData != None ) :
checksum + = str ( userData . get ( " Played " ) )
checksum + = str ( userData . get ( " IsFavorite " ) )
if userData . get ( ' UnplayedItemCount ' ) != None :
checksum + = str ( userData . get ( " UnplayedItemCount " ) )
if userData . get ( ' LastPlayedDate ' ) != None :
checksum + = str ( userData . get ( " LastPlayedDate " ) )
if userData . get ( ' PlaybackPositionTicks ' ) != None :
checksum + = str ( userData . get ( " PlaybackPositionTicks " ) )
2015-05-02 10:26:06 +10:00
return checksum
2015-03-14 08:24:59 +11:00
def getUserData ( self , item ) :
2015-07-18 18:08:05 +10:00
# Default
favorite = False
playcount = None
lastPlayedDate = None
userKey = " "
try :
userdata = item [ ' UserData ' ]
except : # No userdata found.
pass
else :
favorite = userdata [ ' IsFavorite ' ]
userKey = userdata . get ( ' Key ' , " " )
watched = userdata [ ' Played ' ]
if watched :
# Playcount is tied to the watch status
playcount = userdata [ ' PlayCount ' ]
2015-05-20 19:45:43 +10:00
if playcount == 0 :
playcount = 1
2015-03-14 08:24:59 +11:00
else :
2015-07-18 18:08:05 +10:00
playcount = None
lastPlayedDate = userdata . get ( ' LastPlayedDate ' , None )
if lastPlayedDate :
lastPlayedDate = lastPlayedDate . split ( ' . ' ) [ 0 ] . replace ( ' T ' , " " )
return {
' Favorite ' : favorite ,
' PlayCount ' : playcount ,
' LastPlayedDate ' : lastPlayedDate ,
' Key ' : userKey
}
2015-03-14 08:24:59 +11:00
def getRecursiveItemCount ( self , item ) :
if item . get ( " RecursiveItemCount " ) != None :
return str ( item . get ( " RecursiveItemCount " ) )
else :
2015-07-18 18:08:05 +10:00
return " 0 "
2015-03-14 08:24:59 +11:00
def getOverview ( self , item ) :
2015-07-18 18:08:05 +10:00
overview = " "
try :
overview = item [ ' Overview ' ]
overview = overview . replace ( " \" " , " \' " )
overview = overview . replace ( " \n " , " " )
overview = overview . replace ( " \r " , " " )
except : pass
return overview
2015-03-14 08:24:59 +11:00
def getTVInfo ( self , item , userData ) :
TotalSeasons = 0 if item . get ( " ChildCount " ) == None else item . get ( " ChildCount " )
TotalEpisodes = 0 if item . get ( " RecursiveItemCount " ) == None else item . get ( " RecursiveItemCount " )
WatchedEpisodes = 0 if userData . get ( " UnplayedItemCount " ) == None else TotalEpisodes - int ( userData . get ( " UnplayedItemCount " ) )
UnWatchedEpisodes = 0 if userData . get ( " UnplayedItemCount " ) == None else int ( userData . get ( " UnplayedItemCount " ) )
NumEpisodes = TotalEpisodes
tempEpisode = " "
if ( item . get ( " IndexNumber " ) != None ) :
episodeNum = item . get ( " IndexNumber " )
if episodeNum < 10 :
tempEpisode = " 0 " + str ( episodeNum )
else :
tempEpisode = str ( episodeNum )
tempSeason = " "
if ( str ( item . get ( " ParentIndexNumber " ) ) != None ) :
tempSeason = str ( item . get ( " ParentIndexNumber " ) )
if item . get ( " ParentIndexNumber " ) < 10 :
tempSeason = " 0 " + tempSeason
if item . get ( " SeriesName " ) != None :
temp = item . get ( " SeriesName " )
SeriesName = temp . encode ( ' utf-8 ' )
else :
SeriesName = ' '
return { ' TotalSeasons ' : str ( TotalSeasons ) ,
' TotalEpisodes ' : str ( TotalEpisodes ) ,
' WatchedEpisodes ' : str ( WatchedEpisodes ) ,
' UnWatchedEpisodes ' : str ( UnWatchedEpisodes ) ,
' NumEpisodes ' : str ( NumEpisodes ) ,
' Season ' : tempSeason ,
' Episode ' : tempEpisode ,
' SeriesName ' : SeriesName
}
2015-07-18 18:08:05 +10:00
2015-03-15 05:10:27 +11:00
def getDateCreated ( self , item ) :
2015-07-18 18:08:05 +10:00
dateadded = None
try :
dateadded = item [ ' DateCreated ' ]
dateadded = dateadded . split ( ' . ' ) [ 0 ] . replace ( ' T ' , " " )
except : pass
return dateadded
def getPremiereDate ( self , item ) :
premiere = None
try :
premiere = item [ ' PremiereDate ' ]
premiere = premiere . split ( ' . ' ) [ 0 ] . replace ( ' T ' , " " )
except : pass
return premiere
def getTagline ( self , item ) :
tagline = None
try :
tagline = item [ ' Taglines ' ] [ 0 ]
except : pass
return tagline
def getProvider ( self , item , providername ) :
# Provider Name: imdb or tvdb
provider = None
try :
if " imdb " in providername :
provider = item [ ' ProviderIds ' ] [ ' Imdb ' ]
elif " tvdb " in providername :
provider = item [ ' ProviderIds ' ] [ ' Tvdb ' ]
2015-07-22 23:16:08 +10:00
elif " musicBrainzArtist " in providername :
provider = item [ ' ProviderIds ' ] [ ' MusicBrainzArtist ' ]
elif " musicBrainzAlbum " in providername :
provider = item [ ' ProviderIds ' ] [ ' MusicBrainzAlbum ' ]
elif " musicBrainzTrackId " in providername :
provider = item [ ' ProviderIds ' ] [ ' MusicBrainzTrackId ' ]
2015-07-18 18:08:05 +10:00
except : pass
return provider
def getCountry ( self , item ) :
country = None
try :
country = item [ ' ProductionLocations ' ] [ 0 ]
except : pass
return country
def getArtworks ( self , data , type , mediaType = " " , index = " 0 " , getAll = False ) :
"""
Get all artwork , it will return an empty string
for the artwork type not found .
Index only matters when getAll is False .
mediaType : movie , boxset , tvshow , episode , season
Artwork type : Primary , Banner , Logo , Art , Thumb ,
Disc Backdrop
"""
id = data [ ' Id ' ]
maxHeight = 10000
maxWidth = 10000
imageTag = " e3ab56fe27d389446754d0fb04910a34 " # Place holder tag
if getAll :
allartworks = {
' Primary ' : " " ,
' Banner ' : " " ,
' Logo ' : " " ,
' Art ' : " " ,
' Thumb ' : " " ,
' Disc ' : " " ,
' Backdrop ' : " "
}
for keytype in allartworks :
type = keytype
url = " "
allartworks [ keytype ] = url
return allartworks
else : pass
2015-03-15 05:10:27 +11:00
2015-06-30 04:14:54 +10:00
def getArtwork ( self , data , type , mediaType = " " , index = " 0 " , userParentInfo = False ) :
2015-03-15 05:10:27 +11:00
2015-03-26 04:37:21 +11:00
addonSettings = xbmcaddon . Addon ( id = ' plugin.video.emby ' )
2015-03-15 05:10:27 +11:00
id = data . get ( " Id " )
getSeriesData = False
userData = data . get ( " UserData " )
if type == " tvshow.poster " : # Change the Id to the series to get the overall series poster
if data . get ( " Type " ) == " Season " or data . get ( " Type " ) == " Episode " :
id = data . get ( " SeriesId " )
getSeriesData = True
2015-03-20 11:58:58 +11:00
elif type == " poster " and data . get ( " Type " ) == " Episode " and addonSettings . getSetting ( ' useSeasonPoster ' ) == ' true ' : # Change the Id to the Season to get the season poster
2015-03-15 05:10:27 +11:00
id = data . get ( " SeasonId " )
if type == " poster " or type == " tvshow.poster " : # Now that the Ids are right, change type to MB3 name
type = " Primary "
if data . get ( " Type " ) == " Season " : # For seasons: primary (poster), thumb and banner get season art, rest series art
if type != " Primary " and type != " Primary2 " and type != " Primary3 " and type != " Primary4 " and type != " Thumb " and type != " Banner " and type != " Thumb3 " :
id = data . get ( " SeriesId " )
getSeriesData = True
if data . get ( " Type " ) == " Episode " : # For episodes: primary (episode thumb) gets episode art, rest series art.
if type != " Primary " and type != " Primary2 " and type != " Primary3 " and type != " Primary4 " :
id = data . get ( " SeriesId " )
getSeriesData = True
if type == " Primary2 " or type == " Primary3 " or type == " Primary4 " :
id = data . get ( " SeasonId " )
getSeriesData = True
if data . get ( " SeasonUserData " ) != None :
userData = data . get ( " SeasonUserData " )
if id == None :
id = data . get ( " Id " )
imageTag = " e3ab56fe27d389446754d0fb04910a34 " # a place holder tag, needs to be in this format
originalType = type
if type == " Primary2 " or type == " Primary3 " or type == " Primary4 " or type == " SeriesPrimary " :
type = " Primary "
if type == " Backdrop2 " or type == " Backdrop3 " or type == " BackdropNoIndicators " :
type = " Backdrop "
if type == " Thumb2 " or type == " Thumb3 " :
type = " Thumb "
if ( data . get ( " ImageTags " ) != None and data . get ( " ImageTags " ) . get ( type ) != None ) :
imageTag = data . get ( " ImageTags " ) . get ( type )
2015-07-31 05:23:50 +10:00
if ( data . get ( " Type " ) == " Episode " or data . get ( " Type " ) == " Season " ) and type == " Logo " :
2015-03-15 05:10:27 +11:00
imageTag = data . get ( " ParentLogoImageTag " )
if ( data . get ( " Type " ) == " Episode " or data . get ( " Type " ) == " Season " ) and type == " Art " :
imageTag = data . get ( " ParentArtImageTag " )
2015-07-31 05:23:50 +10:00
if ( data . get ( " Type " ) == " Episode " and originalType == " Thumb3 " ) :
2015-03-15 05:10:27 +11:00
imageTag = data . get ( " SeriesThumbImageTag " )
2015-07-31 05:23:50 +10:00
if ( data . get ( " Type " ) == " Season " and originalType == " Thumb3 " and imageTag == " e3ab56fe27d389446754d0fb04910a34 " ) :
2015-03-15 05:10:27 +11:00
imageTag = data . get ( " ParentThumbImageTag " )
id = data . get ( " SeriesId " )
2015-07-31 05:23:50 +10:00
# for music we return the parent art if no image exists
if ( data . get ( " Type " ) == " MusicAlbum " or data . get ( " Type " ) == " Audio " ) and type == " Backdrop " and not data . get ( " BackdropImageTags " ) :
2015-07-31 21:30:52 +10:00
data [ " BackdropImageTags " ] = data . get ( " ParentBackdropImageTags " )
2015-05-11 23:02:34 +10:00
id = data . get ( " ParentBackdropItemId " )
2015-07-31 05:23:50 +10:00
if ( data . get ( " Type " ) == " MusicAlbum " or data . get ( " Type " ) == " Audio " ) and type == " Logo " and ( not imageTag or imageTag == " e3ab56fe27d389446754d0fb04910a34 " ) :
imageTag = data . get ( " ParentLogoImageTag " )
id = data . get ( " ParentLogoItemId " )
if ( data . get ( " Type " ) == " MusicAlbum " or data . get ( " Type " ) == " Audio " ) and type == " Art " and ( not imageTag or imageTag == " e3ab56fe27d389446754d0fb04910a34 " ) :
imageTag = data . get ( " ParentArtImageTag " )
id = data . get ( " ParentArtItemId " )
2015-03-15 05:10:27 +11:00
query = " "
2015-06-30 02:44:55 +10:00
maxHeight = " 10000 "
maxWidth = " 10000 "
height = " "
width = " "
2015-03-15 05:10:27 +11:00
played = " 0 "
totalbackdrops = 0
2015-06-30 02:44:55 +10:00
if addonSettings . getSetting ( ' coverArtratio ' ) == " true " :
if mediaType in ( " movie " , " boxset " , " tvshow " ) :
if " Primary " in type :
# Only force ratio for cover art for main covers
aspectratio = data . get ( " PrimaryImageAspectRatio " )
width = " &Width=1000 "
height = " &Height=1480 "
2015-03-15 05:10:27 +11:00
if originalType == " BackdropNoIndicators " and index == " 0 " and data . get ( " BackdropImageTags " ) != None :
totalbackdrops = len ( data . get ( " BackdropImageTags " ) )
if totalbackdrops != 0 :
index = str ( randrange ( 0 , totalbackdrops ) )
# use the local image proxy server that is made available by this addons service
2015-04-14 04:56:36 +10:00
# Load user information set by UserClient
WINDOW = xbmcgui . Window ( 10000 )
username = WINDOW . getProperty ( ' currUser ' )
server = WINDOW . getProperty ( ' server %s ' % username )
2015-03-20 11:58:58 +11:00
if addonSettings . getSetting ( ' compressArt ' ) == ' true ' :
2015-03-15 05:10:27 +11:00
query = query + " &Quality=90 "
if imageTag == None :
imageTag = " e3ab56fe27d389446754d0fb04910a34 "
2015-06-17 16:13:21 +10:00
2015-06-30 02:44:55 +10:00
artwork = " %s /mediabrowser/Items/ %s /Images/ %s / %s ?MaxWidth= %s &MaxHeight= %s %s %s &Format=original&Tag= %s %s " % ( server , id , type , index , maxWidth , maxHeight , height , width , imageTag , query )
2015-06-17 16:13:21 +10:00
#artwork = "%s/mediabrowser/Items/%s/Images/%s/%s/%s/original/%s/%s/%s?%s" % (server, id, type, index, imageTag, width, height, played, query) <- broken
2015-03-20 11:58:58 +11:00
if addonSettings . getSetting ( ' disableCoverArt ' ) == ' true ' :
2015-03-15 05:10:27 +11:00
artwork = artwork + " &EnableImageEnhancers=false "
# do not return non-existing images
if ( ( type != " Backdrop " and imageTag == " e3ab56fe27d389446754d0fb04910a34 " ) | #Remember, this is the placeholder tag, meaning we didn't find a valid tag
( type == " Backdrop " and data . get ( " BackdropImageTags " ) != None and len ( data . get ( " BackdropImageTags " ) ) == 0 ) |
( type == " Backdrop " and data . get ( " BackdropImageTag " ) != None and len ( data . get ( " BackdropImageTag " ) ) == 0 )
) :
if type != " Backdrop " or ( type == " Backdrop " and getSeriesData == True and data . get ( " ParentBackdropImageTags " ) == None ) or ( type == " Backdrop " and getSeriesData != True ) :
artwork = ' '
return artwork
2015-07-18 18:08:05 +10:00
def imageUrl ( self , id , type , index , width , height ) :
WINDOW = xbmcgui . Window ( 10000 )
username = WINDOW . getProperty ( ' currUser ' )
server = WINDOW . getProperty ( ' server %s ' % username )
# For people image - actors, directors, writers
return " %s /mediabrowser/Items/ %s /Images/ %s ?MaxWidth= %s &MaxHeight= %s &Index= %s " % ( server , id , type , width , height , index )
2015-03-15 05:10:27 +11:00
def getUserArtwork ( self , data , type , index = " 0 " ) :
2015-04-14 04:56:36 +10:00
# Load user information set by UserClient
WINDOW = xbmcgui . Window ( 10000 )
username = WINDOW . getProperty ( ' currUser ' )
server = WINDOW . getProperty ( ' server %s ' % username )
2015-03-15 05:10:27 +11:00
id = data . get ( " Id " )
2015-04-14 04:56:36 +10:00
artwork = " %s /mediabrowser/Users/ %s /Images/ %s ?Format=original " % ( server , id , type )
2015-03-15 05:10:27 +11:00
2015-04-14 04:56:36 +10:00
return artwork
2015-03-15 05:10:27 +11:00