Ejemplo n.º 1
0
        /// <summary>
        /// Initialize the provider
        /// </summary>
        void IValidator.Init(XmlNode config)
        {
            //  get the xml node that holds the key (might be empty)
            XmlNode keyNode = config.SelectSingleNode("key");

            //  look for key in xml
            _key = ExtractKeyFromNode(keyNode);

            //  we've tried to find key in "key" nodes, we should have a good key now; check to be sure
            if (null == _key)
            {
                string error = ApplicationUpdateManager.TraceWrite("[KeyValidator.Init]", "RES_CouldNotFindCryptographicKey");

                CryptographicException ce = new CryptographicException(error);
                ExceptionManager.Publish(ce);
                throw ce;
            }
        }
Ejemplo n.º 2
0
        /// <summary>
        /// Reads the given file and creates a hash code that uses every byte of the file to contribute, then encrypts the resulting hash code using the key
        /// in the KeyedHashAlgorithm
        /// </summary>
        /// <param name="filePath">full path to the file to sign</param>
        /// <param name="key">the "secret" key used to "sign" the hash</param>
        /// <returns>a base64-encoded string which is the encrypted signature of the file</returns>
        string IValidator.Sign(string filePath, string key)
        {
            byte[]     outSignature = null;
            FileStream fs           = null;

            try
            {
                //  using the key (member variable) use hashed-key algorithm to generate
                //  a signature for the file

                //  attempt to open the file with shared read access
                fs = new FileStream(filePath, FileMode.Open, FileAccess.Read, FileShare.Read);

                //  create an instance of keyed hash algo--note that the static Create is its own Factory method (sweet)
                KeyedHashAlgorithm kha = KeyedHashAlgorithm.Create();
                //  feed the hash algo the key
                kha.Key = Convert.FromBase64String(key);
                //  now hash over entire file, munging with key to give uniqueness that depends on both key and file
                //  for a strong signature.
                //  NOTE:  now, the "secret" is the key.  Without the "secret", you CANNOT spoof the identity of the file.
                //  the contract between server and client is that the files are what the server promised; the enforcement of that
                //  contract is the cryptographically strong hash, which depends on both key and file identity.
                //  As long as both parties accept the validity of the "secret", they can trust the identity of the file if its signature matches.
                outSignature = kha.ComputeHash(fs);
            }
            catch (Exception e)
            {
                ApplicationUpdateManager.TraceWrite(e, "[KeyValidator.Sign]", "RES_EXCEPTION_SigningFile", filePath);
                throw e;
            }
            finally
            {
                if (null != fs)
                {
                    fs.Close();
                }
            }
            //  return the signature
            return(Convert.ToBase64String(outSignature));
        }
Ejemplo n.º 3
0
    public void UserCheckForUpdates()
    {
        ApplicationUpdateManager updateManager = services.updateManager;

        updateManager.CheckForUpdates(OnUserCheckForUpdatesComplete);

        LoadingTask waitForUpdateCheckTask = new LoadingTask("Checking for updates...", () =>
        {
            while (updateManager.UpdateCheckInProgress)
            {
                ;
            }
        });

        List <LoadingTask> tasks = new List <LoadingTask>()
        {
            waitForUpdateCheckTask
        };

        LoadingTasksManager tasksManager = services.loadingTasksManager;

        tasksManager.KickTasks(tasks);
    }
Ejemplo n.º 4
0
        /// <summary>
        /// Helper function to get the base64-encoded key from the "key" node
        /// </summary>
        /// <param name="keyNode">contains the base64 encoded key hash</param>
        /// <returns>byte array which is the key decoded from base64</returns>
        private byte[] ExtractKeyFromNode(XmlNode keyNode)
        {
            byte[] key = null;

            //  skip out right away if passed a null node
            if (null == keyNode)
            {
                return(null);
            }

            try
            {
                //  we're passed the key node, so just take the innerText and convert to a byte[] from base64
                key = Convert.FromBase64String(keyNode.InnerText);
            }
            catch (Exception e)
            {
                ApplicationUpdateManager.TraceWrite(e, "[KeyValidator.ExtractKeyFromNode]", "RES_CouldNotFindCryptographicKey");
                ExceptionManager.Publish(e);
                throw e;
            }

            return(key);
        }
Ejemplo n.º 5
0
        public async Task TestMultipleUpdates()
        {
            IEnumerable <AppIdentity> appsToDeploy = new[] { app1v3, app1v4, app1v5 };
            IEnumerable <string>      clusters     = new[] { "clusterId1" };

            IApplicationDeploymentDirectory applicationDeploymentDirectory = new StubIApplicationDeploymentDirectory()
                                                                             .FetchDeployments(() => Task.FromResult(appsToDeploy.Select(identity => new AppDeploymentConfig(identity, clusters))));

            string path = Path.GetTempPath();
            await applicationPool.AddApplication(new ApplicationStub(app1v1, path));

            await applicationPool.AddApplication(new ApplicationStub(app1v2, path));

            await applicationPool.AddApplication(new ApplicationStub(app1v3, path));

            IUpdateSessionManager updateSessionManagerStub = new StubIUpdateSessionManager()
                                                             .TryStartUpdateSession(() => Task.FromResult(true))
                                                             .EndUpdateSession(() => Task.CompletedTask);

            const string             ClusterId  = "clusterId";
            const string             InstanceId = "instanceId";
            ApplicationUpdateManager applicationUpdateManager = new ApplicationUpdateManager(ClusterId, InstanceId,
                                                                                             applicationDeploymentDirectory, applicationPool, applicationDownloader, applicationInstaller,
                                                                                             deploymentStatusWriterStub, updateSessionManagerStub);
            await applicationUpdateManager.CheckForUpdates();

            Assert.Equal(3, applicationPool.Applications.Count());
            Assert.True(applicationPool.HasApplication(app1v3));
            Assert.True(applicationPool.HasApplication(app1v4));
            Assert.True(applicationPool.HasApplication(app1v5));

            Assert.Equal(3, instanceDeploymentStatus.Applications.Count());
            VerifyThatDeploymentStatusHasBeenUpdated(instanceDeploymentStatus, app1v3, ClusterId, InstanceId);
            VerifyThatDeploymentStatusHasBeenUpdated(instanceDeploymentStatus, app1v4, ClusterId, InstanceId);
            VerifyThatDeploymentStatusHasBeenUpdated(instanceDeploymentStatus, app1v5, ClusterId, InstanceId);
        }
Ejemplo n.º 6
0
  private void DoStartupJobs()
  {
    FilterChecker.CheckInstalledVersions();

    Version aParamVersion;
    //
    // 6.5.2600.3243 = KB941568,   6.5.2600.3024 = KB927544
    //
    if (
      !FilterChecker.CheckFileVersion(Environment.SystemDirectory + "\\quartz.dll", "6.5.2600.3024", out aParamVersion))
    {
      string ErrorMsg =
        string.Format("Your version {0} of quartz.dll has too many bugs! \nPlease check our Wiki's requirements page.",
                      aParamVersion.ToString());
      Log.Info("Util: quartz.dll error - {0}", ErrorMsg);
      if (
        MessageBox.Show(ErrorMsg, "Core directshow component (quartz.dll) is outdated!", MessageBoxButtons.OKCancel,
                        MessageBoxIcon.Exclamation) == DialogResult.OK)
      {
        Process.Start(@"http://wiki.team-mediaportal.com/GeneralRequirements");
      }
    }

    EnableS3Trick();
    GUIWindowManager.OnNewAction += new OnActionHandler(OnAction);
    GUIWindowManager.Receivers += new SendMessageHandler(OnMessage);
    GUIWindowManager.Callbacks += new GUIWindowManager.OnCallBackHandler(MPProcess);
    GUIGraphicsContext.CurrentState = GUIGraphicsContext.State.STARTING;
    Utils.OnStartExternal += new Utils.UtilEventHandler(OnStartExternal);
    Utils.OnStopExternal += new Utils.UtilEventHandler(OnStopExternal);
    // load keymapping from keymap.xml
    ActionTranslator.Load();
    //register the playlistplayer for thread messages (like playback stopped,ended)
    Log.Info("Main: Init playlist player");
    g_Player.Factory = new PlayerFactory();
    playlistPlayer.Init();
    // Only load the USBUIRT device if it has been enabled in the configuration
    using (Settings xmlreader = new MPSettings())
    {
      bool inputEnabled = xmlreader.GetValueAsBool("USBUIRT", "internal", false);
      bool outputEnabled = xmlreader.GetValueAsBool("USBUIRT", "external", false);
      if (inputEnabled || outputEnabled)
      {
        Log.Info("Main: Creating the USBUIRT device");
        usbuirtdevice = USBUIRT.Create(new USBUIRT.OnRemoteCommand(OnRemoteCommand));
        Log.Info("Main: Creating the USBUIRT device done");
      }
      //Load Winlirc if enabled.
      bool winlircInputEnabled = xmlreader.GetValueAsString("WINLIRC", "enabled", "false") == "true";
      if (winlircInputEnabled)
      {
        Log.Info("Main: Creating the WINLIRC device");
        winlircdevice = new WinLirc();
        Log.Info("Main: Creating the WINLIRC device done");
      }
      //Load RedEye if enabled.
      bool redeyeInputEnabled = xmlreader.GetValueAsString("RedEye", "internal", "false") == "true";
      if (redeyeInputEnabled)
      {
        Log.Info("Main: Creating the REDEYE device");
        redeyedevice = RedEye.Create(new RedEye.OnRemoteCommand(OnRemoteCommand));
        Log.Info("Main: Creating the RedEye device done");
      }
      inputEnabled = xmlreader.GetValueAsString("SerialUIR", "internal", "false") == "true";
      if (inputEnabled)
      {
        Log.Info("Main: Creating the SerialUIR device");
        serialuirdevice = SerialUIR.Create(new SerialUIR.OnRemoteCommand(OnRemoteCommand));
        Log.Info("Main: Creating the SerialUIR device done");
      }
    }
    //registers the player for video window size notifications
    Log.Info("Main: Init players");
    g_Player.Init();
    GUIGraphicsContext.ActiveForm = Handle;
    //  hook ProcessExit for a chance to clean up when closed peremptorily
#if AUTOUPDATE
    AppDomain.CurrentDomain.ProcessExit += new EventHandler(CurrentDomain_ProcessExit);
    //  hook form close to stop updater too
    this.Closed += new EventHandler(MediaPortal_Closed);
#endif
    XmlDocument doc = new XmlDocument();
    try
    {
      doc.Load("mediaportal.exe.config");
      XmlNode node = doc.SelectSingleNode("/configuration/appStart/ClientApplicationInfo/appFolderName");
      if (node != null)
      {
        node.InnerText = Directory.GetCurrentDirectory();
      }
      node = doc.SelectSingleNode("/configuration/appUpdater/UpdaterConfiguration/application/client/baseDir");
      if (node != null)
      {
        node.InnerText = Directory.GetCurrentDirectory();
      }
      node = doc.SelectSingleNode("/configuration/appUpdater/UpdaterConfiguration/application/client/tempDir");
      if (node != null)
      {
        node.InnerText = Directory.GetCurrentDirectory();
      }
      doc.Save("MediaPortal.exe.config");
    }
    catch (Exception) {}
    Thumbs.CreateFolders();
    try
    {
#if DEBUG
#else
#if AUTOUPDATE
      UpdaterConfiguration config = UpdaterConfiguration.Instance;
      config.Logging.LogPath = Config.Get(Config.Dir.Log) + "updatelog.log";
      config.Applications[0].Client.BaseDir = Config.Get(Config.Dir.Base)
      config.Applications[0].Client.TempDir =  Config.Get(Config.Dir.Base) + "temp";
      config.Applications[0].Client.XmlFile =  Config.Get(Config.Dir.Base) + "MediaPortal.exe.config";
      config.Applications[0].Server.ServerManifestFileDestination =  Config.Get(Config.Dir.Base) + @"xml\ServerManifest.xml";
      try
      {
        System.IO.Directory.CreateDirectory(config.Applications[0].Client.BaseDir + @"temp");
				System.IO.Directory.CreateDirectory(config.Applications[0].Client.BaseDir + @"xml");
				System.IO.Directory.CreateDirectory(config.Applications[0].Client.BaseDir + @"log");
			}
			catch(Exception){}
			Utils.DeleteFiles(config.Applications[0].Client.BaseDir + "log", "*.log");
			ClientApplicationInfo clientInfo = ClientApplicationInfo.Deserialize("MediaPortal.exe.config");
			clientInfo.AppFolderName = System.IO.Directory.GetCurrentDirectory();
			ClientApplicationInfo.Save("MediaPortal.exe.config",clientInfo.AppFolderName, clientInfo.InstalledVersion);
			m_strCurrentVersion = clientInfo.InstalledVersion;
			Text += (" - [v" + m_strCurrentVersion + "]");
			//  make an Updater for use in-process with us
			_updater = new ApplicationUpdateManager();
			//  hook Updater events
			_updater.DownloadStarted += new UpdaterActionEventHandler(OnUpdaterDownloadStarted);
			_updater.UpdateAvailable += new UpdaterActionEventHandler(OnUpdaterUpdateAvailable);
			_updater.DownloadCompleted += new UpdaterActionEventHandler(OnUpdaterDownloadCompleted);
			//  start the updater on a separate thread so that our UI remains responsive
			_updaterThread = new Thread(new ThreadStart(_updater.StartUpdater));
			_updaterThread.Start();
#endif
#endif
    }
    catch (Exception) {}
    using (Settings xmlreader = new MPSettings())
    {
      m_iDateLayout = xmlreader.GetValueAsInt("home", "datelayout", 0);
    }
    GUIGraphicsContext.ResetLastActivity();
  }
Ejemplo n.º 7
0
        public async Task TestMultipleUpdates()
        {
            string id1 = "appId1";
            var    v1  = SemVersion.Parse("1.0.0");
            var    v2  = SemVersion.Parse("2.0.0");
            var    v3  = SemVersion.Parse("3.0.0");
            var    v4  = SemVersion.Parse("4.0.0");
            var    v5  = SemVersion.Parse("5.0.0");

            AppIdentity app1v1 = new AppIdentity(id1, v1);
            AppIdentity app1v2 = new AppIdentity(id1, v2);
            AppIdentity app1v3 = new AppIdentity(id1, v3);
            AppIdentity app1v4 = new AppIdentity(id1, v4);
            AppIdentity app1v5 = new AppIdentity(id1, v5);

            IEnumerable <AppIdentity> appsToDeploy = new[] { app1v3, app1v4, app1v5 };
            IEnumerable <string>      clusters     = new[] { "clusterId1" };

            IApplicationDeploymentDirectory applicationDeploymentDirectory = new StubIApplicationDeploymentDirectory()
                                                                             .FetchDeployments(() => Task.FromResult(appsToDeploy.Select(identity => new AppDeploymentConfig(identity, clusters))));

            IApplicationPool applicationPool = new ApplicationPoolStub();
            string           path            = Path.GetTempPath();
            await applicationPool.AddApplication(new ApplicationStub(app1v1, path));

            await applicationPool.AddApplication(new ApplicationStub(app1v2, path));

            await applicationPool.AddApplication(new ApplicationStub(app1v3, path));

            var downloadedApps = new List <AppIdentity>();
            IApplicationDownloader applicationDownloader = new StubIApplicationDownloader()
                                                           .DownloadApplication(appIdentity =>
            {
                downloadedApps.Add(appIdentity);
                return(Task.FromResult(true));
            }
                                                                                );

            var    installedApps   = new List <AppIdentity>();
            var    uninstalledApps = new List <AppIdentity>();
            string updatedAppId    = null;
            IEnumerable <SemVersion> versionsRemoved      = null;
            IEnumerable <SemVersion> versionsAdded        = null;
            IApplicationInstaller    applicationInstaller = new StubIApplicationInstaller()
                                                            .Install(config =>
            {
                installedApps.Add(config.AppIdentity);
                return(Task.FromResult(true));
            })
                                                            .UnInstall(appIdentity =>
            {
                uninstalledApps.Add(appIdentity);
                return(Task.FromResult(true));
            })
                                                            .Update((applicationsToRemove, applicationsToInstall) =>
            {
                updatedAppId    = applicationsToInstall.First().AppIdentity.Id;
                versionsRemoved = applicationsToRemove.Select(identity => identity.Version);
                versionsAdded   = applicationsToInstall.Select(config => config.AppIdentity.Version);
                return(Task.FromResult(true));
            }
                                                                    );

            ApplicationUpdateManager applicationUpdateManager = new ApplicationUpdateManager("clusterId", applicationDeploymentDirectory, applicationPool, applicationDownloader, applicationInstaller);
            await applicationUpdateManager.CheckForUpdates();

            Assert.Equal(2, downloadedApps.Count);
            Assert.True(downloadedApps.Contains(app1v4));
            Assert.True(downloadedApps.Contains(app1v5));

            Assert.False(installedApps.Any());
            Assert.False(uninstalledApps.Any());

            Assert.Equal(id1, updatedAppId);
            Assert.Equal(new [] { v1, v2 }, versionsRemoved.ToList());
            Assert.Equal(new[] { v4, v5 }, versionsAdded.ToList());
        }
Ejemplo n.º 8
0
        public async Task TestMultipleUpdates()
        {
            string id1 = "appId1";
            var    v1  = SemVersion.Parse("1.0.0");
            var    v2  = SemVersion.Parse("2.0.0");
            var    v3  = SemVersion.Parse("3.0.0");
            var    v4  = SemVersion.Parse("4.0.0");
            var    v5  = SemVersion.Parse("5.0.0");

            AppIdentity app1v1 = new AppIdentity(id1, v1);
            AppIdentity app1v2 = new AppIdentity(id1, v2);
            AppIdentity app1v3 = new AppIdentity(id1, v3);
            AppIdentity app1v4 = new AppIdentity(id1, v4);
            AppIdentity app1v5 = new AppIdentity(id1, v5);

            IEnumerable <AppIdentity> appsToDeploy = new[] { app1v3, app1v4, app1v5 };
            IEnumerable <string>      clusters     = new[] { "clusterId1" };

            IApplicationDeploymentDirectory applicationDeploymentDirectory = new StubIApplicationDeploymentDirectory()
                                                                             .FetchDeployments(() => Task.FromResult(appsToDeploy.Select(identity => new AppDeploymentConfig(identity, clusters))));

            IApplicationPool applicationPool = new ApplicationPoolStub();
            string           path            = Path.GetTempPath();
            await applicationPool.AddApplication(new ApplicationStub(app1v1, path));

            await applicationPool.AddApplication(new ApplicationStub(app1v2, path));

            await applicationPool.AddApplication(new ApplicationStub(app1v3, path));

            var downloadedApps = new List <AppIdentity>();
            IApplicationDownloader applicationDownloader = new StubIApplicationDownloader()
                                                           .DownloadApplication(appIdentity =>
            {
                downloadedApps.Add(appIdentity);
                return(Task.FromResult(true));
            }
                                                                                );

            IApplicationInstaller applicationInstaller = new StubIApplicationInstaller()
                                                         .Install(config =>
            {
                applicationPool.AddApplication(new ApplicationStub(config.AppIdentity, "path"));
                return(Task.FromResult(true));
            })
                                                         .UnInstall(appIdentity =>
            {
                applicationPool.RemoveApplication(appIdentity);
                return(Task.FromResult(true));
            })
                                                         .Update((applicationsToRemove, applicationsToInstall) =>
            {
                foreach (var appIdentity in applicationsToRemove)
                {
                    applicationPool.RemoveApplication(appIdentity);
                }
                foreach (var appInstallConfig in applicationsToInstall)
                {
                    applicationPool.AddApplication(new ApplicationStub(appInstallConfig.AppIdentity, "path"));
                }
                return(Task.FromResult(true));
            }
                                                                 );

            var instanceDeploymentStatus = new InstanceDeploymentStatus();
            IDeploymentStatusWriter deploymentStatusWriterStub = new StubIDeploymentStatusWriter()
                                                                 .PublishInstanceDeploymentStatus((clusterId, instanceId, status) =>
            {
                instanceDeploymentStatus = status;
                return(Task.CompletedTask);
            });

            const string             ClusterId  = "clusterId";
            const string             InstanceId = "instanceId";
            ApplicationUpdateManager applicationUpdateManager = new ApplicationUpdateManager(ClusterId, InstanceId,
                                                                                             applicationDeploymentDirectory, applicationPool, applicationDownloader, applicationInstaller,
                                                                                             deploymentStatusWriterStub);
            await applicationUpdateManager.CheckForUpdates();

            Assert.Equal(3, applicationPool.Applications.Count());
            Assert.True(applicationPool.HasApplication(app1v3));
            Assert.True(applicationPool.HasApplication(app1v4));
            Assert.True(applicationPool.HasApplication(app1v5));

            Assert.Equal(3, instanceDeploymentStatus.Applications.Count());
            VerifyThatDeploymentStatusHasBeenUpdated(instanceDeploymentStatus, app1v3, ClusterId, InstanceId);
            VerifyThatDeploymentStatusHasBeenUpdated(instanceDeploymentStatus, app1v4, ClusterId, InstanceId);
            VerifyThatDeploymentStatusHasBeenUpdated(instanceDeploymentStatus, app1v5, ClusterId, InstanceId);
        }
Ejemplo n.º 9
0
        /// <summary>
        /// Synchronous downloading method using BITS
        /// </summary>
        /// <param name="sourceFile">Source file to download</param>
        /// <param name="destFile">Target file on the local system</param>
        /// <param name="maxTimeWait">Maximum time to wait for a download</param>
        void IDownloader.Download(string sourceFile, string destFile, TimeSpan maxTimeWait)
        {
            IBackgroundCopyManager backGroundCopyManager = null;
            IBackgroundCopyJob     backGroundCopyJob     = null;
            Guid         jobID                = Guid.Empty;
            bool         isCompleted          = false;
            bool         isSuccessful         = false;
            string       cumulativeErrMessage = "";
            BG_JOB_STATE state;

            //  to defend against config errors, check to see if the path given is UNC;
            //  if so, throw immediately there's a misconfiguration.  Paths to BITS must be HTTP/HTTPS
            ThrowIfSourceIsUNC(sourceFile);

            try
            {
                //  use utility function to create manager, job, get back jobid etc.; uses 'out' semantics
                CreateCopyJob(
                    out backGroundCopyManager,
                    out backGroundCopyJob,
                    ref jobID,
                    "RES_BITSJobName",
                    "RES_BITSDescription");

                // Add the file to the Job List
                backGroundCopyJob.AddFile(sourceFile, destFile);

                // Start the Back Ground Copy Job.
                backGroundCopyJob.Resume();

                //  set endtime to current tickcount + allowable # milliseconds to wait for job
                int endTime = Environment.TickCount + (int)maxTimeWait.TotalMilliseconds;

                #region __While Loop Waits On Single Download__

                while (!isCompleted)
                {
                    backGroundCopyJob.GetState(out state);
                    switch (state)
                    {
                    case BG_JOB_STATE.BG_JOB_STATE_ERROR:
                    {
                        //  use utility to:
                        //  a)  get error info
                        //  b)  report it
                        //  c)  cancel and remove copy job
                        HandleDownloadErrorCancelJob(backGroundCopyJob, ref cumulativeErrMessage);

                        //  complete loop, but DON'T say it's successful
                        isCompleted = true;
                        break;
                    }

                    case BG_JOB_STATE.BG_JOB_STATE_TRANSIENT_ERROR:
                    {
                        //  NOTE:  during debugging + test, transient errors resulted in complete job failure about 90%
                        //  of the time.  Therefore we treat transients just like full errors, and CANCEL the job
                        //  use utility to manage error etc.
                        HandleDownloadErrorCancelJob(backGroundCopyJob, ref cumulativeErrMessage);

                        //  stop the loop, set completed to true but not successful
                        isCompleted = true;
                        break;
                    }

                    case BG_JOB_STATE.BG_JOB_STATE_TRANSFERRED:
                    {
                        //  notify BITS we're happy, remove from queue and transfer ownership to us:
                        backGroundCopyJob.Complete();
                        //  remove job from our collection, we won't need to Cancel() in our Dispose()
                        RemoveCopyJobEntry(jobID);
                        isCompleted  = true;
                        isSuccessful = true;
                        break;
                    }

                    default:
                        break;
                    }

                    if (endTime < Environment.TickCount)
                    {
                        HandleDownloadErrorCancelJob(backGroundCopyJob, ref cumulativeErrMessage);
                        break;
                    }

                    //  Avoid 100% CPU utilisation with too tight a loop, let download happen.
                    Thread.Sleep(TIME_WAIT_SYNCH_DOWNLOAD);
                }

                #endregion

                if (!isSuccessful)
                {
                    //  create message + error, package it, publish
                    string error = ApplicationUpdateManager.TraceWrite(
                        "[BITSDownloader.Download]",
                        "RES_MESSAGE_ManifestFileNotDownloaded", sourceFile, cumulativeErrMessage);
                    Exception ex = new Exception(error + Environment.NewLine + cumulativeErrMessage);

                    throw ex;
                }
            }
            catch (ThreadInterruptedException tie)
            {
                //  if interrupted, clean up job
                HandleDownloadErrorCancelJob(backGroundCopyJob, ref cumulativeErrMessage);
                ApplicationUpdateManager.TraceWrite(tie, "[BITSDownloader.Download]", "RES_TIEInBITS", sourceFile);
                throw tie;
            }
            catch (Exception e)
            {
                //  if exception, clean up job
                HandleDownloadErrorCancelJob(backGroundCopyJob, ref cumulativeErrMessage);
                //  then log error
                string error = ApplicationUpdateManager.TraceWrite(
                    e,
                    "[BITSDownloader.Download]",
                    "RES_MESSAGE_ManifestFileNotDownloaded", sourceFile, cumulativeErrMessage);
                Exception ex = new Exception(error, e);
                ExceptionManager.Publish(ex);
                //  throw; allow consuming class to figure out what to do
                throw ex;
            }
            finally
            {
                if (null != backGroundCopyJob)
                {
                    Marshal.ReleaseComObject(backGroundCopyJob);
                }
                if (null != backGroundCopyManager)
                {
                    Marshal.ReleaseComObject(backGroundCopyManager);
                }
            }
        }
Ejemplo n.º 10
0
        /// <summary>
        /// Internal copy-job factory method.  Used to coordinate all aspects of a job set-up,
        /// which includes creating a copy manager, creating a job within it, setting download
        /// parameters, and adding the job to our tracking collection for cleanup later
        /// </summary>
        /// <param name="copyManager">null reference to copy manager</param>
        /// <param name="copyJob">null reference to copy job</param>
        /// <param name="jobID">null reference to job id guid</param>
        /// <param name="jobNameKey">the key used to look up the job name in the resource file</param>
        /// <param name="jobDescriptionKey">the key used to look up the job description in the resource file</param>
        private void CreateCopyJob(
            out IBackgroundCopyManager copyManager,
            out IBackgroundCopyJob copyJob,
            ref Guid jobID,
            string jobNameKey,
            string jobDescriptionKey)
        {
            string jobName = Resource.ResourceManager[jobNameKey];
            string jobDesc = Resource.ResourceManager[jobDescriptionKey];

            //  wrap in try-finally so we can clean COM objects if unexpected error
            try
            {
                //  create the manager
                copyManager = (IBackgroundCopyManager) new BackgroundCopyManager();

                // create the job, set its description, use "out" semantics to get jobid and the actual job object
                copyManager.CreateJob(
                    jobName,
                    BG_JOB_TYPE.BG_JOB_TYPE_DOWNLOAD,
                    out jobID,
                    out copyJob);

                //  set useful description
                copyJob.SetDescription(jobDesc);

                //  ***
                //      SET UP BITS JOB SETTINGS--TIMEOUTS/RETRY ETC
                //      SEE THE FOLLOWING REFERENCES:
                //  **  http://msdn.microsoft.com/library/default.asp?url=/library/en-us/bits/bits/ibackgroundcopyjob_setminimumretrydelay.asp?frame=true
                //  **  http://msdn.microsoft.com/library/default.asp?url=/library/en-us/bits/bits/ibackgroundcopyjob_setnoprogresstimeout.asp?frame=true
                //  **  http://msdn.microsoft.com/library/default.asp?url=/library/en-us/bits/bits/bg_job_priority.asp
                //  ***

                //  in constant set to 0; this makes BITS retry as soon as possible after an error
                copyJob.SetMinimumRetryDelay((uint)BITS_SET_MINIMUM_RETRY_DELAY);
                //  in constant set to 5 seconds; BITS will set job to Error status if exceeded
                copyJob.SetNoProgressTimeout((uint)BITS_SET_NO_PROGRESS_TIMEOUT);
                //  make this job the highest (but still background) priority--
                copyJob.SetPriority(BG_JOB_PRIORITY.BG_JOB_PRIORITY_HIGH);
                //  ***


                //  lock our internal collection of jobs, and add this job--we use this collection in Dispose()
                //  to tell BITS to Cancel() jobs--and remove them from the queue
                //  if we did not do this, BITS would continue for (by default) two weeks to download what we asked!
                lock (_jobs.SyncRoot)
                {
                    _jobs.Add(jobID, jobName);
                }
            }
            catch (Exception e)
            {
                //  bad to catch all exceptions, but OK because we adorn it with necessary additional info then pass it up as innerException
                string error = ApplicationUpdateManager.TraceWrite(e, "[BITSDownloader.CreateCopyJob]", "RES_EXCEPTION_BITSOtherError", jobID, jobName, jobDesc);
                //  publish
                Exception newE = new Exception(error, e);
                ExceptionManager.Publish(newE);
                //  rethrow;
                throw newE;
            }
        }
Ejemplo n.º 11
0
        /// <summary>
        /// returns a job status enum for a particular job identified by its GUID
        /// </summary>
        /// <param name="jobId">a guid for the job requested</param>
        /// <returns>a JobStatus describing the state of the job</returns>
        JobStatus IDownloader.GetJobStatus(Guid jobId)
        {
            IBackgroundCopyManager backGroundCopyManager = null;
            IBackgroundCopyJob     backGroundCopyJob     = null;
            BG_JOB_STATE           state;
            string errMessage = "";
            string jobName    = "";
            string jobDesc    = "";
            string error      = "";

            try
            {
                backGroundCopyManager = (IBackgroundCopyManager) new BackgroundCopyManager();
                backGroundCopyManager.GetJob(ref jobId, out backGroundCopyJob);

                //  get job name
                backGroundCopyJob.GetDisplayName(out jobName);
                //  get job desc
                backGroundCopyJob.GetDescription(out jobDesc);
                //  get job state enum value
                backGroundCopyJob.GetState(out state);

                switch (state)
                {
                case BG_JOB_STATE.BG_JOB_STATE_ERROR:
                {
                    //  use utility method to handle error:
                    HandleDownloadErrorCancelJob(backGroundCopyJob, ref errMessage);

                    //  return status as error
                    return(JobStatus.Error);
                }

                case BG_JOB_STATE.BG_JOB_STATE_TRANSIENT_ERROR:
                {
                    //    NOTE:  if transient, just treat as full error.  During testing about 90% of transients
                    //				resulted in full failure.  Cleanup.
                    //  use utility method to handle error:
                    HandleDownloadErrorCancelJob(backGroundCopyJob, ref errMessage);

                    //  return status as error
                    return(JobStatus.Error);
                }

                case BG_JOB_STATE.BG_JOB_STATE_TRANSFERRED:
                {
                    //  tell BITS to transfer to us and stop thinking about the job
                    backGroundCopyJob.Complete();
                    // remove job from collection to be Dispose()ed
                    RemoveCopyJobEntry(jobId);
                    return(JobStatus.Ready);
                }

                case BG_JOB_STATE.BG_JOB_STATE_CANCELLED:
                {
                    //  use utility method to handle error:
                    HandleDownloadErrorCancelJob(backGroundCopyJob, ref errMessage);

                    //  return status as cancelled
                    return(JobStatus.Cancelled);
                }

                default:
                    return(JobStatus.Downloading);
                }
            }
            catch (ThreadInterruptedException tie)
            {
                //  if interrupted, clean up job
                HandleDownloadErrorCancelJob(backGroundCopyJob, ref errMessage);
                ApplicationUpdateManager.TraceWrite(tie, "[BITSDownloader.Download]", "RES_TIEInBITS", "N/A");
                throw tie;
            }
            catch (Exception e)
            {
                //  use utility method to handle error:
                HandleDownloadErrorCancelJob(backGroundCopyJob, ref errMessage);
                //  bad to catch all exceptions, but OK because we adorn it with necessary additional info then pass it up as innerException
                error = ApplicationUpdateManager.TraceWrite(e, "[BITSDownloader.GetJobStatus]", "RES_EXCEPTION_BITSOtherError", jobId, jobName, jobDesc);
                //  publish
                Exception newE = new Exception(error, e);
                ExceptionManager.Publish(newE);
                //  rethrow;
                throw newE;
            }
            finally
            {
                if (backGroundCopyManager != null)
                {
                    Marshal.ReleaseComObject(backGroundCopyManager);
                }
                if (backGroundCopyJob != null)
                {
                    Marshal.ReleaseComObject(backGroundCopyJob);
                }
            }
        }
Ejemplo n.º 12
0
        public async Task TestMultipleUpdates()
        {
            string id1 = "appId1";
            var    v1  = new Version("1.0.0");
            var    v2  = new Version("2.0.0");
            var    v3  = new Version("3.0.0");
            var    v4  = new Version("4.0.0");
            var    v5  = new Version("5.0.0");

            AppIdentity app1v1 = new AppIdentity(id1, v1);
            AppIdentity app1v2 = new AppIdentity(id1, v2);
            AppIdentity app1v3 = new AppIdentity(id1, v3);
            AppIdentity app1v4 = new AppIdentity(id1, v4);
            AppIdentity app1v5 = new AppIdentity(id1, v5);

            IEnumerable <AppIdentity> appsToDeploy = new[] { app1v3, app1v4, app1v5 };

            IApplicationDeploymentDirectory applicationDeploymentDirectory = new StubIApplicationDeploymentDirectory
            {
                FetchDeployments_String = (deploymentId) => Task.FromResult(appsToDeploy)
            };

            IApplicationPool applicationPool = new ApplicationPoolStub();
            string           path            = Path.GetTempPath();
            await applicationPool.AddApplication(new ApplicationStub(app1v1, path));

            await applicationPool.AddApplication(new ApplicationStub(app1v2, path));

            await applicationPool.AddApplication(new ApplicationStub(app1v3, path));

            var downloadedApps = new List <AppIdentity>();
            IApplicationDownloader applicationDownloader = new StubIApplicationDownloader
            {
                DownloadApplication_AppIdentity = (appIdentity) =>
                {
                    downloadedApps.Add(appIdentity);
                    return(Task.FromResult(true));
                }
            };

            var    installedApps   = new List <AppIdentity>();
            var    uninstalledApps = new List <AppIdentity>();
            string updatedAppId    = null;
            IEnumerable <Version> versionsRemoved      = null;
            IEnumerable <Version> versionsAdded        = null;
            IApplicationInstaller applicationInstaller = new StubIApplicationInstaller
            {
                Install_AppIdentity = (appIdentity) =>
                {
                    installedApps.Add(appIdentity);
                    return(Task.FromResult(true));
                },
                UnInstall_AppIdentity = (appIdentity) =>
                {
                    uninstalledApps.Add(appIdentity);
                    return(Task.FromResult(true));
                },
                Update_String_IEnumerableOfVersion_IEnumerableOfVersion = (appId, versionsToRemove, versionToDeploy) =>
                {
                    updatedAppId    = appId;
                    versionsRemoved = versionsToRemove;
                    versionsAdded   = versionToDeploy;
                    return(Task.FromResult(true));
                }
            };

            ApplicationUpdateManager applicationUpdateManager = new ApplicationUpdateManager("deploymentId", applicationDeploymentDirectory, applicationPool, applicationDownloader, applicationInstaller);
            await applicationUpdateManager.CheckForUpdates();

            Assert.Equal(2, downloadedApps.Count);
            Assert.True(downloadedApps.Contains(app1v4));
            Assert.True(downloadedApps.Contains(app1v5));

            Assert.False(installedApps.Any());
            Assert.False(uninstalledApps.Any());

            Assert.Equal(id1, updatedAppId);
            Assert.Equal(new [] { v1, v2 }, versionsRemoved.ToList());
            Assert.Equal(new[] { v4, v5 }, versionsAdded.ToList());
        }