public override async Task <StatusHandler> ProcessAsync(LibraryBook libraryBook) { OnBegin(libraryBook); OnStreamingBegin($"Begin converting {libraryBook} to mp3"); try { var m4bPath = AudibleFileStorage.Audio.GetPath(libraryBook.Book.AudibleProductId); m4bBook = new Mp4File(m4bPath, FileAccess.Read); m4bBook.ConversionProgressUpdate += M4bBook_ConversionProgressUpdate; fileSize = m4bBook.InputStream.Length; OnTitleDiscovered(m4bBook.AppleTags.Title); OnAuthorsDiscovered(m4bBook.AppleTags.FirstAuthor); OnNarratorsDiscovered(m4bBook.AppleTags.Narrator); OnCoverImageDiscovered(m4bBook.AppleTags.Cover); using var mp3File = File.OpenWrite(Path.GetTempFileName()); var result = await Task.Run(() => m4bBook.ConvertToMp3(mp3File)); m4bBook.InputStream.Close(); mp3File.Close(); var proposedMp3Path = Mp3FileName(m4bPath); var realMp3Path = FileUtility.SaferMoveToValidPath(mp3File.Name, proposedMp3Path); OnFileCreated(libraryBook, realMp3Path); var statusHandler = new StatusHandler(); if (result == ConversionResult.Failed) { statusHandler.AddError("Conversion failed"); } return(statusHandler); } finally { OnStreamingCompleted($"Completed converting to mp3: {libraryBook.Book.Title}"); OnCompleted(libraryBook); } }
// do NOT use ConfigureAwait(false) on ProcessAsync() // often calls events which prints to forms in the UI context public async Task <StatusHandler> ProcessAsync(LibraryBook libraryBook) { Begin?.Invoke(this, libraryBook); try { var aaxFilename = AudibleFileStorage.AAX.GetPath(libraryBook.Book.AudibleProductId); if (aaxFilename == null) { return new StatusHandler { "aaxFilename parameter is null" } } ; if (!File.Exists(aaxFilename)) { return new StatusHandler { $"Cannot find AAX file: {aaxFilename}" } } ; if (AudibleFileStorage.Audio.Exists(libraryBook.Book.AudibleProductId)) { return new StatusHandler { "Cannot find decrypt. Final audio file already exists" } } ; var outputAudioFilename = await aaxToM4bConverterDecrypt(aaxFilename, libraryBook); // decrypt failed if (outputAudioFilename == null) { return new StatusHandler { "Decrypt failed" } } ; var destinationDir = moveFilesToBooksDir(libraryBook.Book, outputAudioFilename); var config = Configuration.Instance; if (config.RetainAaxFiles) { var newAaxFilename = FileUtility.GetValidFilename( destinationDir, Path.GetFileNameWithoutExtension(aaxFilename), "aax"); File.Move(aaxFilename, newAaxFilename); } else { Dinah.Core.IO.FileExt.SafeDelete(aaxFilename); } var statusHandler = new StatusHandler(); var finalAudioExists = AudibleFileStorage.Audio.Exists(libraryBook.Book.AudibleProductId); if (!finalAudioExists) { statusHandler.AddError("Cannot find final audio file after decryption"); } return(statusHandler); } finally { Completed?.Invoke(this, libraryBook); } }