Exemple #1
0
def update_playlist_infos(provider, context, playlist_id_dict, channel_items_dict=None):
    playlist_ids = list(playlist_id_dict.keys())
    if len(playlist_ids) == 0:
        return

    resource_manager = provider.get_resource_manager(context)
    playlist_data = resource_manager.get_playlists(playlist_ids)

    for playlist_id in playlist_data.keys():
        yt_item = playlist_data[playlist_id]
        playlist_item = playlist_id_dict[playlist_id]

        snippet = yt_item['snippet']
        title = snippet['title']
        playlist_item.set_name(title)
        playlist_item.set_image(snippet.get('thumbnails', {}).get('medium', {}).get('url', ''))

        channel_id = snippet['channelId']
        # if the path directs to a playlist of our own, we correct the channel id to 'mine'
        if context.get_path() == '/channel/mine/playlists/':
            channel_id = 'mine'
            pass
        channel_name = snippet.get('channelTitle', '')
        context_menu = []
        # play all videos of the playlist
        yt_context_menu.append_play_all_from_playlist(context_menu, provider, context, playlist_id)

        if provider.is_logged_in():
            if channel_id != 'mine':
                # subscribe to the channel via the playlist item
                yt_context_menu.append_subscribe_to_channel(context_menu, provider, context, channel_id,
                                                            channel_name)
                pass
            else:
                # remove my playlist
                yt_context_menu.append_delete_playlist(context_menu, provider, context, playlist_id, title)

                # rename playlist
                yt_context_menu.append_rename_playlist(context_menu, provider, context, playlist_id, title)
                pass
            pass

        if len(context_menu) > 0:
            playlist_item.set_context_menu(context_menu)
            pass

        # update channel mapping
        if channel_items_dict is not None:
            if not channel_id in channel_items_dict:
                channel_items_dict[channel_id] = []
            channel_items_dict[channel_id].append(playlist_item)
            pass
        pass

    pass
Exemple #2
0
def update_playlist_infos(provider, context, playlist_id_dict, channel_items_dict=None):
    playlist_ids = list(playlist_id_dict.keys())
    if len(playlist_ids) == 0:
        return

    resource_manager = provider.get_resource_manager(context)
    playlist_data = resource_manager.get_playlists(playlist_ids)

    for playlist_id in playlist_data.keys():
        yt_item = playlist_data[playlist_id]
        playlist_item = playlist_id_dict[playlist_id]

        snippet = yt_item['snippet']
        title = snippet['title']
        playlist_item.set_name(title)
        playlist_item.set_image(snippet.get('thumbnails', {}).get('medium', {}).get('url', ''))

        channel_id = snippet['channelId']
        # if the path directs to a playlist of our own, we correct the channel id to 'mine'
        if context.get_path() == '/channel/mine/playlists/':
            channel_id = 'mine'
            pass
        channel_name = snippet.get('channelTitle', '')
        context_menu = []
        # play all videos of the playlist
        yt_context_menu.append_play_all_from_playlist(context_menu, provider, context, playlist_id)

        if provider.is_logged_in():
            if channel_id != 'mine':
                # subscribe to the channel via the playlist item
                yt_context_menu.append_subscribe_to_channel(context_menu, provider, context, channel_id,
                                                            channel_name)
                pass
            else:
                # remove my playlist
                yt_context_menu.append_delete_playlist(context_menu, provider, context, playlist_id, title)

                # rename playlist
                yt_context_menu.append_rename_playlist(context_menu, provider, context, playlist_id, title)
                pass
            pass

        if len(context_menu) > 0:
            playlist_item.set_context_menu(context_menu)
            pass

        # update channel mapping
        if channel_items_dict is not None:
            if not channel_id in channel_items_dict:
                channel_items_dict[channel_id] = []
            channel_items_dict[channel_id].append(playlist_item)
            pass
        pass

    pass
Exemple #3
0
def update_video_infos(provider,
                       context,
                       video_id_dict,
                       playlist_item_id_dict=None,
                       channel_id_dict=None):
    settings = context.get_settings()

    video_ids = list(video_id_dict.keys())
    if len(video_ids) == 0:
        return

    if not playlist_item_id_dict:
        playlist_item_id_dict = {}
        pass

    resource_manager = provider.get_resource_manager(context)
    video_data = resource_manager.get_videos(video_ids)

    my_playlists = {}
    if provider.is_logged_in():
        my_playlists = resource_manager.get_related_playlists(
            channel_id='mine')
        pass

    for video_id in video_data.keys():
        yt_item = video_data[video_id]
        video_item = video_id_dict[video_id]

        snippet = yt_item['snippet']  # crash if not conform

        # set the title
        video_item.set_title(snippet['title'])
        """
        This is experimental. We try to get the most information out of the title of a video.
        This is not based on any language. In some cases this won't work at all.
        TODO: via language and settings provide the regex for matching episode and season.
        """
        video_item.set_season(1)
        video_item.set_episode(1)
        season_episode_regex = [
            'Part (?P<episode>\d+)', '#(?P<episode>\d+)',
            'Ep.[^\w]?(?P<episode>\d+)', '\[(?P<episode>\d+)\]',
            'S(?P<season>\d+)E(?P<episode>\d+)',
            'Season (?P<season>\d+)(.+)Episode (?P<episode>\d+)',
            'Episode (?P<episode>\d+)'
        ]
        for regex in season_episode_regex:
            re_match = re.search(regex, video_item.get_name())
            if re_match:
                if 'season' in re_match.groupdict():
                    video_item.set_season(int(re_match.group('season')))
                    pass

                if 'episode' in re_match.groupdict():
                    video_item.set_episode(int(re_match.group('episode')))
                    pass
                break
            pass

        # plot
        channel_name = snippet.get('channelTitle', '')
        description = kodion.utils.strip_html_from_text(snippet['description'])
        if channel_name and settings.get_bool(
                'youtube.view.description.show_channel_name', True):
            description = '[UPPERCASE][B]%s[/B][/UPPERCASE][CR][CR]%s' % (
                channel_name, description)
            pass
        video_item.set_studio(channel_name)
        # video_item.add_cast(channel_name)
        video_item.add_artist(channel_name)
        video_item.set_plot(description)

        # date time
        datetime = iso8601.parse(snippet['publishedAt'])
        video_item.set_year(datetime.year)
        video_item.set_aired(datetime.year, datetime.month, datetime.day)
        video_item.set_premiered(datetime.year, datetime.month, datetime.day)

        # duration
        duration = yt_item.get('contentDetails', {}).get('duration', '')
        duration = iso8601.parse(duration)
        video_item.set_duration_from_seconds(duration.seconds)

        # try to find a better resolution for the image
        thumbnails = snippet.get('thumbnails', {})
        thumbnail_sizes = ['high', 'medium', 'default']
        for thumbnail_size in thumbnail_sizes:
            image = thumbnails.get(thumbnail_size, {}).get('url', '')
            if image:
                video_item.set_image(image)
                break
            pass

        # update context menu and channel mapping
        channel_id = snippet.get('channelId', '')
        if channel_id_dict is not None:
            if not channel_id in channel_id_dict:
                channel_id_dict[channel_id] = []
            channel_id_dict[channel_id].append(video_item)
            pass

        context_menu = []
        replace_context_menu = False

        # Refresh ('My Subscriptions', all my playlists)
        if context.get_path(
        ) == '/special/new_uploaded_videos/' or context.get_path().startswith(
                '/channel/mine/playlist/'):
            yt_context_menu.append_refresh(context_menu, provider, context)
            pass

        # Queue Video
        yt_context_menu.append_queue_video(context_menu, provider, context)

        # play all videos of the playlist
        some_playlist_match = re.match(
            '^/channel/(.+)/playlist/(?P<playlist_id>.*)/$',
            context.get_path())
        if some_playlist_match:
            replace_context_menu = True
            playlist_id = some_playlist_match.group('playlist_id')

            yt_context_menu.append_play_all_from_playlist(
                context_menu, provider, context, playlist_id, video_id)
            yt_context_menu.append_play_all_from_playlist(
                context_menu, provider, context, playlist_id)
            pass

        # 'play with...' (external player)
        if context.get_settings().is_support_alternative_player_enabled():
            yt_context_menu.append_play_with(context_menu, provider, context)
            pass

        if provider.is_logged_in():
            # add 'Watch Later' only if we are not in my 'Watch Later' list
            watch_later_playlist_id = my_playlists.get('watchLater', '')
            yt_context_menu.append_watch_later(context_menu, provider, context,
                                               watch_later_playlist_id,
                                               video_id)
            pass

        # got to [CHANNEL]
        if channel_id and channel_name:
            # only if we are not directly in the channel provide a jump to the channel
            if kodion.utils.create_path('channel',
                                        channel_id) != context.get_path():
                yt_context_menu.append_go_to_channel(context_menu, provider,
                                                     context, channel_id,
                                                     channel_name)
                pass
            pass

        # find related videos
        yt_context_menu.append_related_videos(context_menu, provider, context,
                                              video_id)

        if provider.is_logged_in():
            # add 'Like Video' only if we are not in my 'Liked Videos' list
            refresh_container = context.get_path().startswith(
                '/channel/mine/playlist/LL') or context.get_path(
                ) == '/special/disliked_videos/'
            yt_context_menu.append_rate_video(context_menu, provider, context,
                                              video_id, refresh_container)

            # add video to a selected playlist
            yt_context_menu.append_add_video_to_playlist(
                context_menu, provider, context, video_id)

            # provide 'remove' for videos in my playlists
            if video_id in playlist_item_id_dict:
                playlist_match = re.match(
                    '^/channel/mine/playlist/(?P<playlist_id>.*)/$',
                    context.get_path())
                if playlist_match:
                    playlist_id = playlist_match.group('playlist_id')
                    # we support all playlist except 'Watch History'
                    if not playlist_id.startswith('HL'):
                        playlist_item_id = playlist_item_id_dict[video_id]
                        context_menu.append(
                            (context.localize(
                                provider.LOCAL_MAP['youtube.remove']),
                             'RunPlugin(%s)' % context.create_uri(
                                 ['playlist', 'remove', 'video'], {
                                     'playlist_id': playlist_id,
                                     'video_id': playlist_item_id,
                                     'video_name': video_item.get_name()
                                 })))
                        pass
                    pass
                pass

            # subscribe to the channel of the video
            yt_context_menu.append_subscribe_to_channel(
                context_menu, provider, context, channel_id, channel_name)
            pass

        if len(context_menu) > 0:
            video_item.set_context_menu(context_menu,
                                        replace=replace_context_menu)
            pass
        pass

    pass
def update_video_infos(provider, context, video_id_dict, playlist_item_id_dict=None, channel_items_dict=None):
    settings = context.get_settings()

    video_ids = list(video_id_dict.keys())
    if len(video_ids) == 0:
        return

    if not playlist_item_id_dict:
        playlist_item_id_dict = {}
        pass

    resource_manager = provider.get_resource_manager(context)
    video_data = resource_manager.get_videos(video_ids)

    my_playlists = {}
    if provider.is_logged_in():
        my_playlists = resource_manager.get_related_playlists(channel_id='mine')
        pass

    for video_id in video_data.keys():
        yt_item = video_data[video_id]
        video_item = video_id_dict[video_id]

        snippet = yt_item['snippet']  # crash if not conform

        # set uses_dash
        video_item.set_use_dash(context.get_settings().use_dash())

        # set mediatype
        video_item.set_mediatype('video')  # using video

        # set the title
        video_item.set_title(snippet['title'])

        """
        This is experimental. We try to get the most information out of the title of a video.
        This is not based on any language. In some cases this won't work at all.
        TODO: via language and settings provide the regex for matching episode and season.
        """
        #video_item.set_season(1)
        #video_item.set_episode(1)
        for regex in __RE_SEASON_EPISODE_MATCHES__:
            re_match = regex.search(video_item.get_name())
            if re_match:
                if 'season' in re_match.groupdict():
                    video_item.set_season(int(re_match.group('season')))
                    pass

                if 'episode' in re_match.groupdict():
                    video_item.set_episode(int(re_match.group('episode')))
                    pass
                break
            pass

        # plot
        channel_name = snippet.get('channelTitle', '')
        description = kodion.utils.strip_html_from_text(snippet['description'])
        if channel_name and settings.get_bool('youtube.view.description.show_channel_name', True):
            description = '[UPPERCASE][B]%s[/B][/UPPERCASE][CR][CR]%s' % (channel_name, description)
            pass
        video_item.set_studio(channel_name)
        # video_item.add_cast(channel_name)
        video_item.add_artist(channel_name)
        video_item.set_plot(description)

        # date time
        datetime = utils.datetime_parser.parse(snippet['publishedAt'])
        video_item.set_year_from_datetime(datetime)
        video_item.set_aired_from_datetime(datetime)
        video_item.set_premiered_from_datetime(datetime)
        video_item.set_date_from_datetime(datetime)

        # duration
        duration = yt_item.get('contentDetails', {}).get('duration', '')
        duration = utils.datetime_parser.parse(duration)
        # we subtract 1 seconds because YouTube returns +1 second to much
        video_item.set_duration_from_seconds(duration.seconds - 1)

        # try to find a better resolution for the image
        thumbnails = snippet.get('thumbnails', {})
        thumbnail_sizes = ['high', 'medium', 'default']
        for thumbnail_size in thumbnail_sizes:
            image = thumbnails.get(thumbnail_size, {}).get('url', '')
            if image:
                video_item.set_image(image)
                break
            pass

        # set fanart
        video_item.set_fanart(provider.get_fanart(context))

        # update channel mapping
        channel_id = snippet.get('channelId', '')
        if channel_items_dict is not None:
            if not channel_id in channel_items_dict:
                channel_items_dict[channel_id] = []
            channel_items_dict[channel_id].append(video_item)
            pass

        context_menu = []
        replace_context_menu = False

        # Refresh ('My Subscriptions')
        if context.get_path() == '/special/new_uploaded_videos_tv/' or context.get_path().startswith(
                '/channel/mine/playlist/'):
            yt_context_menu.append_refresh(context_menu, provider, context)
            pass

        # Queue Video
        yt_context_menu.append_queue_video(context_menu, provider, context)

        """
        Play all videos of the playlist.

        /channel/[CHANNEL_ID]/playlist/[PLAYLIST_ID]/
        /playlist/[PLAYLIST_ID]/
        """
        some_playlist_match = re.match(r'^(/channel/(.+))?/playlist/(?P<playlist_id>.*)/$', context.get_path())
        if some_playlist_match:
            replace_context_menu = True
            playlist_id = some_playlist_match.group('playlist_id')

            yt_context_menu.append_play_all_from_playlist(context_menu, provider, context, playlist_id, video_id)
            yt_context_menu.append_play_all_from_playlist(context_menu, provider, context, playlist_id)
            pass

        # 'play with...' (external player)
        if context.get_settings().is_support_alternative_player_enabled():
            yt_context_menu.append_play_with(context_menu, provider, context)
            pass

        if provider.is_logged_in():
            # add 'Watch Later' only if we are not in my 'Watch Later' list
            watch_later_playlist_id = my_playlists.get('watchLater', '')
            yt_context_menu.append_watch_later(context_menu, provider, context, watch_later_playlist_id, video_id)

            # provide 'remove' for videos in my playlists
            if video_id in playlist_item_id_dict:
                playlist_match = re.match('^/channel/mine/playlist/(?P<playlist_id>.*)/$', context.get_path())
                if playlist_match:
                    playlist_id = playlist_match.group('playlist_id')
                    # we support all playlist except 'Watch History'
                    if not playlist_id.startswith('HL'):
                        playlist_item_id = playlist_item_id_dict[video_id]
                        context_menu.append((context.localize(provider.LOCAL_MAP['youtube.remove']),
                                             'RunPlugin(%s)' % context.create_uri(
                                                 ['playlist', 'remove', 'video'],
                                                 {'playlist_id': playlist_id, 'video_id': playlist_item_id,
                                                  'video_name': video_item.get_name()})))
                        pass
                    pass
                pass
            pass

        # got to [CHANNEL]
        if channel_id and channel_name:
            # only if we are not directly in the channel provide a jump to the channel
            if kodion.utils.create_path('channel', channel_id) != context.get_path():
                yt_context_menu.append_go_to_channel(context_menu, provider, context, channel_id, channel_name)
                pass
            pass

        if provider.is_logged_in():
            # subscribe to the channel of the video
            yt_context_menu.append_subscribe_to_channel(context_menu, provider, context, channel_id, channel_name)
            pass

        # more...
        refresh_container = context.get_path().startswith(
            '/channel/mine/playlist/LL') or context.get_path() == '/special/disliked_videos/'
        yt_context_menu.append_more_for_video(context_menu, provider, context, video_id,
                                              is_logged_in=provider.is_logged_in(),
                                              refresh_container=refresh_container)

        if len(context_menu) > 0:
            video_item.set_context_menu(context_menu, replace=replace_context_menu)
            pass
        pass

    pass
Exemple #5
0
def _process_list_response(provider, context, json_data):
    video_id_dict = {}
    channel_id_dict = {}
    playlist_item_id_dict = {}

    result = []

    yt_items = json_data.get('items', [])
    if len(yt_items) == 0:
        context.log_warning('List of search result is empty')
        return result

    for yt_item in yt_items:
        yt_kind = yt_item.get('kind', '')
        if yt_kind == u'youtube#video':
            video_id = yt_item['id']
            snippet = yt_item['snippet']
            title = snippet['title']
            image = snippet.get('thumbnails', {}).get('medium',
                                                      {}).get('url', '')
            video_item = items.VideoItem(title,
                                         context.create_uri(
                                             ['play'], {'video_id': video_id}),
                                         image=image)
            video_item.set_fanart(provider.get_fanart(context))
            result.append(video_item)
            video_id_dict[video_id] = video_item
            pass
        elif yt_kind == u'youtube#channel':
            channel_id = yt_item['id']
            snippet = yt_item['snippet']
            title = snippet['title']
            image = snippet.get('thumbnails', {}).get('medium',
                                                      {}).get('url', '')

            channel_item = items.DirectoryItem(title,
                                               context.create_uri(
                                                   ['channel', channel_id]),
                                               image=image)
            channel_item.set_fanart(provider.get_fanart(context))

            # if logged in => provide subscribing to the channel
            if provider.is_logged_in():
                context_menu = []
                yt_context_menu.append_subscribe_to_channel(
                    context_menu, provider, context, channel_id)
                channel_item.set_context_menu(context_menu)
                pass
            result.append(channel_item)

            # map channel
            if not channel_id in channel_id_dict:
                channel_id_dict[channel_id] = []
            channel_id_dict[channel_id].append(channel_item)
            pass
        elif yt_kind == u'youtube#guideCategory':
            guide_id = yt_item['id']
            snippet = yt_item['snippet']
            title = snippet['title']

            guide_item = items.DirectoryItem(
                title,
                context.create_uri(['special', 'browse_channels'],
                                   {'guide_id': guide_id}))
            guide_item.set_fanart(provider.get_fanart(context))
            result.append(guide_item)
            pass
        elif yt_kind == u'youtube#subscription':
            snippet = yt_item['snippet']
            image = snippet.get('thumbnails', {}).get('high',
                                                      {}).get('url', '')
            channel_id = snippet['resourceId']['channelId']
            playlist_item = items.DirectoryItem(snippet['title'],
                                                context.create_uri(
                                                    ['channel', channel_id]),
                                                image=image)
            playlist_item.set_fanart(provider.get_fanart(context))

            # unsubscribe from a channel
            subscription_id = yt_item['id']
            context_menu = []
            yt_context_menu.append_unsubscribe_from_channel(
                context_menu, provider, context, subscription_id)
            playlist_item.set_context_menu(context_menu)

            result.append(playlist_item)

            # map playlist to channel
            if not channel_id in channel_id_dict:
                channel_id_dict[channel_id] = []
            channel_id_dict[channel_id].append(playlist_item)
            pass
        elif yt_kind == u'youtube#playlist':
            playlist_id = yt_item['id']
            snippet = yt_item['snippet']
            title = snippet['title']
            image = snippet.get('thumbnails', {}).get('medium',
                                                      {}).get('url', '')

            channel_id = snippet['channelId']

            # if the path directs to a playlist of our own, we correct the channel id to 'mine'
            if context.get_path() == '/channel/mine/playlists/':
                channel_id = 'mine'
                pass
            playlist_item = items.DirectoryItem(title,
                                                context.create_uri([
                                                    'channel', channel_id,
                                                    'playlist', playlist_id
                                                ]),
                                                image=image)
            playlist_item.set_fanart(provider.get_fanart(context))

            channel_name = snippet.get('channelTitle', '')
            if provider.is_logged_in():
                context_menu = []

                # play all videos of the playlist
                yt_context_menu.append_play_all_from_playlist(
                    context_menu, provider, context, playlist_id)

                if channel_id != 'mine':
                    # subscribe to the channel via the playlist item
                    yt_context_menu.append_subscribe_to_channel(
                        context_menu, provider, context, channel_id,
                        channel_name)
                    pass
                else:
                    # remove my playlist
                    yt_context_menu.append_delete_playlist(
                        context_menu, provider, context, playlist_id, title)

                    # rename playlist
                    yt_context_menu.append_rename_playlist(
                        context_menu, provider, context, playlist_id, title)
                    pass

                playlist_item.set_context_menu(context_menu)
                pass

            result.append(playlist_item)

            # map playlist to channel
            if not channel_id in channel_id_dict:
                channel_id_dict[channel_id] = []
            channel_id_dict[channel_id].append(playlist_item)
            pass
        elif yt_kind == u'youtube#playlistItem':
            snippet = yt_item['snippet']
            video_id = snippet['resourceId']['videoId']

            # store the id of the playlistItem - for deleting this item we need this item
            playlist_item_id_dict[video_id] = yt_item['id']

            title = snippet['title']
            image = snippet.get('thumbnails', {}).get('medium',
                                                      {}).get('url', '')
            video_item = items.VideoItem(title,
                                         context.create_uri(
                                             ['play'], {'video_id': video_id}),
                                         image=image)
            video_item.set_fanart(provider.get_fanart(context))
            result.append(video_item)
            video_id_dict[video_id] = video_item
            pass
        elif yt_kind == 'youtube#searchResult':
            yt_kind = yt_item.get('id', {}).get('kind', '')

            # video
            if yt_kind == 'youtube#video':
                video_id = yt_item['id']['videoId']
                snippet = yt_item['snippet']
                title = snippet['title']
                image = snippet.get('thumbnails', {}).get('medium',
                                                          {}).get('url', '')
                video_item = items.VideoItem(
                    title,
                    context.create_uri(['play'], {'video_id': video_id}),
                    image=image)
                video_item.set_fanart(provider.get_fanart(context))
                result.append(video_item)
                video_id_dict[video_id] = video_item
                pass
            # playlist
            elif yt_kind == 'youtube#playlist':
                playlist_id = yt_item['id']['playlistId']
                snippet = yt_item['snippet']
                title = snippet['title']
                image = snippet.get('thumbnails', {}).get('medium',
                                                          {}).get('url', '')

                channel_id = snippet['channelId']
                # if the path directs to a playlist of our own, we correct the channel id to 'mine'
                if context.get_path() == '/channel/mine/playlists/':
                    channel_id = 'mine'
                    pass
                channel_name = snippet.get('channelTitle', '')
                playlist_item = items.DirectoryItem(title,
                                                    context.create_uri([
                                                        'channel', channel_id,
                                                        'playlist', playlist_id
                                                    ]),
                                                    image=image)
                playlist_item.set_fanart(provider.get_fanart(context))

                context_menu = []

                # play all videos of the playlist
                yt_context_menu.append_play_all_from_playlist(
                    context_menu, provider, context, playlist_id)

                if provider.is_logged_in():
                    # subscribe to the channel of the playlist
                    yt_context_menu.append_subscribe_to_channel(
                        context_menu, provider, context, channel_id,
                        channel_name)
                    pass
                if len(context_menu) > 0:
                    playlist_item.set_context_menu(context_menu)
                    pass

                result.append(playlist_item)

                # map playlist to channel
                if not channel_id in channel_id_dict:
                    channel_id_dict[channel_id] = []
                channel_id_dict[channel_id].append(playlist_item)
                pass
            elif yt_kind == 'youtube#channel':
                channel_id = yt_item['id']['channelId']
                snippet = yt_item['snippet']
                title = snippet['title']
                image = snippet.get('thumbnails', {}).get('medium',
                                                          {}).get('url', '')

                channel_item = items.DirectoryItem(
                    title,
                    context.create_uri(['channel', channel_id]),
                    image=image)
                channel_item.set_fanart(provider.get_fanart(context))

                # subscribe to the channel
                if provider.is_logged_in():
                    context_menu = []
                    yt_context_menu.append_subscribe_to_channel(
                        context_menu, provider, context, channel_id)
                    channel_item.set_context_menu(context_menu)
                    pass

                result.append(channel_item)

                # map channel
                if not channel_id in channel_id_dict:
                    channel_id_dict[channel_id] = []
                channel_id_dict[channel_id].append(channel_item)
                pass
            else:
                raise kodion.KodionException("Unknown kind '%s'" % yt_kind)
            pass
        else:
            raise kodion.KodionException("Unknown kind '%s'" % yt_kind)
        pass

    # this will also update the channel_id_dict with the correct channel id for each video.
    utils.update_video_infos(provider, context, video_id_dict,
                             playlist_item_id_dict, channel_id_dict)
    utils.update_channel_infos(provider, context, channel_id_dict)
    return result
Exemple #6
0
def make_video_item_from_json_data(context, provider, json_data, playlist_item_id_dict={}):
    video_id = json_data['id']
    video_item = VideoItem(json_data['title'],
                           uri=context.create_uri(['play'], {'video_id': video_id}))

    video_item.set_image(json_data.get('image', ''))

    """
    This is experimental. We try to get the most information out of the title of a video.
    This is not based on any language. In some cases this won't work at all.
    TODO: via language and settings provide the regex for matching episode and season.
    """
    video_item.set_season(1)
    video_item.set_episode(1)
    for regex in __RE_SEASON_EPISODE_MATCHES__:
        re_match = regex.search(video_item.get_name())
        if re_match:
            if 'season' in re_match.groupdict():
                video_item.set_season(int(re_match.group('season')))
                pass

            if 'episode' in re_match.groupdict():
                video_item.set_episode(int(re_match.group('episode')))
                pass
            break
        pass

    settings = context.get_settings()

    # plot
    channel_name = json_data.get('channel-title', '')
    description = kodion.utils.strip_html_from_text(json_data.get('description', ''))
    if channel_name and settings.get_bool('youtube.view.description.show_channel_name', True):
        description = '[UPPERCASE][B]%s[/B][/UPPERCASE][CR][CR]%s' % (channel_name, description)
        pass
    video_item.set_studio(channel_name)
    # video_item.add_cast(channel_name)
    video_item.add_artist(channel_name)
    video_item.set_plot(description)

    # date time
    date_str = json_data.get('date', '')
    if date_str:
        datetime = utils.datetime_parser.parse()
        video_item.set_year_from_datetime(datetime)
        video_item.set_aired_from_datetime(datetime)
        video_item.set_premiered_from_datetime(datetime)
        pass

    # duration
    duration = json_data.get('duration', '')
    if duration:
        duration = utils.datetime_parser.parse(duration)
        # we subtract 1 seconds because YouTube returns +1 second to much
        video_item.set_duration_from_seconds(duration.seconds - 1)
        pass

    # set fanart
    video_item.set_fanart(provider.get_fanart(context))

    context_menu = []
    replace_context_menu = False

    # Refresh ('My Subscriptions', all my playlists)
    if context.get_path() == '/special/new_uploaded_videos/' or context.get_path().startswith(
            '/channel/mine/playlist/'):
        yt_context_menu.append_refresh(context_menu, provider, context)
        pass

    # Queue Video
    yt_context_menu.append_queue_video(context_menu, provider, context)

    # play all videos of the playlist
    some_playlist_match = re.match('^/channel/(.+)/playlist/(?P<playlist_id>.*)/$', context.get_path())
    if some_playlist_match:
        replace_context_menu = True
        playlist_id = some_playlist_match.group('playlist_id')

        yt_context_menu.append_play_all_from_playlist(context_menu, provider, context, playlist_id, video_id)
        yt_context_menu.append_play_all_from_playlist(context_menu, provider, context, playlist_id)
        pass

    # 'play with...' (external player)
    if context.get_settings().is_support_alternative_player_enabled():
        yt_context_menu.append_play_with(context_menu, provider, context)
        pass

    my_playlists = {}
    if provider.is_logged_in():
        resource_manager = provider.get_resource_manager(context)
        my_playlists = resource_manager.get_related_playlists(channel_id='mine')
        pass

    if provider.is_logged_in():
        # add 'Watch Later' only if we are not in my 'Watch Later' list
        watch_later_playlist_id = my_playlists.get('watchLater', '')
        yt_context_menu.append_watch_later(context_menu, provider, context, watch_later_playlist_id, video_id)
        pass

    channel_id = json_data.get('channel-id', '')

    # got to [CHANNEL]
    if channel_id and channel_name:
        # only if we are not directly in the channel provide a jump to the channel
        if kodion.utils.create_path('channel', channel_id) != context.get_path():
            yt_context_menu.append_go_to_channel(context_menu, provider, context, channel_id, channel_name)
            pass
        pass

    # description links
    yt_context_menu.append_content_from_description(context_menu, provider, context, video_id)

    # find related videos
    yt_context_menu.append_related_videos(context_menu, provider, context, video_id)

    if provider.is_logged_in():
        # add 'Like Video' only if we are not in my 'Liked Videos' list
        refresh_container = context.get_path().startswith(
            '/channel/mine/playlist/LL') or context.get_path() == '/special/disliked_videos/'
        yt_context_menu.append_rate_video(context_menu, provider, context, video_id, refresh_container)

        # add video to a selected playlist
        yt_context_menu.append_add_video_to_playlist(context_menu, provider, context, video_id)

        # provide 'remove' for videos in my playlists
        if video_id in playlist_item_id_dict:
            playlist_match = re.match('^/channel/mine/playlist/(?P<playlist_id>.*)/$', context.get_path())
            if playlist_match:
                playlist_id = playlist_match.group('playlist_id')
                # we support all playlist except 'Watch History'
                if not playlist_id.startswith('HL'):
                    playlist_item_id = playlist_item_id_dict[video_id]
                    context_menu.append((context.localize(provider.LOCAL_MAP['youtube.remove']),
                                         'RunPlugin(%s)' % context.create_uri(
                                             ['playlist', 'remove', 'video'],
                                             {'playlist_id': playlist_id, 'video_id': playlist_item_id,
                                              'video_name': video_item.get_name()})))
                    pass
                pass
            pass

        # subscribe to the channel of the video
        yt_context_menu.append_subscribe_to_channel(context_menu, provider, context, channel_id, channel_name)
        pass

    if len(context_menu) > 0:
        video_item.set_context_menu(context_menu, replace=replace_context_menu)
        pass

    return video_item
Exemple #7
0
def _process_list_response(provider, context, json_data):
    video_id_dict = {}
    channel_id_dict = {}
    playlist_item_id_dict = {}

    result = []

    yt_items = json_data.get('items', [])
    if len(yt_items) == 0:
        context.log_warning('List of search result is empty')
        return result

    for yt_item in yt_items:
        yt_kind = yt_item.get('kind', '')
        if yt_kind == u'youtube#video':
            video_id = yt_item['id']
            snippet = yt_item['snippet']
            title = snippet['title']
            image = snippet.get('thumbnails', {}).get('medium', {}).get('url', '')
            video_item = items.VideoItem(title,
                                         context.create_uri(['play'], {'video_id': video_id}),
                                         image=image)
            video_item.set_fanart(provider.get_fanart(context))
            result.append(video_item)
            video_id_dict[video_id] = video_item
            pass
        elif yt_kind == u'youtube#channel':
            channel_id = yt_item['id']
            snippet = yt_item['snippet']
            title = snippet['title']
            image = snippet.get('thumbnails', {}).get('medium', {}).get('url', '')

            channel_item = items.DirectoryItem(title,
                                               context.create_uri(['channel', channel_id]),
                                               image=image)
            channel_item.set_fanart(provider.get_fanart(context))

            # if logged in => provide subscribing to the channel
            if provider.is_logged_in():
                context_menu = []
                yt_context_menu.append_subscribe_to_channel(context_menu, provider, context, channel_id)
                channel_item.set_context_menu(context_menu)
                pass
            result.append(channel_item)

            # map channel
            if not channel_id in channel_id_dict:
                channel_id_dict[channel_id] = []
            channel_id_dict[channel_id].append(channel_item)
            pass
        elif yt_kind == u'youtube#guideCategory':
            guide_id = yt_item['id']
            snippet = yt_item['snippet']
            title = snippet['title']

            guide_item = items.DirectoryItem(title,
                                             context.create_uri(['special', 'browse_channels'], {'guide_id': guide_id}))
            guide_item.set_fanart(provider.get_fanart(context))
            result.append(guide_item)
            pass
        elif yt_kind == u'youtube#subscription':
            snippet = yt_item['snippet']
            image = snippet.get('thumbnails', {}).get('high', {}).get('url', '')
            channel_id = snippet['resourceId']['channelId']
            playlist_item = items.DirectoryItem(snippet['title'],
                                                context.create_uri(['channel', channel_id]),
                                                image=image)
            playlist_item.set_fanart(provider.get_fanart(context))

            # unsubscribe from a channel
            subscription_id = yt_item['id']
            context_menu = []
            yt_context_menu.append_unsubscribe_from_channel(context_menu, provider, context, subscription_id)
            playlist_item.set_context_menu(context_menu)

            result.append(playlist_item)

            # map playlist to channel
            if not channel_id in channel_id_dict:
                channel_id_dict[channel_id] = []
            channel_id_dict[channel_id].append(playlist_item)
            pass
        elif yt_kind == u'youtube#playlist':
            playlist_id = yt_item['id']
            snippet = yt_item['snippet']
            title = snippet['title']
            image = snippet.get('thumbnails', {}).get('medium', {}).get('url', '')

            channel_id = snippet['channelId']

            # if the path directs to a playlist of our own, we correct the channel id to 'mine'
            if context.get_path() == '/channel/mine/playlists/':
                channel_id = 'mine'
                pass
            playlist_item = items.DirectoryItem(title,
                                                context.create_uri(['channel', channel_id, 'playlist', playlist_id]),
                                                image=image)
            playlist_item.set_fanart(provider.get_fanart(context))

            channel_name = snippet.get('channelTitle', '')
            if provider.is_logged_in():
                context_menu = []

                # play all videos of the playlist
                yt_context_menu.append_play_all_from_playlist(context_menu, provider, context, playlist_id)

                if channel_id != 'mine':
                    # subscribe to the channel via the playlist item
                    yt_context_menu.append_subscribe_to_channel(context_menu, provider, context, channel_id,
                                                                channel_name)
                    pass
                else:
                    # remove my playlist
                    yt_context_menu.append_delete_playlist(context_menu, provider, context, playlist_id, title)

                    # rename playlist
                    yt_context_menu.append_rename_playlist(context_menu, provider, context, playlist_id, title)
                    pass

                playlist_item.set_context_menu(context_menu)
                pass

            result.append(playlist_item)

            # map playlist to channel
            if not channel_id in channel_id_dict:
                channel_id_dict[channel_id] = []
            channel_id_dict[channel_id].append(playlist_item)
            pass
        elif yt_kind == u'youtube#playlistItem':
            snippet = yt_item['snippet']
            video_id = snippet['resourceId']['videoId']

            # store the id of the playlistItem - for deleting this item we need this item
            playlist_item_id_dict[video_id] = yt_item['id']

            title = snippet['title']
            image = snippet.get('thumbnails', {}).get('medium', {}).get('url', '')
            video_item = items.VideoItem(title,
                                         context.create_uri(['play'], {'video_id': video_id}),
                                         image=image)
            video_item.set_fanart(provider.get_fanart(context))
            result.append(video_item)
            video_id_dict[video_id] = video_item
            pass
        elif yt_kind == 'youtube#searchResult':
            yt_kind = yt_item.get('id', {}).get('kind', '')

            # video
            if yt_kind == 'youtube#video':
                video_id = yt_item['id']['videoId']
                snippet = yt_item['snippet']
                title = snippet['title']
                image = snippet.get('thumbnails', {}).get('medium', {}).get('url', '')
                video_item = items.VideoItem(title,
                                             context.create_uri(['play'], {'video_id': video_id}),
                                             image=image)
                video_item.set_fanart(provider.get_fanart(context))
                result.append(video_item)
                video_id_dict[video_id] = video_item
                pass
            # playlist
            elif yt_kind == 'youtube#playlist':
                playlist_id = yt_item['id']['playlistId']
                snippet = yt_item['snippet']
                title = snippet['title']
                image = snippet.get('thumbnails', {}).get('medium', {}).get('url', '')

                channel_id = snippet['channelId']
                # if the path directs to a playlist of our own, we correct the channel id to 'mine'
                if context.get_path() == '/channel/mine/playlists/':
                    channel_id = 'mine'
                    pass
                channel_name = snippet.get('channelTitle', '')
                playlist_item = items.DirectoryItem(title,
                                                    context.create_uri(
                                                        ['channel', channel_id, 'playlist', playlist_id]),
                                                    image=image)
                playlist_item.set_fanart(provider.get_fanart(context))


                context_menu = []

                # play all videos of the playlist
                yt_context_menu.append_play_all_from_playlist(context_menu, provider, context, playlist_id)

                if provider.is_logged_in():
                    # subscribe to the channel of the playlist
                    yt_context_menu.append_subscribe_to_channel(context_menu, provider, context, channel_id,
                                                                channel_name)
                    pass
                if len(context_menu) > 0:
                    playlist_item.set_context_menu(context_menu)
                    pass

                result.append(playlist_item)

                # map playlist to channel
                if not channel_id in channel_id_dict:
                    channel_id_dict[channel_id] = []
                channel_id_dict[channel_id].append(playlist_item)
                pass
            elif yt_kind == 'youtube#channel':
                channel_id = yt_item['id']['channelId']
                snippet = yt_item['snippet']
                title = snippet['title']
                image = snippet.get('thumbnails', {}).get('medium', {}).get('url', '')

                channel_item = items.DirectoryItem(title,
                                                   context.create_uri(['channel', channel_id]),
                                                   image=image)
                channel_item.set_fanart(provider.get_fanart(context))

                # subscribe to the channel
                if provider.is_logged_in():
                    context_menu = []
                    yt_context_menu.append_subscribe_to_channel(context_menu, provider, context, channel_id)
                    channel_item.set_context_menu(context_menu)
                    pass

                result.append(channel_item)

                # map channel
                if not channel_id in channel_id_dict:
                    channel_id_dict[channel_id] = []
                channel_id_dict[channel_id].append(channel_item)
                pass
            else:
                raise kodion.KodionException("Unknown kind '%s'" % yt_kind)
            pass
        else:
            raise kodion.KodionException("Unknown kind '%s'" % yt_kind)
        pass

    # this will also update the channel_id_dict with the correct channel id for each video.
    utils.update_video_infos(provider, context, video_id_dict, playlist_item_id_dict, channel_id_dict)
    utils.update_channel_infos(provider, context, channel_id_dict)
    return result
Exemple #8
0
def update_video_infos(provider,
                       context,
                       video_id_dict,
                       playlist_item_id_dict=None,
                       channel_items_dict=None):
    settings = context.get_settings()

    video_ids = list(video_id_dict.keys())
    if len(video_ids) == 0:
        return

    if not playlist_item_id_dict:
        playlist_item_id_dict = {}
        pass

    resource_manager = provider.get_resource_manager(context)
    video_data = resource_manager.get_videos(video_ids)

    my_playlists = {}
    if provider.is_logged_in():
        my_playlists = resource_manager.get_related_playlists(
            channel_id='mine')
        pass

    for video_id in video_data.keys():
        yt_item = video_data[video_id]
        video_item = video_id_dict[video_id]

        snippet = yt_item['snippet']  # crash if not conform

        # set uses_dash
        video_item.set_use_dash(context.get_settings().use_dash())

        # set mediatype
        video_item.set_mediatype(
            'episode'
        )  # using episode since all setContent is currently episode as well

        # set the title
        video_item.set_title(snippet['title'])
        """
        This is experimental. We try to get the most information out of the title of a video.
        This is not based on any language. In some cases this won't work at all.
        TODO: via language and settings provide the regex for matching episode and season.
        """
        #video_item.set_season(1)
        #video_item.set_episode(1)
        for regex in __RE_SEASON_EPISODE_MATCHES__:
            re_match = regex.search(video_item.get_name())
            if re_match:
                if 'season' in re_match.groupdict():
                    video_item.set_season(int(re_match.group('season')))
                    pass

                if 'episode' in re_match.groupdict():
                    video_item.set_episode(int(re_match.group('episode')))
                    pass
                break
            pass

        # plot
        channel_name = snippet.get('channelTitle', '')
        description = kodion.utils.strip_html_from_text(snippet['description'])
        if channel_name and settings.get_bool(
                'youtube.view.description.show_channel_name', True):
            description = '[UPPERCASE][B]%s[/B][/UPPERCASE][CR][CR]%s' % (
                channel_name, description)
            pass
        video_item.set_studio(channel_name)
        # video_item.add_cast(channel_name)
        video_item.add_artist(channel_name)
        video_item.set_plot(description)

        # date time
        datetime = utils.datetime_parser.parse(snippet['publishedAt'])
        video_item.set_year_from_datetime(datetime)
        video_item.set_aired_from_datetime(datetime)
        video_item.set_premiered_from_datetime(datetime)
        video_item.set_date_from_datetime(datetime)

        # duration
        duration = yt_item.get('contentDetails', {}).get('duration', '')
        duration = utils.datetime_parser.parse(duration)
        # we subtract 1 seconds because YouTube returns +1 second to much
        video_item.set_duration_from_seconds(duration.seconds - 1)

        # try to find a better resolution for the image
        thumbnails = snippet.get('thumbnails', {})
        thumbnail_sizes = ['high', 'medium', 'default']
        for thumbnail_size in thumbnail_sizes:
            image = thumbnails.get(thumbnail_size, {}).get('url', '')
            if image:
                video_item.set_image(image)
                break
            pass

        # set fanart
        video_item.set_fanart(provider.get_fanart(context))

        # update channel mapping
        channel_id = snippet.get('channelId', '')
        if channel_items_dict is not None:
            if not channel_id in channel_items_dict:
                channel_items_dict[channel_id] = []
            channel_items_dict[channel_id].append(video_item)
            pass

        context_menu = []
        replace_context_menu = False

        # Refresh ('My Subscriptions')
        if context.get_path(
        ) == '/special/new_uploaded_videos_tv/' or context.get_path(
        ).startswith('/channel/mine/playlist/'):
            yt_context_menu.append_refresh(context_menu, provider, context)
            pass

        # Queue Video
        yt_context_menu.append_queue_video(context_menu, provider, context)
        """
        Play all videos of the playlist.

        /channel/[CHANNEL_ID]/playlist/[PLAYLIST_ID]/
        /playlist/[PLAYLIST_ID]/
        """
        some_playlist_match = re.match(
            r'^(/channel/(.+))?/playlist/(?P<playlist_id>.*)/$',
            context.get_path())
        if some_playlist_match:
            replace_context_menu = True
            playlist_id = some_playlist_match.group('playlist_id')

            yt_context_menu.append_play_all_from_playlist(
                context_menu, provider, context, playlist_id, video_id)
            yt_context_menu.append_play_all_from_playlist(
                context_menu, provider, context, playlist_id)
            pass

        # 'play with...' (external player)
        if context.get_settings().is_support_alternative_player_enabled():
            yt_context_menu.append_play_with(context_menu, provider, context)
            pass

        if provider.is_logged_in():
            # add 'Watch Later' only if we are not in my 'Watch Later' list
            watch_later_playlist_id = my_playlists.get('watchLater', '')
            yt_context_menu.append_watch_later(context_menu, provider, context,
                                               watch_later_playlist_id,
                                               video_id)

            # provide 'remove' for videos in my playlists
            if video_id in playlist_item_id_dict:
                playlist_match = re.match(
                    '^/channel/mine/playlist/(?P<playlist_id>.*)/$',
                    context.get_path())
                if playlist_match:
                    playlist_id = playlist_match.group('playlist_id')
                    # we support all playlist except 'Watch History'
                    if not playlist_id.startswith('HL'):
                        playlist_item_id = playlist_item_id_dict[video_id]
                        context_menu.append(
                            (context.localize(
                                provider.LOCAL_MAP['youtube.remove']),
                             'RunPlugin(%s)' % context.create_uri(
                                 ['playlist', 'remove', 'video'], {
                                     'playlist_id': playlist_id,
                                     'video_id': playlist_item_id,
                                     'video_name': video_item.get_name()
                                 })))
                        pass
                    pass
                pass
            pass

        # got to [CHANNEL]
        if channel_id and channel_name:
            # only if we are not directly in the channel provide a jump to the channel
            if kodion.utils.create_path('channel',
                                        channel_id) != context.get_path():
                yt_context_menu.append_go_to_channel(context_menu, provider,
                                                     context, channel_id,
                                                     channel_name)
                pass
            pass

        if provider.is_logged_in():
            # subscribe to the channel of the video
            yt_context_menu.append_subscribe_to_channel(
                context_menu, provider, context, channel_id, channel_name)
            pass

        # more...
        refresh_container = context.get_path().startswith(
            '/channel/mine/playlist/LL') or context.get_path(
            ) == '/special/disliked_videos/'
        yt_context_menu.append_more_for_video(
            context_menu,
            provider,
            context,
            video_id,
            is_logged_in=provider.is_logged_in(),
            refresh_container=refresh_container)

        if len(context_menu) > 0:
            video_item.set_context_menu(context_menu,
                                        replace=replace_context_menu)
            pass
        pass

    pass