internal static bool RateEpisode(TraktShowSummary show, TraktEpisodeSummary episode)
        {
            // this object will work without episode ids
            var rateObjectEx = new TraktSyncShowRatedEx
            {
                Ids = show.Ids,
                Title = show.Title,
                Year = show.Year,
                Seasons = new List<TraktSyncShowRatedEx.Season>
                {
                    new TraktSyncShowRatedEx.Season
                    {
                        Number = episode.Season,
                        Episodes = new List<TraktSyncShowRatedEx.Season.Episode>
                        {
                            new TraktSyncShowRatedEx.Season.Episode
                            {
                                Number = episode.Number,
                                RatedAt = DateTime.UtcNow.ToISO8601()
                            }
                        }
                    }
                }
            };

            // only use if we have episode ids
            var rateObject = new TraktSyncEpisodeRated
            {
                Ids = new TraktEpisodeId
                {
                    Trakt = episode.Ids.Trakt,
                    Imdb = episode.Ids.Imdb.ToNullIfEmpty(),
                    Tmdb = episode.Ids.Tmdb,
                    Tvdb = episode.Ids.Tvdb,
                    TvRage = episode.Ids.TvRage
                },
                Title = episode.Title,
                Season = episode.Season,
                Number = episode.Number,
                RatedAt = DateTime.UtcNow.ToISO8601()
            };

            int? prevRating = episode.UserRating(show);
            int newRating = 0;

            if (episode.Ids == null || episode.Ids.Trakt == null)
            {
                newRating = GUIUtils.ShowRateDialog<TraktSyncShowRatedEx>(rateObjectEx);
            }
            else
            {
                newRating = GUIUtils.ShowRateDialog<TraktSyncEpisodeRated>(rateObject);
            }

            if (newRating == -1) return false;

            // If previous rating not equal to current rating then
            // update skin properties to reflect changes
            if (prevRating == newRating)
                return false;

            if (prevRating == null || prevRating == 0)
            {
                // add to ratings
                TraktCache.AddEpisodeToRatings(show, episode, newRating);
                episode.Votes++;
            }
            else if (newRating == 0)
            {
                // remove from ratings
                TraktCache.RemoveEpisodeFromRatings(episode);
                episode.Votes--;
            }
            else
            {
                // rating changed, remove then add
                TraktCache.RemoveEpisodeFromRatings(episode);
                TraktCache.AddEpisodeToRatings(show, episode, newRating);
            }

            // update ratings until next online update
            // if we have the ratings distribution we could calculate correctly
            if (episode.Votes == 0)
            {
                episode.Rating = 0;
            }
            else if (episode.Votes == 1 && newRating > 0)
            {
                episode.Rating = newRating;
            }

            return true;
        }
        /// <summary>
        /// Rate a single episode on trakt.tv
        /// </summary>
        public static TraktSyncResponse AddEpisodeToRatings(TraktSyncEpisodeRated episode)
        {
            var episodes = new TraktSyncEpisodesRated
            {
                Episodes = new List<TraktSyncEpisodeRated>() { episode }
            };

            return AddEpisodesToRatings(episodes);
        }