mirror of
https://github.com/Stone-Red-Code/HyperbolicDownloader.git
synced 2026-09-04 09:06:10 +02:00
Improve code structure
- Add separate API project - Add notification system
This commit is contained in:
@@ -0,0 +1,33 @@
|
||||
using System.IO.Compression;
|
||||
|
||||
namespace HyperbolicDownloaderApi.FileProcessing;
|
||||
|
||||
internal static class FileCompressor
|
||||
{
|
||||
public static void CompressFile(string inputFilePath, string compressedFilePath)
|
||||
{
|
||||
using FileStream originalFileStream = File.Open(inputFilePath, FileMode.Open);
|
||||
using FileStream compressedFileStream = File.Create(compressedFilePath);
|
||||
using GZipStream? compressor = new GZipStream(compressedFileStream, CompressionMode.Compress);
|
||||
originalFileStream.CopyTo(compressor);
|
||||
}
|
||||
|
||||
public static void DecompressFile(string compressedFilePath, string outputFilePath)
|
||||
{
|
||||
using FileStream compressedFileStream = File.Open(compressedFilePath, FileMode.Open);
|
||||
using FileStream outputFileStream = File.Create(outputFilePath);
|
||||
using GZipStream? decompressor = new GZipStream(compressedFileStream, CompressionMode.Decompress);
|
||||
decompressor.CopyTo(outputFileStream);
|
||||
}
|
||||
|
||||
public static IEnumerable<byte[]> ReadChunks(string path, int chunkSize)
|
||||
{
|
||||
byte[] buffer = new byte[chunkSize];
|
||||
using FileStream fs = File.Open(path, FileMode.Open, FileAccess.Read, FileShare.Read);
|
||||
using BufferedStream bs = new BufferedStream(fs);
|
||||
while (bs.Read(buffer, 0, chunkSize) != 0)
|
||||
{
|
||||
yield return buffer;
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,29 @@
|
||||
using System.Security.Cryptography;
|
||||
|
||||
namespace HyperbolicDownloaderApi.FileProcessing;
|
||||
|
||||
internal static class FileValidator
|
||||
{
|
||||
public static async Task<string> CalculateHashAsync(string filePath)
|
||||
{
|
||||
using SHA512 sha = SHA512.Create();
|
||||
using FileStream? stream = File.OpenRead(filePath);
|
||||
byte[]? hash = await sha.ComputeHashAsync(stream);
|
||||
return BitConverter.ToString(hash).Replace("-", "").ToLowerInvariant();
|
||||
}
|
||||
|
||||
public static string CalculateHash(string filePath)
|
||||
{
|
||||
return CalculateHashAsync(filePath).GetAwaiter().GetResult();
|
||||
}
|
||||
|
||||
public static async Task<bool> ValidateHashAsync(string filePath, string hash)
|
||||
{
|
||||
return await CalculateHashAsync(filePath) == hash;
|
||||
}
|
||||
|
||||
public static bool ValidateHash(string filePath, string hash)
|
||||
{
|
||||
return CalculateHash(filePath) == hash;
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,98 @@
|
||||
using HyperbolicDownloaderApi.Managment;
|
||||
|
||||
using System.Text.Json;
|
||||
|
||||
namespace HyperbolicDownloaderApi.FileProcessing;
|
||||
|
||||
public class FilesManager
|
||||
{
|
||||
private readonly List<PrivateHyperFileInfo> files = new List<PrivateHyperFileInfo>();
|
||||
|
||||
public bool TryAdd(string filePath, out PrivateHyperFileInfo? fileInfo, out string? errorMessage)
|
||||
{
|
||||
if (string.IsNullOrWhiteSpace(filePath))
|
||||
{
|
||||
fileInfo = null;
|
||||
errorMessage = "Path is empty!";
|
||||
return false;
|
||||
}
|
||||
|
||||
string fullPath = Path.GetFullPath(filePath);
|
||||
|
||||
if (!File.Exists(fullPath))
|
||||
{
|
||||
fileInfo = null;
|
||||
errorMessage = "Invalid file path!";
|
||||
return false;
|
||||
}
|
||||
|
||||
string hash = FileValidator.CalculateHash(filePath);
|
||||
|
||||
if (Contains(hash))
|
||||
{
|
||||
fileInfo = null;
|
||||
errorMessage = "File already tracked!";
|
||||
return false;
|
||||
}
|
||||
|
||||
fileInfo = new PrivateHyperFileInfo(hash, fullPath);
|
||||
|
||||
files.Add(fileInfo);
|
||||
|
||||
SaveFiles();
|
||||
|
||||
errorMessage = null;
|
||||
return true;
|
||||
}
|
||||
|
||||
public void AddRange(IEnumerable<PrivateHyperFileInfo> fileInfos)
|
||||
{
|
||||
foreach (PrivateHyperFileInfo fileInfo in fileInfos)
|
||||
{
|
||||
if (File.Exists(fileInfo.FilePath) && !Contains(fileInfo.Hash))
|
||||
{
|
||||
files.Add(fileInfo);
|
||||
}
|
||||
}
|
||||
|
||||
SaveFiles();
|
||||
}
|
||||
|
||||
public bool TryGet(string hash, out PrivateHyperFileInfo? fileInfo)
|
||||
{
|
||||
if (Contains(hash))
|
||||
{
|
||||
fileInfo = files.First(x => x.Hash == hash);
|
||||
return true;
|
||||
}
|
||||
else
|
||||
{
|
||||
fileInfo = null;
|
||||
return false;
|
||||
}
|
||||
}
|
||||
|
||||
public bool TryRemove(string hash)
|
||||
{
|
||||
int count = files.RemoveAll(f => f.Hash == hash);
|
||||
|
||||
SaveFiles();
|
||||
|
||||
return count > 0;
|
||||
}
|
||||
|
||||
public bool Contains(string? hash)
|
||||
{
|
||||
return files.Any(f => f.Hash == hash);
|
||||
}
|
||||
|
||||
public List<PrivateHyperFileInfo> ToList()
|
||||
{
|
||||
return files.ToList();
|
||||
}
|
||||
|
||||
private void SaveFiles()
|
||||
{
|
||||
File.WriteAllText(ApiConfiguration.FilesInfoPath, JsonSerializer.Serialize(files));
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,13 @@
|
||||
namespace HyperbolicDownloaderApi.FileProcessing;
|
||||
|
||||
public class PrivateHyperFileInfo
|
||||
{
|
||||
public string Hash { get; set; }
|
||||
public string FilePath { get; set; }
|
||||
|
||||
public PrivateHyperFileInfo(string hash, string filePath)
|
||||
{
|
||||
Hash = hash;
|
||||
FilePath = filePath;
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,24 @@
|
||||
using HyperbolicDownloaderApi.Networking;
|
||||
|
||||
namespace HyperbolicDownloaderApi.FileProcessing;
|
||||
|
||||
public class PublicHyperFileInfo
|
||||
{
|
||||
public string Hash { get; set; } = string.Empty;
|
||||
public List<NetworkSocket> Hosts { get; set; } = new();
|
||||
|
||||
public PublicHyperFileInfo()
|
||||
{
|
||||
}
|
||||
|
||||
public PublicHyperFileInfo(string hash)
|
||||
{
|
||||
Hash = hash;
|
||||
}
|
||||
|
||||
public PublicHyperFileInfo(string hash, List<NetworkSocket> hosts)
|
||||
{
|
||||
Hash = hash;
|
||||
Hosts = hosts;
|
||||
}
|
||||
}
|
||||
Reference in New Issue
Block a user