private static void UpdateAssetMap(PatchManifest patchManifest, PatchBundle patchBundle)
        {
            // 构建主动收集的资源路径和资源包之间的映射关系。
            // 注意:这里面不包括依赖的非主动收集资源。
            foreach (var assetPath in patchBundle.CollectAssets)
            {
                // 添加原始路径
                // 注意:我们不允许原始路径存在重名
                if (patchManifest.AssetsMapping.ContainsKey(assetPath))
                {
                    throw new Exception($"Asset path have existed : {assetPath}");
                }
                patchManifest.AssetsMapping.Add(assetPath, patchBundle);

                // 添加去掉后缀名的路径
                if (Path.HasExtension(assetPath))
                {
                    string assetPathWithoutExtension = assetPath.RemoveExtension();
                    if (patchManifest.AssetsMapping.ContainsKey(assetPathWithoutExtension))
                    {
                        MotionLog.Warning($"Asset path have existed : {assetPathWithoutExtension}");
                    }
                    else
                    {
                        patchManifest.AssetsMapping.Add(assetPathWithoutExtension, patchBundle);
                    }
                }
            }
        }
        /// <summary>
        /// 反序列化
        /// </summary>
        public static PatchManifest Deserialize(string jsonData)
        {
            PatchManifest patchManifest = JsonUtility.FromJson <PatchManifest>(jsonData);

            // 构建资源包集合
            foreach (var patchBundle in patchManifest.BundleList)
            {
                patchManifest.Bundles.Add(patchBundle.BundleName, patchBundle);

                // 解析标记位
                PatchBundle.ParseFlags(patchBundle.Flags, out patchBundle.IsEncrypted);

                // 解析依赖列表
                patchBundle.Depends = GetDepends(patchManifest, patchBundle);

                // 构建资源映射集合
                UpdateAssetMap(patchManifest, patchBundle);
            }

            // 构建变种集合
            foreach (var variant in patchManifest.VariantList)
            {
                patchManifest.Variants.Add(variant.BundleName, variant);
            }

            return(patchManifest);
        }
        private static int[] GetPatchDpendIDs(PatchManifest patchManifest, PatchBundle patchBundle)
        {
            List <int> result = new List <int>();

            foreach (var bundleName in patchBundle.Depends)
            {
                int dependID = GetPatchDependID(patchManifest, bundleName);
                result.Add(dependID);
            }
            return(result.ToArray());
        }
Exemplo n.º 4
0
        private WebFileRequest CreateDownloader(PatchBundle element)
        {
            // 注意:资源版本号只用于确定下载路径
            string url      = _patcher.GetWebDownloadURL(element.Version.ToString(), element.Hash);
            string savePath = PatchHelper.MakeSandboxCacheFilePath(element.Hash);

            FileUtility.CreateFileDirectory(savePath);

            // 创建下载器
            MotionLog.Log($"Beginning to download web file : {url}");
            WebFileRequest download = new WebFileRequest(url, savePath);

            download.UserData = element;
            download.DownLoad();
            return(download);
        }
Exemplo n.º 5
0
        private WebFileRequest CreateDownloader(PatchBundle patchBundle)
        {
            // 注意:资源版本号只用于确定下载路径
            string mainURL     = _patcherMgr.GetPatchDownloadURL(patchBundle.Version, patchBundle.Hash);
            string fallbackURL = _patcherMgr.GetPatchDownloadFallbackURL(patchBundle.Version, patchBundle.Hash);
            string savePath    = PatchHelper.MakeSandboxCacheFilePath(patchBundle.Hash);

            FileUtility.CreateFileDirectory(savePath);

            // 创建下载器
            MotionLog.Log($"Beginning to download web file : {patchBundle.BundleName} URL : {mainURL}");
            WebFileRequest download = WebFileSystem.GetWebFileRequest(mainURL, fallbackURL, savePath, _failedTryAgain);

            download.UserData = patchBundle;
            return(download);
        }
        private static string[] GetDepends(PatchManifest patchManifest, PatchBundle patchBundle)
        {
            List <string> result = new List <string>(patchBundle.DependIDs.Length);

            foreach (var dependID in patchBundle.DependIDs)
            {
                if (dependID >= 0 && dependID < patchManifest.BundleList.Count)
                {
                    var dependPatchBundle = patchManifest.BundleList[dependID];
                    result.Add(dependPatchBundle.BundleName);
                }
                else
                {
                    throw new Exception($"Invalid depend id : {dependID} : {patchBundle.BundleName}");
                }
            }
            return(result.ToArray());
        }
Exemplo n.º 7
0
 public bool CheckContentIntegrity(PatchBundle patchBundle)
 {
     return(CheckContentIntegrity(patchBundle.Hash, patchBundle.CRC, patchBundle.SizeBytes));
 }
Exemplo n.º 8
0
        /// <summary>
        /// 更新下载器
        /// </summary>
        public void Update()
        {
            if (DownloadStates != EDownloaderStates.Loading)
            {
                return;
            }

            // 检测下载器结果
            for (int i = _loaders.Count - 1; i >= 0; i--)
            {
                var loader = _loaders[i];
                if (loader.IsDone() == false)
                {
                    continue;
                }

                PatchBundle element = loader.UserData as PatchBundle;

                // 检测是否下载失败
                if (loader.HasError())
                {
                    loader.ReportError();
                    loader.Dispose();
                    _loaders.RemoveAt(i);
                    _loadFailedList.Add(element);
                    continue;
                }

                // 验证下载文件完整性
                if (_patcher.CheckContentIntegrity(element) == false)
                {
                    MotionLog.Error($"Check download content integrity is failed : {element.BundleName}");
                    loader.Dispose();
                    _loaders.RemoveAt(i);
                    _checkFailedList.Add(element);
                    continue;
                }

                // 下载成功
                loader.Dispose();
                _loaders.RemoveAt(i);
                _succeedList.Add(element);
                CurrentDownloadCount++;
                CurrentDownloadBytes += element.SizeBytes;
                OnPatchFileDownloadSucceedCallback?.Invoke(TotalDownloadCount, CurrentDownloadCount, TotalDownloadBytes, CurrentDownloadBytes);
            }

            // 动态创建新的下载器到最大数量限制
            // 注意:如果期间有下载失败的文件,暂停动态创建下载器
            if (_downloadList.Count > 0 && _loadFailedList.Count == 0 && _checkFailedList.Count == 0)
            {
                if (_loaders.Count < _maxNumberOnLoad)
                {
                    int            index      = _downloadList.Count - 1;
                    WebFileRequest downloader = CreateDownloader(_downloadList[index]);
                    _loaders.Add(downloader);
                    _downloadList.RemoveAt(index);
                }
            }

            // 下载结算
            if (_loaders.Count == 0)
            {
                // 更新缓存并保存
                if (_succeedList.Count > 0)
                {
                    _patcher.CacheDownloadPatchFiles(_succeedList);
                }

                if (_loadFailedList.Count > 0)
                {
                    DownloadStates = EDownloaderStates.Failed;
                    OnPatchFileDownloadFailedCallback?.Invoke(_loadFailedList[0].BundleName);
                }
                else if (_checkFailedList.Count > 0)
                {
                    DownloadStates = EDownloaderStates.Failed;
                    OnPatchFileCheckFailedCallback?.Invoke(_checkFailedList[0].BundleName);
                }
                else
                {
                    // 结算成功
                    DownloadStates = EDownloaderStates.Succeed;
                }
            }
        }
Exemplo n.º 9
0
        /// <summary>
        /// 更新下载器
        /// </summary>
        public void Update()
        {
            if (DownloadStates != EDownloaderStates.Loading)
            {
                return;
            }

            // 检测下载器结果
            _removeList.Clear();
            long downloadBytes = CurrentDownloadBytes;

            foreach (var loader in _downloaders)
            {
                downloadBytes += (long)loader.DownloadedBytes;
                if (loader.IsDone() == false)
                {
                    continue;
                }

                PatchBundle patchBundle = loader.UserData as PatchBundle;

                // 检测是否下载失败
                if (loader.HasError())
                {
                    loader.ReportError();
                    loader.Dispose();
                    _removeList.Add(loader);
                    _loadFailedList.Add(patchBundle);
                    continue;
                }

                // 验证下载文件完整性
                if (_patcherMgr.CheckContentIntegrity(patchBundle) == false)
                {
                    MotionLog.Error($"Check download content integrity is failed : {patchBundle.BundleName}");
                    loader.Dispose();
                    _removeList.Add(loader);
                    _checkFailedList.Add(patchBundle);
                    continue;
                }

                // 下载成功
                loader.Dispose();
                _removeList.Add(loader);
                _succeedList.Add(patchBundle);
                CurrentDownloadCount++;
                CurrentDownloadBytes += patchBundle.SizeBytes;
            }

            // 移除已经完成的下载器(无论成功或失败)
            foreach (var loader in _removeList)
            {
                _downloaders.Remove(loader);
            }

            // 如果下载进度发生变化
            if (_lastDownloadBytes != downloadBytes || _lastDownloadCount != CurrentDownloadCount)
            {
                _lastDownloadBytes = downloadBytes;
                _lastDownloadCount = CurrentDownloadCount;
                OnDownloadProgressCallback?.Invoke(TotalDownloadCount, _lastDownloadCount, TotalDownloadBytes, _lastDownloadBytes);
            }

            // 动态创建新的下载器到最大数量限制
            // 注意:如果期间有下载失败的文件,暂停动态创建下载器
            if (_downloadList.Count > 0 && _loadFailedList.Count == 0 && _checkFailedList.Count == 0)
            {
                if (_downloaders.Count < _maxNumberOnLoad)
                {
                    int            index      = _downloadList.Count - 1;
                    WebFileRequest downloader = CreateDownloader(_downloadList[index]);
                    _downloaders.Add(downloader);
                    _downloadList.RemoveAt(index);
                }
            }

            // 下载结算
            if (_downloaders.Count == 0)
            {
                // 更新缓存并保存
                if (_succeedList.Count > 0)
                {
                    _patcherMgr.CacheDownloadPatchFiles(_succeedList);
                }

                if (_loadFailedList.Count > 0)
                {
                    DownloadStates = EDownloaderStates.Failed;
                    OnPatchFileDownloadFailedCallback?.Invoke(_loadFailedList[0].BundleName);
                    OnDownloadOverCallback?.Invoke(false);
                }
                else if (_checkFailedList.Count > 0)
                {
                    DownloadStates = EDownloaderStates.Failed;
                    OnPatchFileCheckFailedCallback?.Invoke(_checkFailedList[0].BundleName);
                    OnDownloadOverCallback?.Invoke(false);
                }
                else
                {
                    // 结算成功
                    DownloadStates = EDownloaderStates.Succeed;
                    OnDownloadOverCallback?.Invoke(true);
                }
            }
        }
 public bool CheckContentIntegrity(PatchBundle element)
 {
     return(CheckContentIntegrity(element.Hash, element.CRC, element.SizeBytes));
 }