public MainWindow()
 {
     try
     {
         InitializeComponent();
         _serviceOptions = new ServiceRefreshOptions();
         Instance = this;
         Go();
     }
     catch (Exception e)
     {
         Console.WriteLine("Critical error launching Media Browser Service, please report this bug with the full contents below to http://community.mediabrowser.tv");
         Console.WriteLine(e.ToString());
         Console.WriteLine(e.StackTrace);
         Console.WriteLine(e.InnerException);
         Console.ReadKey();
     }
 }
        void FullRefresh(bool force, ServiceRefreshOptions manualOptions)
        {
            _refreshRunning = true;
            Dispatcher.Invoke(DispatcherPriority.Background, (System.Windows.Forms.MethodInvoker)(() =>
            {
                gbManual.IsEnabled = false;
                refreshProgress.Value = 0;
                refreshProgress.Visibility = Visibility.Visible;
                _refreshCanceled = false;
                _refreshCanceledTime = DateTime.MinValue;
                _config.RefreshFailed = false;
                _config.Save();
                _refreshStartTime = DateTime.Now;
                if (manualOptions.AllowCancel)
                {
                    btnCancelRefresh.IsEnabled = true;
                    btnCancelRefresh.Visibility = Visibility.Visible;
                }
                lblSvcActivity.Content = "Refresh Running...";
                lblSvcActivity.Foreground = Brushes.Black;
                lblNextSvcRefresh.Foreground = Brushes.Black;
                notifyIcon.ContextMenu.MenuItems["refresh"].Enabled = false;
                notifyIcon.ContextMenu.MenuItems["exit"].Enabled = false;
                notifyIcon.ContextMenu.MenuItems["refresh"].Text = "Refresh Running...";
                //Stream iconStream = Application.GetResourceStream(new Uri("pack://application:,,,/MediaBrowserService;component/MBServiceRefresh.ico")).Stream;
                notifyIcon.Icon = RefreshIcons[0];
                lblNextSvcRefresh.Content = "";
            }));

            bool onSchedule = (!force && (DateTime.Now.Hour == _config.FullRefreshPreferredHour));

            Logger.ReportInfo("Full Refresh Started");

            refreshElapsed = Async.Every(1000, UpdateRefreshElapsed);

            using (new Profiler(Kernel.Instance.GetString("FullRefreshProf")))
            {
                try
                {
                    Kernel.Instance.ReLoadRoot(); // make sure we are dealing with the current state of the library
                    if (force)
                    {
                        if (manualOptions.ClearCacheOption)
                        {
                            //clear all cache items except displayprefs and playstate
                            Logger.ReportInfo("Clearing Cache on manual refresh...");
                            UpdateProgress("Clearing Cache", 0);
                            try
                            {
                                Kernel.Instance.ItemRepository.ClearEntireCache();
                            }
                            catch (Exception e)
                            {
                                Logger.ReportException("Error attempting to clear cache.", e);
                            }
                        }
                        if (manualOptions.ClearImageCacheOption)
                        {
                            try
                            {
                                Directory.Delete(ApplicationPaths.AppImagePath, true);
                                Thread.Sleep(1000); //wait for the delete to fiinish
                            }
                            catch (Exception e) { Logger.ReportException("Error trying to clear image cache.", e); } //just log it
                            try
                            {
                                Directory.CreateDirectory(ApplicationPaths.AppImagePath);
                                Thread.Sleep(1000); //wait for the directory to create
                            }
                            catch (Exception e) { Logger.ReportException("Error trying to create image cache.", e); } //just log it
                        }
                    }

                    MetadataRefreshOptions refreshOptions = manualOptions.AllowSlowProviderOption ? MetadataRefreshOptions.Default : MetadataRefreshOptions.FastOnly;

                    if (FullRefresh(Kernel.Instance.RootFolder, refreshOptions, manualOptions))
                    {
                        _config.LastFullRefresh = DateTime.Now;
                        _lastRefreshElapsedTime = DateTime.Now - _refreshStartTime;
                        _config.Save();
                    }

                    MBServiceController.SendCommandToCore(IPCCommands.ReloadItems);

                }
                catch (Exception ex)
                {
                    Logger.ReportException("Failed to refresh library! ", ex);
                    Debug.Assert(false, "Full refresh service should never crash!");
                }
                finally
                {
                    Kernel.Instance.ReLoadRoot(); // re-dump this to stay clean
                    refreshElapsed.Change(-1,0); //kill the progress timer
                    _refreshRunning = false;
                    Logger.ReportInfo("Full Refresh Finished");
                    Dispatcher.Invoke(DispatcherPriority.Background, (System.Windows.Forms.MethodInvoker)(() =>
                    {
                        refreshProgress.Value = 0;
                        refreshProgress.Visibility = Visibility.Hidden;
                        btnCancelRefresh.Visibility = Visibility.Hidden;
                        gbManual.IsEnabled = true;
                        refreshElapsed = null;
                        notifyIcon.ContextMenu.MenuItems["exit"].Enabled = true;
                        notifyIcon.ContextMenu.MenuItems["refresh"].Enabled = true;
                        notifyIcon.ContextMenu.MenuItems["refresh"].Text = "Refresh Now";
                        Stream iconStream = Application.GetResourceStream(new Uri("pack://application:,,,/MediaBrowserService;component/MBService.ico")).Stream;
                        notifyIcon.Icon = new System.Drawing.Icon(iconStream);
                        UpdateStatus();
                    }));

                    if (onSchedule)
                    {
                        ClearLogFiles(Kernel.Instance.ConfigData.LogFileRetentionDays);
                        if (_config.SleepAfterScheduledRefresh)
                        {
                            Async.Queue("Sleep After Refresh", () =>
                            {
                                Logger.ReportInfo("Putting computer to sleep...");
                                System.Windows.Forms.Application.SetSuspendState(System.Windows.Forms.PowerState.Suspend, true, false);
                            }, 10000);
                        }
                    }
                }
            }
        }
        bool FullRefresh(AggregateFolder folder, MetadataRefreshOptions options, ServiceRefreshOptions manualOptions)
        {
            int phases = manualOptions.AnyImageOptionsSelected || manualOptions.MigrateOption ? 3 : 2;
            double totalIterations = 0;
            UpdateProgress("Determining Library Size", 0);
            //this will trap any circular references in the library tree
            try
            {
                Async.RunWithTimeout(() => { totalIterations = folder.AllRecursiveChildren.Count() * phases; }, 600000);
            }
            catch (TimeoutException)
            {
                Logger.ReportError("ERROR DURING REFRESH.  Timed out attempting to retrieve count of all items.  Most likely there is a circular reference in your library.  Look for *.lnk files that might be pointing back to a parent of the folder that contatians that link.");
                _config.RefreshFailed = true;
                _config.Save();
                return false;
            }

            if (totalIterations == 0) return true; //nothing to do

            int currentIteration = 0;

            UpdateProgress("Validating Root", 0);

            folder.RefreshMetadata(options);

            using (new Profiler(Kernel.Instance.GetString("FullValidationProf")))
            {
                if (!RunActionRecursively(folder, item =>
                {
                    currentIteration++;
                    UpdateProgress("Validating",currentIteration / totalIterations);
                    var f = item as Folder;
                    if (f != null)
                    {
                        f.ValidateChildren();
                    }

                })) return false;
            }

            string msg = (options & MetadataRefreshOptions.FastOnly) == MetadataRefreshOptions.FastOnly ?
                "Not allowing internet and other slow providers." :
                "Allowing internet and other slow providers.";
            Logger.ReportInfo(msg);
            var processedItems = new HashSet<Guid>();
            using (new Profiler(Kernel.Instance.GetString("SlowRefresh")))
            {
                if (!RunActionRecursively(folder, item =>
                {
                    currentIteration++;
                    UpdateProgress("All Metadata",(currentIteration / totalIterations));
                    if (!processedItems.Contains(item.Id)) //only process any given item once (could be multiple refs to same item)
                    {
                        if (manualOptions.MigrateOption)
                        {
                            MigratePlayState(item);
                        }
                        item.RefreshMetadata(options);
                        processedItems.Add(item.Id);
                        //Logger.ReportInfo(item.Name + " id: " + item.Id);
                        //test
                        //throw new InvalidOperationException("Test Error...");
                    }
                })) return false;
            }

            if (manualOptions.AnyImageOptionsSelected || manualOptions.MigrateOption)
            {
                processedItems.Clear();
                using (new Profiler(Kernel.Instance.GetString("ImageRefresh")))
                {
                    var studiosProcessed = new List<string>();
                    var genresProcessed = new List<string>();
                    var peopleProcessed = new List<string>();
                    var yearsProcessed = new List<string>();

                    if (!RunActionRecursively(folder, item =>
                    {
                        currentIteration++;
                        UpdateProgress("Images",(currentIteration / totalIterations));
                        if (!processedItems.Contains(item.Id))
                        {
                            if (manualOptions.IncludeImagesOption) //main images
                            {
                                Logger.ReportInfo("Caching all images for " + item.Name );
                                item.ReCacheAllImages();
                            }
                            if (manualOptions.MigrateOption) //migrate main images
                            {
                                item.MigrateAllImages();
                            }
                            // optionally cause genre, poeple, year and studio images to cache as well
                            if (item is Show)
                            {
                                var show = item as Show;
                                if ((manualOptions.IncludeGenresOption || manualOptions.MigrateOption) && show.Genres != null)
                                {
                                    foreach (var genre in show.Genres)
                                    {
                                        if (!genresProcessed.Contains(genre))
                                        {
                                            Genre g = Genre.GetGenre(genre);
                                            g.RefreshMetadata();
                                            if (g.PrimaryImage != null)
                                            {
                                                if (manualOptions.IncludeGenresOption)
                                                {
                                                    Logger.ReportInfo("Caching image for genre: " + genre);
                                                    g.PrimaryImage.ClearLocalImages();
                                                    g.PrimaryImage.GetLocalImagePath();
                                                }
                                                if (manualOptions.MigrateOption)
                                                {
                                                    Logger.ReportInfo("Migrating image for genre: " + genre);
                                                    g.PrimaryImage.MigrateFromOldID();
                                                }

                                            }
                                            foreach (MediaBrowser.Library.ImageManagement.LibraryImage image in g.BackdropImages)
                                            {
                                                if (manualOptions.IncludeGenresOption)
                                                {
                                                    image.GetLocalImagePath();
                                                }
                                                if (manualOptions.MigrateOption)
                                                {
                                                    image.MigrateFromOldID();
                                                }
                                            }
                                            genresProcessed.Add(genre);
                                        }
                                    }
                                }
                                if ((manualOptions.IncludeStudiosOption || manualOptions.MigrateOption) && show.Studios != null)
                                {
                                    foreach (var studio in show.Studios)
                                    {
                                        if (!studiosProcessed.Contains(studio))
                                        {
                                                Logger.ReportInfo("Caching image for studio: " + studio);
                                                Studio st = Studio.GetStudio(studio);
                                                st.RefreshMetadata();
                                                if (st.PrimaryImage != null)
                                                {
                                                    if (manualOptions.IncludeStudiosOption)
                                                    {
                                                        Logger.ReportInfo("Caching image for studio: " + studio);
                                                        st.PrimaryImage.ClearLocalImages();
                                                        st.PrimaryImage.GetLocalImagePath();
                                                    }
                                                    if (manualOptions.MigrateOption)
                                                    {
                                                        Logger.ReportInfo("Migrating image for studio: " + studio);
                                                        st.PrimaryImage.MigrateFromOldID();
                                                    }
                                                }

                                            foreach (MediaBrowser.Library.ImageManagement.LibraryImage image in st.BackdropImages)
                                            {
                                                if (manualOptions.IncludeStudiosOption)
                                                {
                                                    image.ClearLocalImages();
                                                    image.GetLocalImagePath();
                                                }
                                                if (manualOptions.MigrateOption)
                                                {
                                                    image.MigrateFromOldID();
                                                }
                                            }
                                            studiosProcessed.Add(studio);
                                        }
                                    }
                                }
                                if ((manualOptions.IncludePeopleOption || manualOptions.MigrateOption) && show.Actors != null)
                                {
                                    foreach (var actor in show.Actors)
                                    {
                                        if (!peopleProcessed.Contains(actor.Name))
                                        {
                                            Person p = Person.GetPerson(actor.Name);
                                            p.RefreshMetadata();
                                            if (p.PrimaryImage != null)
                                            {
                                                if (manualOptions.IncludePeopleOption)
                                                {
                                                    Logger.ReportInfo("Caching image for person: " + actor.Name);
                                                    p.PrimaryImage.ClearLocalImages();
                                                    p.PrimaryImage.GetLocalImagePath();
                                                }
                                                if (manualOptions.MigrateOption)
                                                {
                                                    Logger.ReportInfo("Migrating image for person: " + actor.Name);
                                                    p.PrimaryImage.MigrateFromOldID();
                                                }

                                            }
                                            foreach (MediaBrowser.Library.ImageManagement.LibraryImage image in p.BackdropImages)
                                            {
                                                if (manualOptions.IncludePeopleOption)
                                                {
                                                    image.ClearLocalImages();
                                                    image.GetLocalImagePath();
                                                }
                                                if (manualOptions.MigrateOption)
                                                {
                                                    image.MigrateFromOldID();
                                                }
                                            }
                                            peopleProcessed.Add(actor.Name);
                                        }
                                    }
                                }
                                if (manualOptions.IncludePeopleOption && show.Directors != null)
                                {
                                    foreach (var director in show.Directors)
                                    {
                                        if (!peopleProcessed.Contains(director))
                                        {
                                            Person p = Person.GetPerson(director);
                                            p.RefreshMetadata();
                                            if (p.PrimaryImage != null)
                                            {
                                                Logger.ReportInfo("Caching image for person: " + director);
                                                p.PrimaryImage.ClearLocalImages();
                                                p.PrimaryImage.GetLocalImagePath();
                                            }
                                            foreach (MediaBrowser.Library.ImageManagement.LibraryImage image in p.BackdropImages)
                                            {
                                                image.ClearLocalImages();
                                                image.GetLocalImagePath();
                                            }
                                            peopleProcessed.Add(director);
                                        }
                                    }
                                }
                                if (manualOptions.IncludeYearOption && show.ProductionYear != null)
                                {
                                    if (!yearsProcessed.Contains(show.ProductionYear.ToString()))
                                    {
                                        Year yr = Year.GetYear(show.ProductionYear.ToString());
                                        yr.RefreshMetadata();
                                        if (yr.PrimaryImage != null)
                                        {
                                            Logger.ReportInfo("Caching image for year: " + yr);
                                            yr.PrimaryImage.ClearLocalImages();
                                            yr.PrimaryImage.GetLocalImagePath();
                                        }
                                        foreach (MediaBrowser.Library.ImageManagement.LibraryImage image in yr.BackdropImages)
                                        {
                                            image.ClearLocalImages();
                                            image.GetLocalImagePath();
                                        }
                                        yearsProcessed.Add(show.ProductionYear.ToString());
                                    }

                                }
                            }
                            processedItems.Add(item.Id);
                        }
                        else Logger.ReportInfo("Not processing " + item.Name + " again.");
                    })) return false;
                }
            }
            return true;
        }
        public void ForceRebuild()
        {
            //force a re-build of the entire library - used when new version requires cache clear
            //first create options - just the items as we will attempt to migrate the old images
            var options = new ServiceRefreshOptions()
            {
                ClearCacheOption = true,
                ClearImageCacheOption = false,
                IncludeImagesOption = false,
                IncludeGenresOption = false,
                IncludeStudiosOption = false,
                IncludeYearOption = false,
                MigrateOption = true,
                AllowSlowProviderOption = true,
                AllowCancel = false
            };

            //kick off a manual refresh on a high-priority thread
            Thread manual = new Thread(new ThreadStart(() =>
            {
                _config.ForceRebuildInProgress = true;
                _config.Save();
                FullRefresh(true, options);
                _config.ForceRebuildInProgress = false;
                _config.Save();
            }));
            manual.Name = "Force Rebuild";
            manual.IsBackground = true;
            manual.Priority = ThreadPriority.Highest;
            manual.Start();
        }