예제 #1
0
 /// <summary>
 /// Initilisation
 /// </summary>
 /// <remarks>LOUIS Yoann 18/07/2016 création</remarks>
 private void Initialisation()
 {
     // yl - De base en selectionne le module de selection des ecriture
     this.ModuleEnCours = EModule.SelectionEcriture;
     // yl - Gestion des abonnement
     this.GestionAbonnement();
 }
        /// <summary>
        /// Determines whether or not the local copy of the manifest for the specifed module is outdated.
        /// </summary>
        /// <exception cref="ArgumentOutOfRangeException">
        /// Will be thrown if the <see cref="EModule"/> passed to the function is not a valid value.
        /// </exception>
        protected virtual bool IsModuleManifestOutdated(EModule module)
        {
            string manifestPath;

            switch (module)
            {
            case EModule.Launcher:
            case EModule.Game:
            {
                manifestPath = this.FileManifestHandler.GetManifestPath((EManifestType)module, false);
                break;
            }

            default:
            {
                throw new ArgumentOutOfRangeException(nameof(module), module,
                                                      "An invalid module value was passed to RefreshModuleManifest.");
            }
            }

            if (File.Exists(manifestPath))
            {
                string remoteHash = GetRemoteModuleManifestChecksum(module);
                using (Stream file = File.OpenRead(manifestPath))
                {
                    string localHash = MD5Handler.GetStreamHash(file);

                    return(remoteHash != localHash);
                }
            }

            return(true);
        }
        /// <summary>
        /// Gets the checksum of the manifest for the specified module.
        /// </summary>
        protected virtual string GetRemoteModuleManifestChecksum(EModule Module)
        {
            string checksum;

            switch (Module)
            {
            case EModule.Launcher:
            {
                checksum = ReadRemoteFile(Manifest.GetLaunchpadManifestChecksumURL());
                break;
            }

            case EModule.Game:
            {
                checksum = ReadRemoteFile(Manifest.GetGameManifestChecksumURL());
                break;
            }

            default:
            {
                throw new ArgumentOutOfRangeException(nameof(Module), Module, null);
            }
            }

            return(Utilities.SanitizeString(checksum));
        }
        /// <summary>
        /// Gets the checksum of the manifest for the specified module.
        /// </summary>
        /// <param name="module">The module.</param>
        /// <returns>The checksum.</returns>
        /// <exception cref="ArgumentOutOfRangeException">
        /// Will be thrown if the <see cref="EModule"/> passed to the function is not a valid value.
        /// </exception>
        protected virtual string GetRemoteModuleManifestChecksum(EModule module)
        {
            string checksum;

            switch (module)
            {
            case EModule.Launcher:
            case EModule.Game:
            {
                checksum = ReadRemoteFile(this.FileManifestHandler.GetManifestChecksumURL((EManifestType)module)).RemoveLineSeparatorsAndNulls();
                break;
            }

            default:
            {
                throw new ArgumentOutOfRangeException
                      (
                          nameof(module),
                          module,
                          "An invalid module value was passed to GetRemoteModuleManifestChecksum."
                      );
            }
            }

            return(checksum.RemoveLineSeparatorsAndNulls());
        }
        /// <summary>
        /// Refreshes the current manifest by redownloading it, if required;
        /// </summary>
        /// <exception cref="ArgumentOutOfRangeException">
        /// Will be thrown if the <see cref="EModule"/> passed to the function is not a valid value.
        /// </exception>
        protected virtual void RefreshModuleManifest(EModule module)
        {
            bool manifestExists;

            switch (module)
            {
            case EModule.Launcher:
            case EModule.Game:
            {
                manifestExists = File.Exists(this.FileManifestHandler.GetManifestPath((EManifestType)module, false));
                break;
            }

            default:
            {
                throw new ArgumentOutOfRangeException(nameof(module), module,
                                                      "An invalid module value was passed to RefreshModuleManifest");
            }
            }

            if (manifestExists)
            {
                if (IsModuleManifestOutdated(module))
                {
                    DownloadModuleManifest(module);
                }
            }
            else
            {
                DownloadModuleManifest(module);
            }

            // Now update the handler instance
            this.FileManifestHandler.ReloadManifests((EManifestType)module);
        }
예제 #6
0
        /// <summary>
        /// Verifies and repairs the files of the specified module.
        /// </summary>
        public override void VerifyModule(EModule module)
        {
            List <ManifestEntry> manifest    = this.FileManifestHandler.GetManifest((EManifestType)module, false);
            List <ManifestEntry> brokenFiles = new List <ManifestEntry>();

            try
            {
                int verifiedFiles = 0;
                foreach (ManifestEntry fileEntry in manifest)
                {
                    ++verifiedFiles;

                    // Prepare the progress event contents
                    this.ModuleVerifyProgressArgs.IndicatorLabelMessage = GetVerifyIndicatorLabelMessage(Path.GetFileName(fileEntry.RelativePath),
                                                                                                         verifiedFiles, manifest.Count);
                    OnModuleVerifyProgressChanged();

                    if (!fileEntry.IsFileIntegrityIntact())
                    {
                        brokenFiles.Add(fileEntry);
                        Log.Info($"File \"{Path.GetFileName(fileEntry.RelativePath)}\" failed its integrity check and was queued for redownload.");
                    }
                }

                int downloadedFiles = 0;
                foreach (ManifestEntry fileEntry in brokenFiles)
                {
                    ++downloadedFiles;

                    // Prepare the progress event contents
                    this.ModuleDownloadProgressArgs.IndicatorLabelMessage = GetDownloadIndicatorLabelMessage(Path.GetFileName(fileEntry.RelativePath),
                                                                                                             downloadedFiles, brokenFiles.Count);
                    OnModuleDownloadProgressChanged();

                    for (int i = 0; i < this.Config.GetFileRetries(); ++i)
                    {
                        if (!fileEntry.IsFileIntegrityIntact())
                        {
                            DownloadManifestEntry(fileEntry, module);
                            Log.Info($"File \"{Path.GetFileName(fileEntry.RelativePath)}\" failed its integrity check again after redownloading. ({i} retries)");
                        }
                        else
                        {
                            break;
                        }
                    }
                }
            }
            catch (IOException ioex)
            {
                Log.Warn($"Verification of {module} files failed (IOException): " + ioex.Message);
                OnModuleInstallationFailed();
            }

            OnModuleInstallationFinished();
        }
        /// <summary>
        /// Downloads the manifest for the specified module, and backs up the old copy of the manifest.
        /// </summary>
        /// <exception cref="ArgumentOutOfRangeException">
        /// Will be thrown if the <see cref="EModule"/> passed to the function is not a valid value.
        /// </exception>
        protected virtual void DownloadModuleManifest(EModule module)
        {
            string remoteURL;
            string localPath;
            string oldLocalPath;

            switch (module)
            {
            case EModule.Launcher:
            {
                remoteURL    = ManifestHandler.GetLaunchpadManifestURL();
                localPath    = ManifestHandler.GetLaunchpadManifestPath();
                oldLocalPath = ManifestHandler.GetOldLaunchpadManifestPath();

                break;
            }

            case EModule.Game:
            {
                remoteURL    = FileManifestHandler.GetGameManifestURL();
                localPath    = ManifestHandler.GetGameManifestPath();
                oldLocalPath = ManifestHandler.GetOldGameManifestPath();

                break;
            }

            default:
            {
                throw new ArgumentOutOfRangeException(nameof(module), module,
                                                      "An invalid module value was passed to DownloadModuleManifest");
            }
            }

            try
            {
                // Delete the old backup (if there is one)
                if (File.Exists(oldLocalPath))
                {
                    File.Delete(oldLocalPath);
                }

                // Create a backup of the old manifest so that we can compare them when updating the game
                File.Move(localPath, oldLocalPath);
            }
            catch (IOException ioex)
            {
                Log.Warn("Failed to back up the old launcher manifest (IOException): " + ioex.Message);
            }

            DownloadRemoteFile(remoteURL, localPath);
        }
        /// <inheritdoc />
        public override bool IsModuleOutdated(EModule module)
        {
            try
            {
                Version local;
                Version remote;

                switch (module)
                {
                case EModule.Launcher:
                {
                    local  = this.LocalVersionService.GetLocalLauncherVersion();
                    remote = GetRemoteLauncherVersion();
                    break;
                }

                case EModule.Game:
                {
                    local  = this.LocalVersionService.GetLocalGameVersion();
                    remote = GetRemoteGameVersion();
                    break;
                }

                default:
                {
                    throw new ArgumentOutOfRangeException
                          (
                              nameof(module),
                              module,
                              "An invalid module value was passed to IsModuleOutdated."
                          );
                }
                }

                return(local < remote);
            }
            catch (WebException wex)
            {
                Log.Warn("Unable to determine whether or not the launcher was outdated (WebException): " + wex.Message);
                return(false);
            }
        }
        /// <summary>
        /// Determines whether or not the local copy of the manifest for the specifed module is outdated.
        /// </summary>
        protected virtual bool IsModuleManifestOutdated(EModule Module)
        {
            string manifestPath;

            switch (Module)
            {
            case EModule.Launcher:
            {
                manifestPath = ManifestHandler.GetLaunchpadManifestPath();
                break;
            }

            case EModule.Game:
            {
                manifestPath = ManifestHandler.GetGameManifestPath();
                break;
            }

            default:
            {
                throw new ArgumentOutOfRangeException(nameof(Module), Module, "The module passed to RefreshModuleManifest was invalid.");
            }
            }

            if (File.Exists(manifestPath))
            {
                string remoteHash = GetRemoteModuleManifestChecksum(Module);
                using (Stream file = File.OpenRead(manifestPath))
                {
                    string localHash = MD5Handler.GetStreamHash(file);

                    return(remoteHash != localHash);
                }
            }

            return(true);
        }
        public override bool IsModuleOutdated(EModule Module)
        {
            try
            {
                Version local;
                Version remote;

                switch (Module)
                {
                case EModule.Launcher:
                {
                    local  = Config.GetLocalLauncherVersion();
                    remote = GetRemoteLauncherVersion();
                    break;
                }

                case EModule.Game:
                {
                    local  = Config.GetLocalGameVersion();
                    remote = GetRemoteGameVersion();
                    break;
                }

                default:
                {
                    throw new ArgumentOutOfRangeException(nameof(Module), Module, null);
                }
                }

                return(local < remote);
            }
            catch (WebException wex)
            {
                Log.Warn("Unable to determine whether or not the launcher was outdated (WebException): " + wex.Message);
                return(false);
            }
        }
        /// <summary>
        /// Refreshes the current manifest by redownloading it, if required;
        /// </summary>
        /// <exception cref="ArgumentOutOfRangeException">
        /// Will be thrown if the <see cref="EModule"/> passed to the function is not a valid value.
        /// </exception>
        protected virtual void RefreshModuleManifest(EModule module)
        {
            bool doesManifestExist;

            switch (module)
            {
            case EModule.Launcher:
            {
                doesManifestExist = File.Exists(ManifestHandler.GetLaunchpadManifestPath());
                break;
            }

            case EModule.Game:
            {
                doesManifestExist = File.Exists(ManifestHandler.GetGameManifestPath());
                break;
            }

            default:
            {
                throw new ArgumentOutOfRangeException(nameof(module), module,
                                                      "An invalid module value was passed to RefreshModuleManifest");
            }
            }

            if (doesManifestExist)
            {
                if (IsModuleManifestOutdated(module))
                {
                    DownloadModuleManifest(module);
                }
            }
            else
            {
                DownloadModuleManifest(module);
            }
        }
        protected virtual void DownloadManifestEntry(ManifestEntry Entry, EModule Module)
        {
            ModuleDownloadProgressArgs.Module = Module;

            string baseRemoteURL;
            string baseLocalPath;

            switch (Module)
            {
            case EModule.Launcher:
            {
                baseRemoteURL = Config.GetLauncherBinariesURL();
                baseLocalPath = ConfigHandler.GetTempLauncherDownloadPath();
                break;
            }

            case EModule.Game:
            {
                baseRemoteURL = Config.GetGameURL();
                baseLocalPath = Config.GetGamePath();
                break;
            }

            default:
            {
                throw new ArgumentOutOfRangeException(nameof(Module), Module, "The module passed to DownloadManifestEntry was invalid.");
            }
            }

            // Build the access strings
            string remoteURL = $"{baseRemoteURL}{Entry.RelativePath}";
            string localPath = $"{baseLocalPath}{Path.DirectorySeparatorChar}{Entry.RelativePath}";

            // Make sure we have a directory to put the file in
            if (Path.GetDirectoryName(localPath) != null)
            {
                Directory.CreateDirectory(Path.GetDirectoryName(localPath));
            }
            else
            {
                throw new ArgumentNullException(nameof(localPath), "The local path was null.");
            }

            // Reset the cookie
            File.WriteAllText(ConfigHandler.GetInstallCookiePath(), string.Empty);

            // Write the current file progress to the install cookie
            using (TextWriter textWriterProgress = new StreamWriter(ConfigHandler.GetInstallCookiePath()))
            {
                textWriterProgress.WriteLine(Entry);
                textWriterProgress.Flush();
            }

            if (File.Exists(localPath))
            {
                FileInfo fileInfo = new FileInfo(localPath);
                if (fileInfo.Length != Entry.Size)
                {
                    // If the file is partial, resume the download.
                    if (fileInfo.Length < Entry.Size)
                    {
                        Log.Info($"Resuming interrupted file \"{Path.GetFileNameWithoutExtension(Entry.RelativePath)}\" at byte {fileInfo.Length}.");
                        DownloadRemoteFile(remoteURL, localPath, Entry.Size, fileInfo.Length);
                    }
                    else
                    {
                        // If it's larger than expected, toss it in the bin and try again.
                        Log.Info($"Restarting interrupted file \"{Path.GetFileNameWithoutExtension(Entry.RelativePath)}\": File bigger than expected.");

                        File.Delete(localPath);
                        DownloadRemoteFile(remoteURL, localPath, Entry.Size);
                    }
                }
                else
                {
                    string localHash;
                    using (FileStream fs = File.OpenRead(localPath))
                    {
                        localHash = MD5Handler.GetStreamHash(fs);
                    }

                    if (localHash != Entry.Hash)
                    {
                        // If the hash doesn't match, toss it in the bin and try again.
                        Log.Info($"Redownloading file \"{Path.GetFileNameWithoutExtension(Entry.RelativePath)}\": " +
                                 $"Hash sum mismatch. Local: {localHash}, Expected: {Entry.Hash}");

                        File.Delete(localPath);
                        DownloadRemoteFile(remoteURL, localPath, Entry.Size);
                    }
                }
            }
            else
            {
                // No file, download it
                DownloadRemoteFile(remoteURL, localPath, Entry.Size);
            }

            if (ChecksHandler.IsRunningOnUnix())
            {
                // If we're dealing with a file that should be executable,
                string gameName = Config.GetGameName();
                bool   bFileIsGameExecutable = (Path.GetFileName(localPath).EndsWith(".exe")) || (Path.GetFileName(localPath) == gameName);
                if (bFileIsGameExecutable)
                {
                    // Set the execute bits
                    UnixHandler.MakeExecutable(localPath);
                }
            }

            // We've finished the download, so empty the cookie
            File.WriteAllText(ConfigHandler.GetInstallCookiePath(), string.Empty);
        }
예제 #13
0
 protected override void DownloadModule(EModule module)
 {
     throw new NotImplementedException();
 }
        /// <summary>
        /// Downloads the latest version of the specified module.
        /// </summary>
        /// <exception cref="ArgumentOutOfRangeException">
        /// Will be thrown if the <see cref="EModule"/> passed to the function is not a valid value.
        /// </exception>
        protected override void DownloadModule(EModule module)
        {
            IReadOnlyList <ManifestEntry> moduleManifest;

            switch (module)
            {
            case EModule.Launcher:
            {
                RefreshModuleManifest(EModule.Launcher);

                this.ModuleInstallFinishedArgs.Module = EModule.Launcher;
                this.ModuleInstallFailedArgs.Module   = EModule.Launcher;
                moduleManifest = this.FileManifestHandler.GetManifest(EManifestType.Launchpad, false);
                break;
            }

            case EModule.Game:
            {
                RefreshModuleManifest(EModule.Game);

                this.ModuleInstallFinishedArgs.Module = EModule.Game;
                this.ModuleInstallFailedArgs.Module   = EModule.Game;
                moduleManifest = this.FileManifestHandler.GetManifest(EManifestType.Game, false);
                break;
            }

            default:
            {
                throw new ArgumentOutOfRangeException(nameof(module), module,
                                                      "An invalid module value was passed to DownloadModule.");
            }
            }

            if (moduleManifest == null)
            {
                Log.Error($"No manifest was found when installing the module \"{module}\". The server files may be inaccessible or missing.");
                OnModuleInstallationFailed();
                return;
            }

            // In order to be able to resume downloading, we check if there is an entry
            // stored in the install cookie.

            // Attempt to parse whatever is inside the install cookie
            ManifestEntry lastDownloadedFile;

            if (ManifestEntry.TryParse(File.ReadAllText(ConfigHandler.GetGameCookiePath()), out lastDownloadedFile))
            {
                // Loop through all the entries in the manifest until we encounter
                // an entry which matches the one in the install cookie

                foreach (ManifestEntry fileEntry in moduleManifest)
                {
                    if (lastDownloadedFile.Equals(fileEntry))
                    {
                        // Skip all entries before the one we were last at.
                        moduleManifest = moduleManifest.Skip(moduleManifest.ToList().IndexOf(fileEntry)).ToList();
                    }
                }
            }

            int downloadedFiles = 0;

            foreach (ManifestEntry fileEntry in moduleManifest)
            {
                ++downloadedFiles;

                // Prepare the progress event contents
                this.ModuleDownloadProgressArgs.IndicatorLabelMessage = GetDownloadIndicatorLabelMessage(Path.GetFileName(fileEntry.RelativePath),
                                                                                                         downloadedFiles, moduleManifest.Count);
                OnModuleDownloadProgressChanged();

                DownloadManifestEntry(fileEntry, module);
            }
        }
        /// <summary>
        /// Downloads the file referred to by the specifed manifest entry.
        /// </summary>
        /// <param name="fileEntry">The entry to download.</param>
        /// <param name="module">The module that the entry belongs to.</param>
        /// <param name="oldFileEntry">The old entry, if one exists.</param>
        /// <exception cref="ArgumentOutOfRangeException">
        /// Will be thrown if the <see cref="EModule"/> passed to the function is not a valid value.
        /// </exception>
        /// <exception cref="ArgumentNullException">
        /// Will be thrown if the local path set in the <paramref name="fileEntry"/> passed to the function is not a valid value.
        /// </exception>
        protected virtual void DownloadManifestEntry(ManifestEntry fileEntry, EModule module, ManifestEntry oldFileEntry = null)
        {
            this.ModuleDownloadProgressArgs.Module = module;

            string baseRemoteURL;
            string baseLocalPath;

            switch (module)
            {
            case EModule.Launcher:
            {
                baseRemoteURL = this.Config.GetLauncherBinariesURL();
                baseLocalPath = ConfigHandler.GetTempLauncherDownloadPath();
                break;
            }

            case EModule.Game:
            {
                baseRemoteURL = this.Config.GetGameURL();
                baseLocalPath = this.Config.GetGamePath();
                break;
            }

            default:
            {
                throw new ArgumentOutOfRangeException(nameof(module), module,
                                                      "An invalid module value was passed to DownloadManifestEntry.");
            }
            }

            // Build the access strings
            string remoteURL = $"{baseRemoteURL}{fileEntry.RelativePath}";
            string localPath = $"{baseLocalPath}{fileEntry.RelativePath}";

            // Make sure we have a directory to put the file in
            if (!string.IsNullOrEmpty(localPath))
            {
                string localPathParentDir = Path.GetDirectoryName(localPath);
                if (!Directory.Exists(localPathParentDir))
                {
                    Directory.CreateDirectory(Path.GetDirectoryName(localPath));
                }
            }
            else
            {
                throw new ArgumentNullException(nameof(localPath), "The local path was null or empty.");
            }

            // Reset the cookie
            File.WriteAllText(ConfigHandler.GetGameCookiePath(), string.Empty);

            // Write the current file progress to the install cookie
            using (TextWriter textWriterProgress = new StreamWriter(ConfigHandler.GetGameCookiePath()))
            {
                textWriterProgress.WriteLine(fileEntry);
                textWriterProgress.Flush();
            }

            // First, let's see if an old file exists, and is valid.
            if (oldFileEntry != null)
            {
                // Check if the file is present, the correct size, and the correct hash
                if (oldFileEntry.IsFileIntegrityIntact())
                {
                    // If it is, delete it.
                    File.Delete(localPath);
                }
            }

            if (File.Exists(localPath))
            {
                FileInfo fileInfo = new FileInfo(localPath);
                if (fileInfo.Length != fileEntry.Size)
                {
                    // If the file is partial, resume the download.
                    if (fileInfo.Length < fileEntry.Size)
                    {
                        Log.Info($"Resuming interrupted file \"{Path.GetFileNameWithoutExtension(fileEntry.RelativePath)}\" at byte {fileInfo.Length}.");
                        DownloadRemoteFile(remoteURL, localPath, fileEntry.Size, fileInfo.Length);
                    }
                    else
                    {
                        // If it's larger than expected, toss it in the bin and try again.
                        Log.Info($"Restarting interrupted file \"{Path.GetFileNameWithoutExtension(fileEntry.RelativePath)}\": File bigger than expected.");

                        File.Delete(localPath);
                        DownloadRemoteFile(remoteURL, localPath, fileEntry.Size);
                    }
                }
                else
                {
                    string localHash;
                    using (FileStream fs = File.OpenRead(localPath))
                    {
                        localHash = MD5Handler.GetStreamHash(fs);
                    }

                    if (localHash != fileEntry.Hash)
                    {
                        // If the hash doesn't match, toss it in the bin and try again.
                        Log.Info($"Redownloading file \"{Path.GetFileNameWithoutExtension(fileEntry.RelativePath)}\": " +
                                 $"Hash sum mismatch. Local: {localHash}, Expected: {fileEntry.Hash}");

                        File.Delete(localPath);
                        DownloadRemoteFile(remoteURL, localPath, fileEntry.Size);
                    }
                }
            }
            else
            {
                // No file, download it
                DownloadRemoteFile(remoteURL, localPath, fileEntry.Size);
            }

            // We've finished the download, so empty the cookie
            File.WriteAllText(ConfigHandler.GetGameCookiePath(), string.Empty);
        }
예제 #16
0
 /// <summary>
 /// Passes the internal event in the protocol handler to the outward-facing
 /// event.
 /// </summary>
 /// <param name="sender">Sender.</param>
 /// <param name="e">E.</param>
 private void OnModuleInstallationFailed(object sender, EModule e)
 {
     this.DownloadFailed?.Invoke(sender, EventArgs.Empty);
 }
        /// <summary>
        /// Updates the specified module to the latest version.
        /// </summary>
        /// <param name="module">The module to update.</param>
        /// <exception cref="ArgumentOutOfRangeException">
        /// Will be thrown if the <see cref="EModule"/> passed to the function is not a valid value.
        /// </exception>
        public override void UpdateModule(EModule module)
        {
            IReadOnlyList <ManifestEntry> manifest;
            IReadOnlyList <ManifestEntry> oldManifest;

            switch (module)
            {
            case EModule.Launcher:
            {
                RefreshModuleManifest(EModule.Launcher);

                this.ModuleInstallFinishedArgs.Module = EModule.Launcher;
                this.ModuleInstallFailedArgs.Module   = EModule.Launcher;
                manifest    = this.FileManifestHandler.GetManifest(EManifestType.Launchpad, false);
                oldManifest = this.FileManifestHandler.GetManifest(EManifestType.Launchpad, true);
                break;
            }

            case EModule.Game:
            {
                RefreshModuleManifest(EModule.Game);

                this.ModuleInstallFinishedArgs.Module = EModule.Game;
                this.ModuleInstallFailedArgs.Module   = EModule.Game;
                manifest    = this.FileManifestHandler.GetManifest(EManifestType.Game, false);
                oldManifest = this.FileManifestHandler.GetManifest(EManifestType.Game, true);
                break;
            }

            default:
            {
                throw new ArgumentOutOfRangeException(nameof(module), module, "An invalid module value was passed to UpdateModule.");
            }
            }

            // Check to see if we have valid manifests
            if (manifest == null)
            {
                Log.Error($"No manifest was found when updating the module \"{module}\". The server files may be inaccessible or missing.");
                OnModuleInstallationFailed();
                return;
            }

            // This dictionary holds a list of new entries and their equivalents from the old manifest. It is used
            // to determine whether or not a file is partial, or merely old yet smaller.
            Dictionary <ManifestEntry, ManifestEntry> oldEntriesBeingReplaced = new Dictionary <ManifestEntry, ManifestEntry>();
            List <ManifestEntry> filesRequiringUpdate = new List <ManifestEntry>();

            foreach (ManifestEntry fileEntry in manifest)
            {
                filesRequiringUpdate.Add(fileEntry);
                if (oldManifest != null)
                {
                    if (!oldManifest.Contains(fileEntry))
                    {
                        // See if there is an old entry which matches the new one.
                        ManifestEntry matchingOldEntry =
                            oldManifest.FirstOrDefault(oldEntry => oldEntry.RelativePath == fileEntry.RelativePath);

                        if (matchingOldEntry != null)
                        {
                            oldEntriesBeingReplaced.Add(fileEntry, matchingOldEntry);
                        }
                    }
                }
            }

            try
            {
                int updatedFiles = 0;
                foreach (ManifestEntry fileEntry in filesRequiringUpdate)
                {
                    ++updatedFiles;

                    this.ModuleUpdateProgressArgs.IndicatorLabelMessage = GetUpdateIndicatorLabelMessage(Path.GetFileName(fileEntry.RelativePath),
                                                                                                         updatedFiles,
                                                                                                         filesRequiringUpdate.Count);
                    OnModuleUpdateProgressChanged();

                    // If we're updating an existing file, make sure to let the downloader know
                    if (oldEntriesBeingReplaced.ContainsKey(fileEntry))
                    {
                        DownloadManifestEntry(fileEntry, module, oldEntriesBeingReplaced[fileEntry]);
                    }
                    else
                    {
                        DownloadManifestEntry(fileEntry, module);
                    }
                }
            }
            catch (IOException ioex)
            {
                Log.Warn($"Updating of {module} files failed (IOException): " + ioex.Message);
                OnModuleInstallationFailed();
                return;
            }

            OnModuleInstallationFinished();
        }
예제 #18
0
 /// <summary>
 /// Changeemnt de module
 /// </summary>
 /// <param name="pModule">Module appeler</param>
 /// <remarks>LOUIS Yoann 06/09/2016</remarks>
 private void ChangeModule(EModule pModule)
 {
     // yl - Affectation du module
     this.ModuleEnCours = pModule;
 }
예제 #19
0
 /// <summary>
 /// Invoke the <see cref="ModuleInstallationFailed"/> event.
 /// </summary>
 /// <param name="module">The module that failed.</param>
 protected void OnModuleInstallationFailed(EModule module)
 {
     this.ModuleInstallationFailed?.Invoke(this, module);
 }
예제 #20
0
 private void OnLauncherDownloadFinished(object sender, EModule e)
 {
     this.LauncherDownloadFinished?.Invoke(sender, EventArgs.Empty);
 }
        public override void UpdateModule(EModule Module)
        {
            List <ManifestEntry> Manifest;
            List <ManifestEntry> OldManifest;

            switch (Module)
            {
            case EModule.Launcher:
            {
                RefreshModuleManifest(EModule.Launcher);


                ModuleInstallFinishedArgs.Module = EModule.Launcher;
                ModuleInstallFailedArgs.Module   = EModule.Launcher;
                Manifest    = this.Manifest.LaunchpadManifest;
                OldManifest = this.Manifest.OldLaunchpadManifest;
                break;
            }

            case EModule.Game:
            {
                RefreshModuleManifest(EModule.Game);


                ModuleInstallFinishedArgs.Module = EModule.Game;
                ModuleInstallFailedArgs.Module   = EModule.Game;
                Manifest    = this.Manifest.GameManifest;
                OldManifest = this.Manifest.OldGameManifest;
                break;
            }

            default:
            {
                throw new ArgumentOutOfRangeException(nameof(Module), Module, null);
            }
            }

            List <ManifestEntry> FilesRequiringUpdate = new List <ManifestEntry>();

            foreach (ManifestEntry Entry in Manifest)
            {
                if (!OldManifest.Contains(Entry))
                {
                    FilesRequiringUpdate.Add(Entry);
                }
            }

            try
            {
                int updatedFiles = 0;
                foreach (ManifestEntry Entry in FilesRequiringUpdate)
                {
                    ++updatedFiles;

                    ModuleUpdateProgressArgs.IndicatorLabelMessage = GetUpdateIndicatorLabelMessage(Path.GetFileName(Entry.RelativePath),
                                                                                                    updatedFiles,
                                                                                                    FilesRequiringUpdate.Count);
                    OnModuleUpdateProgressChanged();

                    DownloadManifestEntry(Entry, Module);
                }
            }
            catch (IOException ioex)
            {
                Log.Warn($"Updating of {Module} files failed (IOException): " + ioex.Message);
                OnModuleInstallationFailed();
            }

            OnModuleInstallationFinished();
        }
        /// <inheritdoc />
        public override void VerifyModule(EModule module)
        {
            var manifest    = this.FileManifestHandler.GetManifest((EManifestType)module, false);
            var brokenFiles = new List <ManifestEntry>();

            if (manifest == null)
            {
                Log.Error($"No manifest was found when verifying the module \"{module}\". The server files may be inaccessible or missing.");
                OnModuleInstallationFailed(module);
                return;
            }

            try
            {
                var verifiedFiles = 0;
                foreach (var fileEntry in manifest)
                {
                    ++verifiedFiles;

                    // Prepare the progress event contents
                    this.ModuleVerifyProgressArgs.IndicatorLabelMessage = GetVerifyIndicatorLabelMessage
                                                                          (
                        Path.GetFileName(fileEntry.RelativePath),
                        verifiedFiles,
                        manifest.Count
                                                                          );
                    OnModuleVerifyProgressChanged();

                    if (fileEntry.IsFileIntegrityIntact())
                    {
                        continue;
                    }

                    brokenFiles.Add(fileEntry);
                    Log.Info($"File \"{Path.GetFileName(fileEntry.RelativePath)}\" failed its integrity check and was queued for redownload.");
                }

                var downloadedFiles = 0;
                foreach (var fileEntry in brokenFiles)
                {
                    ++downloadedFiles;

                    // Prepare the progress event contents
                    this.ModuleDownloadProgressArgs.IndicatorLabelMessage = GetDownloadIndicatorLabelMessage
                                                                            (
                        Path.GetFileName(fileEntry.RelativePath),
                        downloadedFiles,
                        brokenFiles.Count
                                                                            );
                    OnModuleDownloadProgressChanged();

                    for (int i = 0; i < this.Configuration.RemoteFileDownloadRetries; ++i)
                    {
                        if (!fileEntry.IsFileIntegrityIntact())
                        {
                            DownloadManifestEntry(fileEntry, module);
                            Log.Info($"File \"{Path.GetFileName(fileEntry.RelativePath)}\" failed its integrity check again after redownloading. ({i} retries)");
                        }
                        else
                        {
                            break;
                        }
                    }
                }
            }
            catch (IOException ioex)
            {
                Log.Warn($"Verification of {module} files failed (IOException): " + ioex.Message);
                OnModuleInstallationFailed(module);
            }

            OnModuleInstallationFinished(module);
        }
예제 #23
0
 /// <summary>
 /// Updates the specified module to the latest version.
 /// </summary>
 /// <param name="module">The module to update.</param>
 public abstract void UpdateModule(EModule module);
예제 #24
0
 /// <summary>
 /// Determines whether or not the specified module is outdated.
 /// </summary>
 /// <param name="module">The module.</param>
 /// <returns>true if the module is outdated; otherwise, false.</returns>
 public abstract bool IsModuleOutdated(EModule module);
예제 #25
0
 public override bool IsModuleOutdated(EModule module)
 {
     throw new NotImplementedException();
 }
예제 #26
0
        /// <summary>
        /// Downloads the provided manifest entry.
        /// This function resumes incomplete files, verifies downloaded files and
        /// downloads missing files.
        /// </summary>
        /// <param name="Entry">The entry to download.</param>
        /// <param name="Module">The module to download the file for. Determines download location.</param>
        private void DownloadEntry(ManifestEntry Entry, EModule Module)
        {
            ModuleDownloadProgressArgs.Module = Module;

            string baseRemotePath;
            string baseLocalPath;

            if (Module == EModule.Game)
            {
                baseRemotePath = Config.GetGameURL();
                baseLocalPath  = Config.GetGamePath();
            }
            else
            {
                baseRemotePath = Config.GetLauncherBinariesURL();
                baseLocalPath  = ConfigHandler.GetTempLauncherDownloadPath();
            }

            string RemotePath = String.Format("{0}{1}",
                                              baseRemotePath,
                                              Entry.RelativePath);

            string LocalPath = String.Format("{0}{1}{2}",
                                             baseLocalPath,
                                             Path.DirectorySeparatorChar,
                                             Entry.RelativePath);

            // Make sure we have a directory to put the file in
            Directory.CreateDirectory(Path.GetDirectoryName(LocalPath));

            // Reset the cookie
            File.WriteAllText(ConfigHandler.GetInstallCookiePath(), String.Empty);

            // Write the current file progress to the install cookie
            using (TextWriter textWriterProgress = new StreamWriter(ConfigHandler.GetInstallCookiePath()))
            {
                textWriterProgress.WriteLine(Entry);
                textWriterProgress.Flush();
            }

            if (File.Exists(LocalPath))
            {
                FileInfo fileInfo = new FileInfo(LocalPath);
                if (fileInfo.Length != Entry.Size)
                {
                    // If the file is partial, resume the download.
                    if (fileInfo.Length < Entry.Size)
                    {
                        DownloadRemoteFile(RemotePath, LocalPath, fileInfo.Length);
                    }
                    else
                    {
                        // If it's larger than expected, toss it in the bin and try again.
                        File.Delete(LocalPath);
                        DownloadRemoteFile(RemotePath, LocalPath);
                    }
                }
                else
                {
                    string LocalHash;
                    using (FileStream fs = File.OpenRead(LocalPath))
                    {
                        LocalHash = MD5Handler.GetStreamHash(fs);
                    }

                    if (LocalHash != Entry.Hash)
                    {
                        File.Delete(LocalPath);
                        DownloadRemoteFile(RemotePath, LocalPath);
                    }
                }
            }
            else
            {
                //no file, download it
                DownloadRemoteFile(RemotePath, LocalPath);
            }

            if (ChecksHandler.IsRunningOnUnix())
            {
                //if we're dealing with a file that should be executable,
                string gameName = Config.GetGameName();
                bool   bFileIsGameExecutable = (Path.GetFileName(LocalPath).EndsWith(".exe")) || (Path.GetFileName(LocalPath) == gameName);
                if (bFileIsGameExecutable)
                {
                    //set the execute bits
                    UnixHandler.MakeExecutable(LocalPath);
                }
            }

            // We've finished the download, so empty the cookie
            File.WriteAllText(ConfigHandler.GetInstallCookiePath(), String.Empty);
        }
예제 #27
0
 /// <summary>
 /// Downloads the latest version of the specified module.
 /// </summary>
 /// <param name="module">The module.</param>
 protected abstract void DownloadModule(EModule module);
예제 #28
0
 public override void UpdateModule(EModule module)
 {
     throw new NotImplementedException();
 }
예제 #29
0
 /// <summary>
 /// Verifies and repairs the files of the specified module.
 /// </summary>
 /// <param name="module">The module.</param>
 public abstract void VerifyModule(EModule module);
예제 #30
0
 public override void VerifyModule(EModule module)
 {
     throw new NotImplementedException();
 }