public override List <AssetOp> GetInstallOps(ModContext context) { if (InstallAction == null) { throw new InvalidOperationException("Tried to install AssetsModComponent, but install action is null."); } if (InstallAction.Actions == null || InstallAction.Actions.Count < 1) { throw new InvalidOperationException("Install action has no asset actions defined!"); } using (new LogTiming("preloading asset files for assets mod")) { if (InstallAction.PreloadFiles != null) { InstallAction.PreloadFiles.ForEach(x => context.GetEngine().Manager.GetAssetsFile(x)); } } List <AssetOp> ops = new List <AssetOp>(); foreach (var action in InstallAction.Actions.OrderBy(x => x.StepNumber)) { using (new LogTiming($"getting operations for asset mod action step {action.StepNumber}")) { ops.AddRange(action.GetOps(context)); } } Log.LogMsg($"Returning {ops.Count} for assets mod component installation..."); return(ops); }
public override IEnumerable <AssetOp> GetOps(ModContext context) { if (Locator == null) { throw new Exception("Locator is null for RestoreAssetsAction!"); } if (context.BackupEngine == null) { throw new Exception("BackupEngine is not set in the context!"); } byte[] assetData = null; try { var bqae = context.BackupEngine; var fromAsset = Locator.Locate(bqae.Manager); if (fromAsset == null) { throw new Exception($"Unable to locate asset in backup apk for mod uninstallation on step {StepNumber}!"); } using (var ms = new MemoryStream()) { using (var writer = new AssetsWriter(ms)) { fromAsset.Write(writer); } ms.Seek(0, SeekOrigin.Begin); assetData = ms.ToArray(); } } catch (Exception ex) { Log.LogErr("Exception while restoring asset!", ex); throw; } AssetLocator locatorOverride = null; try { var res = Locator.Locate(context.GetEngine().Manager, false); if (res == null) { throw new LocatorException("Unable to find asset."); } } catch (LocatorException ex) { Log.LogErr($"The locator for restore threw an exception, attempting to locate against backup and identify path.", ex); try { var res = Locator.Locate(context.BackupEngine.Manager, false); if (res == null) { throw new LocatorException("Unable to find asset, locator returned null"); } locatorOverride = new AssetLocator() { PathIs = new PathLocator() { AssetFilename = res.ObjectInfo.ParentFile.AssetsFilename, PathID = res.ObjectInfo.ObjectID } }; } catch (Exception ex2) { Log.LogErr($"Unable to find path in backup for the locator either", ex2); throw ex; } } yield return(new ReplaceAssetOp(locatorOverride ?? Locator, assetData, true)); }
public override List <AssetOp> GetUninstallOps(ModContext context) { if (UninstallAction == null) { throw new InvalidOperationException("Tried to install AssetsModComponent, but uninstall action is null."); } if (UninstallAction.Actions == null || UninstallAction.Actions.Count < 1) { throw new InvalidOperationException("Uninstall action has no asset actions defined!"); } if (string.IsNullOrEmpty(context.Config.BackupApkFileAbsolutePath)) { throw new InvalidOperationException("Uninstall assets mod can't happen when the backup APK isn't set!"); } string backup = null; if (!File.Exists(context.Config.BackupApkFileAbsolutePath)) { Log.LogErr($"WARNING: primary APK backup doesn't exist at {context.Config.BackupApkFileAbsolutePath}, will attempt to fall back..."); if (!File.Exists(context.Config.ModdedFallbackBackupPath)) { throw new Exception($"Backup APK file does not exist at {context.Config.BackupApkFileAbsolutePath} and even the fallback doesn't exist at {context.Config.ModdedFallbackBackupPath}"); } else { backup = context.Config.ModdedFallbackBackupPath; } } else { backup = context.Config.BackupApkFileAbsolutePath; } using (new LogTiming("preloading asset files for uninstall assets mod")) { if (UninstallAction.PreloadFiles != null) { UninstallAction.PreloadFiles.ForEach(x => context.GetEngine().Manager.GetAssetsFile(x)); } } Log.LogMsg($"Opening backup APK..."); List <AssetOp> ops = new List <AssetOp>(); using (var apk = new ZipFileProvider(backup, FileCacheMode.Memory, true, FileUtils.GetTempDirectory())) { var backupCfg = new QaeConfig() { AssetsPath = BeatSaber.BSConst.KnownFiles.AssetsRootPath, SongsPath = "", ModsSourcePath = "", PlaylistArtPath = "", RootFileProvider = apk }; using (var backupQae = new QuestomAssetsEngine(backupCfg)) { using (new LogTiming("preloading asset files for uninstall assets mod on BACKUP apk/qae")) { if (UninstallAction.PreloadFiles != null) { UninstallAction.PreloadFiles.ForEach(x => backupQae.Manager.GetAssetsFile(x)); } } using (new LogTiming("preloading asset files that are loaded in the main engine")) { context.GetEngine().Manager.OpenFiles.ForEach(x => backupQae.Manager.GetAssetsFile(x.AssetsFilename)); } context.BackupEngine = backupQae; foreach (var action in UninstallAction.Actions.OrderBy(x => x.StepNumber)) { using (new LogTiming($"getting operations for asset mod uninstall action step {action.StepNumber}")) { ops.AddRange(action.GetOps(context)); } } } context.BackupEngine = null; } Log.LogMsg($"Returning {ops.Count} for assets mod component uninstall..."); return(ops); }