Skip to content

Commit 4e315e7

Browse files
Merge pull request #55 from TheGuitarleader/feature/gui
Checksum generation is now during pushes to improve performance
2 parents 5479817 + 468d7aa commit 4e315e7

6 files changed

Lines changed: 36 additions & 42 deletions

File tree

Parallel.Core/Diagnostics/IProgressReporter.cs

Lines changed: 2 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -11,7 +11,8 @@ public enum ProgressOperation
1111
Pushed,
1212
Synced,
1313
Downloading,
14-
Uploading
14+
Uploading,
15+
Hashing
1516
}
1617

1718
/// <summary>

Parallel.Core/IO/Scanning/FileScanner.cs

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -9,6 +9,7 @@
99
using Parallel.Core.Database;
1010
using Parallel.Core.IO.Syncing;
1111
using Parallel.Core.Models;
12+
using Parallel.Core.Security;
1213
using Parallel.Core.Settings;
1314
using Parallel.Core.Utils;
1415
using FileInfo = System.IO.FileInfo;
@@ -98,6 +99,7 @@ public async Task<SystemFile[]> GetFileChangesAsync(string path, string[] ignore
9899
/// <returns>True is success, otherwise false.</returns>
99100
public static bool HasChanged(SystemFile sourcePath, SystemFile? targetPath)
100101
{
102+
if (string.IsNullOrEmpty(sourcePath.CheckSum)) sourcePath.TryGenerateCheckSum();
101103
return targetPath == null || (sourcePath.LastWrite.TotalMilliseconds > targetPath.LastWrite.TotalMilliseconds && Convert.ToBoolean(!sourcePath.CheckSum?.Equals(targetPath.CheckSum)));
102104
}
103105

Parallel.Core/IO/Syncing/FileSyncManager.cs

Lines changed: 8 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -5,6 +5,7 @@
55
using Parallel.Core.Database;
66
using Parallel.Core.Diagnostics;
77
using Parallel.Core.Models;
8+
using Parallel.Core.Security;
89
using Parallel.Core.Settings;
910
using Parallel.Core.Utils;
1011

@@ -36,13 +37,14 @@ public override async Task<int> PushFilesAsync(SystemFile[] files, IProgressRepo
3637
Task worker = System.Threading.Tasks.Parallel.ForEachAsync(uploadFiles, ParallelConfig.Options, async (file, ct) =>
3738
{
3839
Interlocked.Increment(ref queued);
39-
SemaphoreSlim lockedThread = threadPool.GetOrAdd(file.CheckSum, _ => new SemaphoreSlim(1, 1));
40+
if (string.IsNullOrEmpty(file.CheckSum) && !file.TryGenerateCheckSum()) return;
41+
SemaphoreSlim lockedThread = threadPool.GetOrAdd(file.CheckSum!, _ => new SemaphoreSlim(1, 1));
4042
await lockedThread.WaitAsync(ct);
4143

4244
try
4345
{
4446
Log.Debug($"Pushing -> {file.LocalPath}");
45-
file.RemotePath = PathBuilder.GetObjectPath(RemoteVault, file.CheckSum);
47+
file.RemotePath = PathBuilder.GetObjectPath(RemoteVault, file.CheckSum!);
4648
long result = await StorageProvider.UploadFileAsync(file, false, ct);
4749
if (result <= 0)
4850
{
@@ -63,7 +65,7 @@ public override async Task<int> PushFilesAsync(SystemFile[] files, IProgressRepo
6365
finally
6466
{
6567
lockedThread.Release();
66-
threadPool.TryRemove(file.CheckSum, out _);
68+
threadPool.TryRemove(file.CheckSum!, out _);
6769
Interlocked.Increment(ref completed);
6870
Interlocked.Decrement(ref queued);
6971
}
@@ -101,7 +103,8 @@ public override async Task<int> PullFilesAsync(SystemFile[] files, IProgressRepo
101103
Task worker = System.Threading.Tasks.Parallel.ForEachAsync(files, ParallelConfig.Options, async (file, ct) =>
102104
{
103105
Interlocked.Increment(ref queued);
104-
SemaphoreSlim lockedThread = threadPool.GetOrAdd(file.CheckSum, _ => new SemaphoreSlim(1, 1));
106+
if (string.IsNullOrEmpty(file.CheckSum) && !file.TryGenerateCheckSum()) return;
107+
SemaphoreSlim lockedThread = threadPool.GetOrAdd(file.CheckSum!, _ => new SemaphoreSlim(1, 1));
105108
await lockedThread.WaitAsync(ct);
106109

107110
try
@@ -131,7 +134,7 @@ public override async Task<int> PullFilesAsync(SystemFile[] files, IProgressRepo
131134
finally
132135
{
133136
lockedThread.Release();
134-
threadPool.TryRemove(file.CheckSum, out _);
137+
threadPool.TryRemove(file.CheckSum!, out _);
135138
Interlocked.Increment(ref completed);
136139
Interlocked.Decrement(ref queued);
137140
}

Parallel.Core/Models/Manifest.cs

Lines changed: 0 additions & 21 deletions
This file was deleted.

Parallel.Core/Models/SystemFile.cs

Lines changed: 24 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -1,6 +1,7 @@
11
// Copyright 2025 Kyle Ebbinga
22

33
using System.Data;
4+
using System.Security.Cryptography;
45
using Parallel.Core.Data;
56
using Parallel.Core.Diagnostics;
67
using Parallel.Core.Security;
@@ -71,7 +72,7 @@ public class SystemFile
7172
/// <summary>
7273
/// The checksum used to check if the file has changed.
7374
/// </summary>
74-
public string CheckSum { get; } = string.Empty;
75+
public string? CheckSum { get; set; } = string.Empty;
7576

7677

7778
/// <summary>
@@ -89,7 +90,6 @@ public SystemFile(string path)
8990
Type = FileTypes.GetFileCategory(Path.GetExtension(fileInfo.Name));
9091
Hidden = fileInfo.Attributes.HasFlag(FileAttributes.Hidden);
9192
ReadOnly = fileInfo.Attributes.HasFlag(FileAttributes.ReadOnly);
92-
CheckSum = HashGenerator.CheckSum(path) ?? string.Empty;
9393
Deleted = !fileInfo.Exists;
9494
}
9595

@@ -166,5 +166,27 @@ public bool Equals(SystemFile value)
166166

167167
return results.All(b => b != null && (bool)b);
168168
}
169+
170+
public bool TryGenerateCheckSum()
171+
{
172+
// Ignore if already valid.
173+
if (!string.IsNullOrEmpty(CheckSum)) return true;
174+
175+
try
176+
{
177+
Log.Debug($"Generating checksum -> {LocalPath}");
178+
if (!File.Exists(LocalPath)) return false;
179+
180+
using SHA256 sha256 = SHA256.Create();
181+
using FileStream fs = File.OpenRead(LocalPath);
182+
CheckSum = Convert.ToHexStringLower(sha256.ComputeHash(fs));
183+
return !string.IsNullOrEmpty(CheckSum);
184+
}
185+
catch (Exception ex)
186+
{
187+
Log.Error(ex, $"Checksum generation failed -> {LocalPath}");
188+
return false;
189+
}
190+
}
169191
}
170192
}

Parallel.Core/Security/HashGenerator.cs

Lines changed: 0 additions & 13 deletions
Original file line numberDiff line numberDiff line change
@@ -96,18 +96,5 @@ public static string CreateSHA256(string value)
9696
ArgumentException.ThrowIfNullOrEmpty(value);
9797
return Convert.ToHexString(SHA256.HashData(Encoding.UTF8.GetBytes(value))).ToLower();
9898
}
99-
100-
/// <summary>
101-
///
102-
/// </summary>
103-
/// <param name="path"></param>
104-
/// <returns></returns>
105-
public static string? CheckSum(string path)
106-
{
107-
if (!File.Exists(path)) return null;
108-
using FileStream fs = File.OpenRead(path);
109-
using SHA256 sha256 = SHA256.Create();
110-
return Convert.ToHexStringLower(sha256.ComputeHash(fs));
111-
}
11299
}
113100
}

0 commit comments

Comments
 (0)