diff --git a/src/N_m3u8DL-RE.Common/Util/HTTPUtil.cs b/src/N_m3u8DL-RE.Common/Util/HTTPUtil.cs index fa56e2d..e5cdbe1 100644 --- a/src/N_m3u8DL-RE.Common/Util/HTTPUtil.cs +++ b/src/N_m3u8DL-RE.Common/Util/HTTPUtil.cs @@ -84,6 +84,10 @@ namespace N_m3u8DL_RE.Common.Util public static async Task GetBytesAsync(string url, Dictionary? headers = null) { + if (url.StartsWith("file:")) + { + return await File.ReadAllBytesAsync(new Uri(url).LocalPath); + } byte[] bytes = new byte[0]; var webResponse = await DoGetAsync(url, headers); bytes = await webResponse.Content.ReadAsByteArrayAsync(); diff --git a/src/N_m3u8DL-RE.Parser/Processor/HLS/DefaultHLSKeyProcessor.cs b/src/N_m3u8DL-RE.Parser/Processor/HLS/DefaultHLSKeyProcessor.cs index d1c7db7..ad6e113 100644 --- a/src/N_m3u8DL-RE.Parser/Processor/HLS/DefaultHLSKeyProcessor.cs +++ b/src/N_m3u8DL-RE.Parser/Processor/HLS/DefaultHLSKeyProcessor.cs @@ -73,10 +73,10 @@ namespace N_m3u8DL_RE.Parser.Processor.HLS else if (!string.IsNullOrEmpty(uri)) { var retryCount = parserConfig.KeyRetryCount; + var segUrl = PreProcessUrl(ParserUtil.CombineURL(m3u8Url, uri), parserConfig); getHttpKey: try { - var segUrl = PreProcessUrl(ParserUtil.CombineURL(m3u8Url, uri), parserConfig); var bytes = HTTPUtil.GetBytesAsync(segUrl, parserConfig.Headers).Result; encryptInfo.Key = bytes; } diff --git a/src/N_m3u8DL-RE/CommandLine/CommandInvoker.cs b/src/N_m3u8DL-RE/CommandLine/CommandInvoker.cs index b9248c1..a8e9300 100644 --- a/src/N_m3u8DL-RE/CommandLine/CommandInvoker.cs +++ b/src/N_m3u8DL-RE/CommandLine/CommandInvoker.cs @@ -431,7 +431,7 @@ namespace N_m3u8DL_RE.CommandLine Environment.Exit(0); } - var rootCommand = new RootCommand("N_m3u8DL-RE (Beta version) 20220925") + var rootCommand = new RootCommand("N_m3u8DL-RE (Beta version) 20220927") { Input, TmpDir, SaveDir, SaveName, BaseUrl, ThreadCount, DownloadRetryCount, AutoSelect, SkipMerge, SkipDownload, CheckSegmentsCount, BinaryMerge, DelAfterDone, WriteMetaJson, AppendUrlParams, ConcurrentDownload, Headers, /**SavePattern,**/ SubOnly, SubtitleFormat, AutoSubtitleFix, diff --git a/src/N_m3u8DL-RE/Util/DownloadUtil.cs b/src/N_m3u8DL-RE/Util/DownloadUtil.cs index a46a6d3..012ca22 100644 --- a/src/N_m3u8DL-RE/Util/DownloadUtil.cs +++ b/src/N_m3u8DL-RE/Util/DownloadUtil.cs @@ -2,14 +2,8 @@ using N_m3u8DL_RE.Common.Resource; using N_m3u8DL_RE.Common.Util; using N_m3u8DL_RE.Entity; -using System; -using System.Collections.Generic; -using System.Linq; using System.Net; -using System.Net.Http; using System.Net.Http.Headers; -using System.Text; -using System.Threading.Tasks; namespace N_m3u8DL_RE.Util { @@ -17,9 +11,39 @@ namespace N_m3u8DL_RE.Util { private static readonly HttpClient AppHttpClient = HTTPUtil.AppHttpClient; + private static async Task CopyFileAsync(string sourceFile, string path, SpeedContainer speedContainer, long? fromPosition = null, long? toPosition = null) + { + using var inputStream = new FileStream(sourceFile, FileMode.Open, FileAccess.Read, FileShare.Read); + using var outputStream = new FileStream(path, FileMode.OpenOrCreate); + inputStream.Seek(fromPosition ?? 0L, SeekOrigin.Begin); + var expect = (toPosition ?? inputStream.Length) - inputStream.Position + 1; + if (expect == inputStream.Length + 1) + { + await inputStream.CopyToAsync(outputStream); + speedContainer.Add(inputStream.Length); + } + else + { + var buffer = new byte[expect]; + await inputStream.ReadAsync(buffer); + await outputStream.WriteAsync(buffer, 0, buffer.Length); + speedContainer.Add(buffer.Length); + } + return new DownloadResult() + { + ActualContentLength = outputStream.Length, + ActualFilePath = path + }; + } + public static async Task DownloadToFileAsync(string url, string path, SpeedContainer speedContainer, Dictionary? headers = null, long? fromPosition = null, long? toPosition = null) { Logger.Debug(ResString.fetch + url); + if (url.StartsWith("file:")) + { + var file = new Uri(url).LocalPath; + return await CopyFileAsync(file, path, speedContainer, fromPosition, toPosition); + } using var request = new HttpRequestMessage(HttpMethod.Get, new Uri(url)); if (fromPosition != null || toPosition != null) request.Headers.Range = new(fromPosition, toPosition);