Keyword to work with Amazon
This commit is contained in:
@ -85,10 +85,12 @@ csharp_using_directive_placement = outside_namespace
|
||||
dotnet_code_quality_unused_parameters = all
|
||||
dotnet_code_quality_unused_parameters = non_public # IDE0060: Remove unused parameter
|
||||
dotnet_code_quality.CAXXXX.api_surface = private, internal
|
||||
dotnet_diagnostic.CA1511.severity = warning # CA1511: Use 'ArgumentException.ThrowIfNullOrEmpty' instead of explicitly throwing a new exception instance
|
||||
dotnet_diagnostic.CA1825.severity = warning # CA1823: Avoid zero-length array allocations
|
||||
dotnet_diagnostic.CA1829.severity = warning # CA1829: Use Length/Count property instead of Count() when available
|
||||
dotnet_diagnostic.CA1834.severity = warning # CA1834: Consider using 'StringBuilder.Append(char)' when applicable
|
||||
dotnet_diagnostic.CA1860.severity = warning # CA1860: Prefer comparing 'Count' to 0 rather than using 'Any()', both for clarity and for performance
|
||||
dotnet_diagnostic.CA1862.severity = warning # CA1862: Prefer using 'string.Equals(string, StringComparison)' to perform a case-insensitive comparison, but keep in mind that this might cause subtle changes in behavior, so make sure to conduct thorough testing after applying the suggestion, or if culturally sensitive comparison is not required, consider using 'StringComparison.OrdinalIgnoreCase'
|
||||
dotnet_diagnostic.CA1869.severity = none # CA1869: Avoid creating a new 'JsonSerializerOptions' instance for every serialization operation. Cache and reuse instances instead.
|
||||
dotnet_diagnostic.CA2254.severity = none # CA2254: The logging message template should not vary between calls to 'LoggerExtensions.LogInformation(ILogger, string?, params object?[])'
|
||||
dotnet_diagnostic.IDE0001.severity = warning # IDE0001: Simplify name
|
||||
@ -99,7 +101,9 @@ dotnet_diagnostic.IDE0028.severity = warning # IDE0028: Collection initializatio
|
||||
dotnet_diagnostic.IDE0031.severity = warning # Use null propagation (IDE0031)
|
||||
dotnet_diagnostic.IDE0047.severity = warning # IDE0047: Parentheses can be removed
|
||||
dotnet_diagnostic.IDE0049.severity = warning # Use language keywords instead of framework type names for type references (IDE0049)
|
||||
dotnet_diagnostic.IDE0058.severity = warning # IDE0058: Expression value is never used
|
||||
dotnet_diagnostic.IDE0060.severity = warning # IDE0060: Remove unused parameter
|
||||
dotnet_diagnostic.IDE0074.severity = warning # IDE0074: Use compound assignment
|
||||
dotnet_diagnostic.IDE0200.severity = warning # IDE0200: Lambda expression can be removed [Map]
|
||||
dotnet_diagnostic.IDE0290.severity = none # Use primary constructor [Distance]csharp(IDE0290)
|
||||
dotnet_diagnostic.IDE0300.severity = warning # IDE0300: Collection initialization can be simplified
|
||||
|
@ -193,15 +193,11 @@ public class DateGroup
|
||||
if (item.Property is not null)
|
||||
dateTimes = item.Property.GetDateTimes();
|
||||
else
|
||||
{
|
||||
if (item.ImageFileHolder.LastWriteTime is null)
|
||||
throw new Exception();
|
||||
dateTimes = [item.ImageFileHolder.LastWriteTime.Value];
|
||||
}
|
||||
dateTimes = [new(item.FilePath.LastWriteTicks)];
|
||||
if (item.Property is not null && item.Property.DateTimeOriginal is not null)
|
||||
dateTime = item.Property.DateTimeOriginal.Value;
|
||||
else if (item.ImageFileHolder.LastWriteTime is not null && item.Property is null)
|
||||
dateTime = item.ImageFileHolder.LastWriteTime.Value;
|
||||
else if (item.Property is null)
|
||||
dateTime = new(item.FilePath.LastWriteTicks);
|
||||
else
|
||||
dateTime = Shared.Models.Stateless.Methods.IProperty.GetMinimumDateTime(item.Property);
|
||||
day = dateTime.ToString("MM-dd");
|
||||
@ -213,7 +209,7 @@ public class DateGroup
|
||||
}
|
||||
else
|
||||
{
|
||||
(isWrongYear, _) = Shared.Models.Stateless.Methods.IProperty.IsWrongYear(item.ImageFileHolder, item.Property.DateTimeOriginal, dateTimes);
|
||||
(isWrongYear, _) = Shared.Models.Stateless.Methods.IProperty.IsWrongYear(item.FilePath, item.Property.DateTimeOriginal, dateTimes);
|
||||
if (isWrongYear is null)
|
||||
flag = '#';
|
||||
else if (isWrongYear.Value)
|
||||
@ -283,18 +279,16 @@ public class DateGroup
|
||||
}
|
||||
}
|
||||
if (!_Configuration.ByHash || item.Property?.Id is null)
|
||||
fileName = item.ImageFileHolder.Name;
|
||||
fileName = item.FilePath.Name;
|
||||
else
|
||||
fileName = $"{item.Property.Id.Value}{item.ImageFileHolder.ExtensionLowered}";
|
||||
fileName = $"{item.Property.Id.Value}{item.FilePath.ExtensionLowered}";
|
||||
destinationCollection.Add(destinationDirectory);
|
||||
destinationCollection.AddRange(directoryNames);
|
||||
destinationCollection.Add(fileName);
|
||||
if (item.ImageFileHolder.LastWriteTime is null)
|
||||
continue;
|
||||
if (item.Property is not null)
|
||||
results.Add(new(item, item.Property.LastWriteTime.Ticks, dateTime.Ticks, destinationCollection.ToArray()));
|
||||
if (item.Property is null)
|
||||
results.Add(new(item, item.FilePath.LastWriteTicks, dateTime.Ticks, destinationCollection.ToArray()));
|
||||
else
|
||||
results.Add(new(item, item.ImageFileHolder.LastWriteTime.Value.Ticks, dateTime.Ticks, destinationCollection.ToArray()));
|
||||
results.Add(new(item, item.Property.LastWriteTime.Ticks, dateTime.Ticks, destinationCollection.ToArray()));
|
||||
}
|
||||
return results;
|
||||
}
|
||||
@ -313,7 +307,7 @@ public class DateGroup
|
||||
List<Item> results = [];
|
||||
foreach (Item item in container.Items)
|
||||
{
|
||||
if (item.ImageFileHolder is not null)
|
||||
if (item.FilePath is not null)
|
||||
results.Add(item);
|
||||
}
|
||||
return results.ToArray();
|
||||
@ -422,13 +416,13 @@ public class DateGroup
|
||||
continue;
|
||||
}
|
||||
}
|
||||
File.Move(item.ImageFileHolder.FullName, fullFileName);
|
||||
File.Move(item.FilePath.FullName, fullFileName);
|
||||
moved += 1;
|
||||
if (hasDuplicate)
|
||||
{
|
||||
try
|
||||
{
|
||||
windowsShortcut = new() { Path = item.ImageFileHolder.DirectoryName, Description = item.ImageFileHolder.Name };
|
||||
windowsShortcut = new() { Path = item.FilePath.DirectoryName, Description = item.FilePath.Name };
|
||||
windowsShortcut.Save(string.Concat(fullFileName, ".lnk"));
|
||||
windowsShortcut.Dispose();
|
||||
}
|
||||
@ -447,11 +441,11 @@ public class DateGroup
|
||||
foreach ((Item item, long lastWriteTimeTicks, long minimumDateTimeTicks, string[] destination) in fileMoveCollectionAll)
|
||||
{
|
||||
fullFileName = Path.Combine(destination);
|
||||
if (File.Exists(item.ImageFileHolder.FullName))
|
||||
if (File.Exists(item.FilePath.FullName))
|
||||
continue;
|
||||
if (!File.Exists(fullFileName))
|
||||
continue;
|
||||
File.Move(fullFileName, item.ImageFileHolder.FullName);
|
||||
File.Move(fullFileName, item.FilePath.FullName);
|
||||
moved += 1;
|
||||
}
|
||||
_Logger?.LogInformation($"Done moving back {moved} file(s)");
|
||||
@ -493,8 +487,8 @@ public class DateGroup
|
||||
relativePathDirectory = Path.GetDirectoryName(item.RelativePath);
|
||||
if (string.IsNullOrEmpty(relativePathDirectory))
|
||||
continue;
|
||||
if (item.ImageFileHolder.LastWriteTime is not null && item.Property is null)
|
||||
dateTime = item.ImageFileHolder.LastWriteTime.Value;
|
||||
if (item.Property is null)
|
||||
dateTime = new(item.FilePath.LastWriteTicks);
|
||||
else if (item.Property is not null && item.Property.DateTimeOriginal is not null)
|
||||
dateTime = item.Property.DateTimeOriginal.Value;
|
||||
else
|
||||
|
@ -166,7 +166,7 @@ public partial class E_Distance : IDistance
|
||||
if (mappedFaceDirectory is null)
|
||||
throw new NotSupportedException();
|
||||
deterministicHashCodeKey = Shared.Models.Stateless.Methods.IMapping.GetDeterministicHashCodeKey(filePath, face.Location, Shared.Models.Stateless.ILocation.Digits, face.OutputResolution);
|
||||
checkFile = Path.Combine(mappedFaceDirectory, $"{deterministicHashCodeKey}{mappingFromItem.ImageFileHolder.ExtensionLowered}{facesFileNameExtension}");
|
||||
checkFile = Path.Combine(mappedFaceDirectory, $"{deterministicHashCodeKey}{mappingFromItem.FilePath.ExtensionLowered}{facesFileNameExtension}");
|
||||
if (checkFile == file)
|
||||
continue;
|
||||
result = new FileInfo(checkFile);
|
||||
|
@ -160,10 +160,10 @@ public partial class DragDropSearch : Form
|
||||
LoadData();
|
||||
if (int.TryParse(segments[0], out int id) && _IdToItem.TryGetValue(id, out Item? item))
|
||||
{
|
||||
Text = item.ImageFileHolder.Name;
|
||||
_TextBox.Text = item.ImageFileHolder.FullName;
|
||||
if (!string.IsNullOrEmpty(item.ImageFileHolder.DirectoryName))
|
||||
_ = Process.Start("explorer.exe", string.Concat("\"", item.ImageFileHolder.DirectoryName, "\""));
|
||||
Text = item.FilePath.Name;
|
||||
_TextBox.Text = item.FilePath.FullName;
|
||||
if (!string.IsNullOrEmpty(item.FilePath.DirectoryName))
|
||||
_ = Process.Start("explorer.exe", string.Concat("\"", item.FilePath.DirectoryName, "\""));
|
||||
}
|
||||
}
|
||||
}
|
||||
|
@ -19,9 +19,8 @@ public class Program
|
||||
List<Item> results = [];
|
||||
foreach (Item item in container.Items)
|
||||
{
|
||||
if (item.ImageFileHolder is not null
|
||||
&& item.IsValidImageFormatExtension
|
||||
&& !configuration.IgnoreExtensions.Contains(item.ImageFileHolder.ExtensionLowered))
|
||||
if (item.IsValidImageFormatExtension
|
||||
&& !configuration.IgnoreExtensions.Contains(item.FilePath.ExtensionLowered))
|
||||
results.Add(item);
|
||||
}
|
||||
return results.ToArray();
|
||||
|
@ -116,7 +116,7 @@ public partial class DragDropSetPropertyItem : Form
|
||||
fileHolder = IFileHolder.Get(file);
|
||||
isValidImageFormatExtension = _PropertyConfiguration.ValidImageFormatExtensions.Contains(fileHolder.ExtensionLowered);
|
||||
isIgnoreExtension = isValidImageFormatExtension && _PropertyConfiguration.IgnoreExtensions.Contains(fileHolder.ExtensionLowered);
|
||||
(dateTimeOriginal, _, id, message) = Property.Models.Stateless.IProperty.Get(_PropertyConfiguration.PopulatePropertyId, fileHolder, isIgnoreExtension, isValidImageFormatExtension, asciiEncoding);
|
||||
(dateTimeOriginal, _, id, message) = Property.Models.Stateless.IProperty.Get(_PropertyConfiguration, _PropertyConfiguration.PopulatePropertyId, fileHolder, isIgnoreExtension, isValidImageFormatExtension, asciiEncoding);
|
||||
if (message is not null)
|
||||
throw new Exception(message);
|
||||
if (id is null)
|
||||
@ -165,7 +165,7 @@ public partial class DragDropSetPropertyItem : Form
|
||||
bitmap.SetPropertyItem(propertyItem);
|
||||
bitmap.Save(checkFile);
|
||||
bitmap.Dispose();
|
||||
(_, _, id, message) = Property.Models.Stateless.IProperty.Get(_PropertyConfiguration.PopulatePropertyId, record.FileHolder, record.IsIgnoreExtension, record.IsValidImageFormatExtension, asciiEncoding);
|
||||
(_, _, id, message) = Property.Models.Stateless.IProperty.Get(_PropertyConfiguration, _PropertyConfiguration.PopulatePropertyId, record.FileHolder, record.IsIgnoreExtension, record.IsValidImageFormatExtension, asciiEncoding);
|
||||
if (id is null || id.Value != record.Id)
|
||||
throw new NotSupportedException();
|
||||
File.Delete(record.FileHolder.FullName);
|
||||
|
@ -60,10 +60,10 @@ public class DuplicateSearch
|
||||
File.WriteAllText(Path.Combine(alongSideDirectory, $"{directoryName}-{ticks}.json"), json);
|
||||
}
|
||||
|
||||
private static void Move(ILogger<Program>? logger, long ticks, string destinationRoot, List<(FileHolder ImageFileHolder, string Destination)> collection)
|
||||
private static void Move(ILogger<Program>? logger, long ticks, string destinationRoot, List<(FilePath FilePath, string Destination)> collection)
|
||||
{
|
||||
StringBuilder stringBuilder = new();
|
||||
foreach ((FileHolder fileHolder, string destination) in collection)
|
||||
foreach ((FilePath fileHolder, string destination) in collection)
|
||||
{
|
||||
_ = stringBuilder.AppendLine(fileHolder.FullName);
|
||||
_ = stringBuilder.AppendLine(destination);
|
||||
@ -77,12 +77,12 @@ public class DuplicateSearch
|
||||
break;
|
||||
}
|
||||
logger?.LogInformation(". . .");
|
||||
foreach ((FileHolder fileHolder, string destination) in collection)
|
||||
foreach ((FilePath filePath, string destination) in collection)
|
||||
{
|
||||
try
|
||||
{ File.Move(fileHolder.FullName, destination); }
|
||||
{ File.Move(filePath.FullName, destination); }
|
||||
catch (Exception exception)
|
||||
{ logger?.LogError(exception, $"Failed to move <{fileHolder.FullName}>"); }
|
||||
{ logger?.LogError(exception, $"Failed to move <{filePath.FullName}>"); }
|
||||
}
|
||||
logger?.LogInformation($"{collection.Count} file(s) moved");
|
||||
for (int y = 0; y < int.MaxValue; y++)
|
||||
@ -91,14 +91,14 @@ public class DuplicateSearch
|
||||
if (System.Console.ReadKey().Key != ConsoleKey.Y)
|
||||
continue;
|
||||
logger?.LogInformation(". . .");
|
||||
foreach ((FileHolder fileHolder, string destination) in collection)
|
||||
foreach ((FilePath filePath, string destination) in collection)
|
||||
{
|
||||
if (!File.Exists(destination))
|
||||
continue;
|
||||
if (File.Exists(fileHolder.FullName))
|
||||
if (File.Exists(filePath.FullName))
|
||||
continue;
|
||||
try
|
||||
{ File.Move(destination, fileHolder.FullName); }
|
||||
{ File.Move(destination, filePath.FullName); }
|
||||
catch (Exception exception)
|
||||
{ logger?.LogError(exception, $"Failed to move <{destination}>"); }
|
||||
}
|
||||
@ -119,7 +119,7 @@ public class DuplicateSearch
|
||||
if (System.Console.ReadKey().Key != ConsoleKey.Y)
|
||||
continue;
|
||||
logger?.LogInformation(". . .");
|
||||
List<(FileHolder ImageFileHolder, string Destination)> collection = GetCollectionAndCreateDirectories(idToCollection);
|
||||
List<(FilePath FilePath, string Destination)> collection = GetCollectionAndCreateDirectories(idToCollection);
|
||||
Move(logger, ticks, destinationRoot, collection);
|
||||
}
|
||||
}
|
||||
@ -170,7 +170,7 @@ public class DuplicateSearch
|
||||
{
|
||||
if (item.Property?.Id is null)
|
||||
{
|
||||
if (int.TryParse(item.ImageFileHolder.NameWithoutExtension, out int id))
|
||||
if (int.TryParse(item.FilePath.NameWithoutExtension, out int id))
|
||||
continue;
|
||||
continue;
|
||||
}
|
||||
@ -188,7 +188,7 @@ public class DuplicateSearch
|
||||
if (mappingFromItem is not null)
|
||||
{
|
||||
resizedFileHolder = Shared.Models.Stateless.Methods.IFileHolder.Get(mappingFromItem.ResizedFileHolder.FullName.Replace($"0{duplicates}", $"1{duplicates}"));
|
||||
collection[0] = new(mappingFromItem.ContainerDateTimes, item.Property.DateTimeDigitized, item.Property.DateTimeOriginal, mappingFromItem.Id, mappingFromItem.ImageFileHolder, mappingFromItem.IsWrongYear, item.Property.Keywords ?? [], mappingFromItem.MinimumDateTime, item.Property.Model, mappingFromItem.RelativePath, resizedFileHolder);
|
||||
collection[0] = new(mappingFromItem.ContainerDateTimes, item.Property.DateTimeDigitized, item.Property.DateTimeOriginal, mappingFromItem.Id, mappingFromItem.FilePath, mappingFromItem.IsWrongYear, item.Property.Keywords ?? [], mappingFromItem.MinimumDateTime, item.Property.Model, mappingFromItem.RelativePath, resizedFileHolder);
|
||||
}
|
||||
}
|
||||
resizedFileHolder = Shared.Models.Stateless.Methods.IFileHolder.Get(string.Concat(Path.Combine(destinationRoot, directory), item.RelativePath));
|
||||
@ -199,9 +199,9 @@ public class DuplicateSearch
|
||||
return results;
|
||||
}
|
||||
|
||||
private static List<(FileHolder ImageFileHolder, string Destination)> GetCollectionAndCreateDirectories(Dictionary<int, List<MappingFromItem?>> idToCollection)
|
||||
private static List<(FilePath FilePath, string Destination)> GetCollectionAndCreateDirectories(Dictionary<int, List<MappingFromItem?>> idToCollection)
|
||||
{
|
||||
List<(FileHolder ImageFileHolder, string Destination)> results = [];
|
||||
List<(FilePath FilePath, string Destination)> results = [];
|
||||
List<string> collection = [];
|
||||
foreach (KeyValuePair<int, List<MappingFromItem?>> keyValuePair in idToCollection)
|
||||
{
|
||||
@ -209,10 +209,10 @@ public class DuplicateSearch
|
||||
{
|
||||
if (mappingFromItem?.ResizedFileHolder.DirectoryName is null)
|
||||
continue;
|
||||
if (!mappingFromItem.ImageFileHolder.Exists || mappingFromItem.ResizedFileHolder.Exists)
|
||||
if (mappingFromItem.ResizedFileHolder.Exists)
|
||||
continue;
|
||||
collection.Add(mappingFromItem.ResizedFileHolder.DirectoryName);
|
||||
results.Add(new(mappingFromItem.ImageFileHolder, mappingFromItem.ResizedFileHolder.FullName));
|
||||
results.Add(new(mappingFromItem.FilePath, mappingFromItem.ResizedFileHolder.FullName));
|
||||
}
|
||||
}
|
||||
foreach (string directory in collection.Distinct())
|
||||
|
@ -326,7 +326,7 @@ public class D_Face
|
||||
string[] changesFrom = [nameof(A_Property), nameof(B_Metadata), nameof(C_Resize)];
|
||||
List<DateTime> dateTimes = (from l in subFileTuples where changesFrom.Contains(l.Item1) select l.Item2).ToList();
|
||||
(_, int directoryIndex) = Shared.Models.Stateless.Methods.IPath.GetDirectoryNameAndIndex(_PropertyConfiguration, filePath);
|
||||
FileInfo fileInfo = new(Path.Combine(_FileGroups[_PropertyConfiguration.ResultCollection][directoryIndex], $"{mappingFromItem.ImageFileHolder.NameWithoutExtension}{mappingFromItem.ImageFileHolder.ExtensionLowered}.json"));
|
||||
FileInfo fileInfo = new(Path.Combine(_FileGroups[_PropertyConfiguration.ResultCollection][directoryIndex], $"{mappingFromItem.FilePath.NameWithoutExtension}{mappingFromItem.FilePath.ExtensionLowered}.json"));
|
||||
if (_ForceFaceLastWriteTimeToCreationTime && !fileInfo.Exists && File.Exists(Path.ChangeExtension(fileInfo.FullName, ".delete")))
|
||||
{
|
||||
File.Move(Path.ChangeExtension(fileInfo.FullName, ".delete"), fileInfo.FullName);
|
||||
@ -403,7 +403,7 @@ public class D_Face
|
||||
string[] changesFrom = [nameof(A_Property), nameof(B_Metadata), nameof(C_Resize)];
|
||||
List<DateTime> dateTimes = (from l in subFileTuples where changesFrom.Contains(l.Item1) select l.Item2).ToList();
|
||||
(_, int directoryIndex) = Shared.Models.Stateless.Methods.IPath.GetDirectoryNameAndIndex(_PropertyConfiguration, filePath);
|
||||
string directory = Path.Combine(_FileGroups[_PropertyConfiguration.ResultContent][directoryIndex], mappingFromItem.ImageFileHolder.NameWithoutExtension);
|
||||
string directory = Path.Combine(_FileGroups[_PropertyConfiguration.ResultContent][directoryIndex], mappingFromItem.FilePath.NameWithoutExtension);
|
||||
bool directoryExists = Directory.Exists(directory);
|
||||
foreach (Shared.Models.Face face in faces)
|
||||
{
|
||||
@ -414,7 +414,7 @@ public class D_Face
|
||||
continue;
|
||||
}
|
||||
deterministicHashCodeKey = Shared.Models.Stateless.Methods.IMapping.GetDeterministicHashCodeKey(filePath, face.Location, Shared.Models.Stateless.ILocation.Digits, face.OutputResolution);
|
||||
fileInfo = new FileInfo(Path.Combine(directory, $"{deterministicHashCodeKey}{mappingFromItem.ImageFileHolder.ExtensionLowered}{_FileNameExtension}"));
|
||||
fileInfo = new FileInfo(Path.Combine(directory, $"{deterministicHashCodeKey}{mappingFromItem.FilePath.ExtensionLowered}{_FileNameExtension}"));
|
||||
if (!directoryExists)
|
||||
save = true;
|
||||
else if (_OverrideForFaceImages)
|
||||
@ -423,7 +423,7 @@ public class D_Face
|
||||
save = true;
|
||||
else if (_CheckDFaceAndUpWriteDates && dateTimes.Count > 0 && dateTimes.Max() > fileInfo.LastWriteTime)
|
||||
save = true;
|
||||
results.Add(new(face, fileInfo, Path.Combine(directory, $"{deterministicHashCodeKey}{mappingFromItem.ImageFileHolder.ExtensionLowered}{_HiddenFileNameExtension}"), save));
|
||||
results.Add(new(face, fileInfo, Path.Combine(directory, $"{deterministicHashCodeKey}{mappingFromItem.FilePath.ExtensionLowered}{_HiddenFileNameExtension}"), save));
|
||||
}
|
||||
if (results.Any(l => l.Save))
|
||||
{
|
||||
|
@ -75,12 +75,12 @@ public class D2_FaceParts
|
||||
bool angleBracketCollectionAny = _AngleBracketCollection.Count != 0;
|
||||
if (!angleBracketCollectionAny)
|
||||
{
|
||||
if (item.ImageFileHolder.DirectoryName is null)
|
||||
throw new NullReferenceException(nameof(item.ImageFileHolder.DirectoryName));
|
||||
SetAngleBracketCollection(configuration, dResultsFullGroupDirectory, item.ImageFileHolder.DirectoryName);
|
||||
if (item.FilePath.DirectoryName is null)
|
||||
throw new NullReferenceException(nameof(item.FilePath.DirectoryName));
|
||||
SetAngleBracketCollection(configuration, dResultsFullGroupDirectory, item.FilePath.DirectoryName);
|
||||
}
|
||||
if (includeNameWithoutExtension)
|
||||
result = Path.Combine(_AngleBracketCollection[0].Replace("<>", _PropertyConfiguration.ResultContent), item.ImageFileHolder.NameWithoutExtension);
|
||||
result = Path.Combine(_AngleBracketCollection[0].Replace("<>", _PropertyConfiguration.ResultContent), item.FilePath.NameWithoutExtension);
|
||||
else
|
||||
{
|
||||
result = _AngleBracketCollection[0].Replace("<>", $"[{_PropertyConfiguration.ResultContent}]");
|
||||
@ -259,7 +259,7 @@ public class D2_FaceParts
|
||||
string[] changesFrom = [nameof(A_Property), nameof(B_Metadata), nameof(C_Resize), nameof(D_Face)];
|
||||
List<DateTime> dateTimes = (from l in subFileTuples where changesFrom.Contains(l.Item1) select l.Item2).ToList();
|
||||
(_, int directoryIndex) = Shared.Models.Stateless.Methods.IPath.GetDirectoryNameAndIndex(_PropertyConfiguration, filePath);
|
||||
string directory = Path.Combine(_FileGroups[_PropertyConfiguration.ResultContent][directoryIndex], mappingFromItem.ImageFileHolder.NameWithoutExtension);
|
||||
string directory = Path.Combine(_FileGroups[_PropertyConfiguration.ResultContent][directoryIndex], mappingFromItem.FilePath.NameWithoutExtension);
|
||||
bool directoryExists = Directory.Exists(directory);
|
||||
foreach (Shared.Models.Face face in faces)
|
||||
{
|
||||
@ -269,10 +269,10 @@ public class D2_FaceParts
|
||||
continue;
|
||||
}
|
||||
deterministicHashCodeKey = Shared.Models.Stateless.Methods.IMapping.GetDeterministicHashCodeKey(filePath, face.Location, Shared.Models.Stateless.ILocation.Digits, face.OutputResolution);
|
||||
fileInfo = new FileInfo(Path.Combine(directory, $"{deterministicHashCodeKey}{mappingFromItem.ImageFileHolder.ExtensionLowered}{_FileNameExtension}"));
|
||||
fileInfo = new FileInfo(Path.Combine(directory, $"{deterministicHashCodeKey}{mappingFromItem.FilePath.ExtensionLowered}{_FileNameExtension}"));
|
||||
if (string.IsNullOrEmpty(fileInfo.DirectoryName))
|
||||
continue;
|
||||
rotatedFileInfo = new FileInfo(Path.Combine(fileInfo.DirectoryName, $"{deterministicHashCodeKey} - R{mappingFromItem.ImageFileHolder.ExtensionLowered}{_FileNameExtension}"));
|
||||
rotatedFileInfo = new FileInfo(Path.Combine(fileInfo.DirectoryName, $"{deterministicHashCodeKey} - R{mappingFromItem.FilePath.ExtensionLowered}{_FileNameExtension}"));
|
||||
collection.Add(new(face, fileInfo.FullName, rotatedFileInfo.FullName));
|
||||
if (check)
|
||||
continue;
|
||||
@ -363,7 +363,7 @@ public class D2_FaceParts
|
||||
public void CopyFacesAndSaveFaceLandmarkImage(string facePartsCollectionDirectory, MappingFromItem mappingFromItem, List<(Shared.Models.Face Face, FileInfo?, string, bool)> faceCollection)
|
||||
{
|
||||
bool hasNotMapped = GetNotMapped(facePartsCollectionDirectory, faceCollection);
|
||||
string fileName = Path.Combine(facePartsCollectionDirectory, $"{mappingFromItem.ImageFileHolder.Name}{_FileNameExtension}");
|
||||
string fileName = Path.Combine(facePartsCollectionDirectory, $"{mappingFromItem.FilePath.Name}{_FileNameExtension}");
|
||||
bool save = faceCollection.Any(l => l.Face.FaceEncoding is not null && l.Face.Location is not null && l.Face.OutputResolution is not null && l.Face.FaceParts is not null && l.Face.FaceParts.Count != 0);
|
||||
FileInfo fileInfo = new(fileName);
|
||||
if (save && (!fileInfo.Exists || new TimeSpan(DateTime.Now.Ticks - fileInfo.LastWriteTime.Ticks).TotalDays > 10))
|
||||
|
@ -392,7 +392,7 @@ public partial class DlibDotNet
|
||||
&& _Exceptions.Count == 0)
|
||||
MapLogic(ticks, readOnlyContainers, fPhotoPrismContentDirectory, mapLogic, outputResolution, new(personKeyToIds), distinctFilteredFaces, distinctFilteredMappingCollection);
|
||||
if (runToDoCollectionFirst && _Configuration.SaveRandomForOutputResolutions.Contains(outputResolution) && personKeyToIds.Count > 0 && distinctFilteredMappingCollection.Count > 0)
|
||||
_Random.Random(_Configuration.PropertyConfiguration, _Configuration.RadomUseBirthdayMinimum, _Configuration.ValidKeyWordsToIgnoreInRandom, outputResolution, personKeyToIds, notNineCollection, distinctFilteredMappingCollection);
|
||||
_Random.Random(_Configuration.PropertyConfiguration, _Configuration.RadomUseBirthdayMinimum, _Configuration.ValidKeyWordsToIgnoreInRandom, personKeyToIds, notNineCollection, distinctFilteredMappingCollection);
|
||||
if (_IsEnvironment.Development)
|
||||
continue;
|
||||
if (!_IsEnvironment.Development)
|
||||
@ -598,7 +598,9 @@ public partial class DlibDotNet
|
||||
|
||||
private static void SaveDistinctIds(Property.Models.Configuration propertyConfiguration, string bResultsFullGroupDirectory, ReadOnlyCollection<Container> readOnlyContainers)
|
||||
{
|
||||
string paddedId;
|
||||
List<int> distinct = [];
|
||||
List<Identifier> identifiers = [];
|
||||
string bMetadataCollectionDirectory = Path.Combine(bResultsFullGroupDirectory, propertyConfiguration.ResultCollection);
|
||||
if (!Directory.Exists(bMetadataCollectionDirectory))
|
||||
_ = Directory.CreateDirectory(bMetadataCollectionDirectory);
|
||||
@ -610,13 +612,16 @@ public partial class DlibDotNet
|
||||
{
|
||||
if (item.Property?.Id is null)
|
||||
continue;
|
||||
if (item.Property.Id != item.FilePath.Id)
|
||||
throw new NotSupportedException();
|
||||
if (distinct.Contains(item.Property.Id.Value))
|
||||
continue;
|
||||
distinct.Add(item.Property.Id.Value);
|
||||
paddedId = IId.GetPaddedId(propertyConfiguration, item.Property.Id.Value, item.FilePath.IsIgnore, index: null);
|
||||
identifiers.Add(new(item.Property.Id.Value, paddedId));
|
||||
}
|
||||
}
|
||||
distinct.Sort();
|
||||
string json = JsonSerializer.Serialize(distinct);
|
||||
string json = JsonSerializer.Serialize(identifiers.OrderBy(l => l.PaddedId).ToArray(), IdentifierCollectionSourceGenerationContext.Default.IdentifierArray);
|
||||
_ = Shared.Models.Stateless.Methods.IPath.WriteAllText(Path.Combine(bMetadataCollectionDirectory, ".json"), json, updateDateWhenMatches: false, compareBeforeWrite: true, updateToWhenMatches: null);
|
||||
}
|
||||
|
||||
@ -710,13 +715,13 @@ public partial class DlibDotNet
|
||||
List<(string, string, string)> collection = [];
|
||||
foreach (Item item in distinctFilteredItems)
|
||||
{
|
||||
if (item.Property?.Id is null || item.ImageFileHolder.LastWriteTime is null)
|
||||
if (item.Property?.Id is null)
|
||||
continue;
|
||||
if (item.IsNotUniqueAndNeedsReview is null || !item.IsNotUniqueAndNeedsReview.Value)
|
||||
continue;
|
||||
directory = Path.Combine($"{eDistanceContentDirectory[..^1]}{nameof(item.IsNotUniqueAndNeedsReview)})", item.ImageFileHolder.NameWithoutExtension);
|
||||
fileName = Path.Combine(directory, $"{item.ImageFileHolder.Length} {item.ImageFileHolder.LastWriteTime.Value.Ticks}.lnk");
|
||||
collection.Add((item.ImageFileHolder.FullName, directory, fileName));
|
||||
directory = Path.Combine($"{eDistanceContentDirectory[..^1]}{nameof(item.IsNotUniqueAndNeedsReview)})", item.FilePath.NameWithoutExtension);
|
||||
fileName = Path.Combine(directory, $"{item.FilePath.Length} {item.FilePath.LastWriteTicks}.lnk");
|
||||
collection.Add((item.FilePath.FullName, directory, fileName));
|
||||
if (distinct.Contains(directory))
|
||||
continue;
|
||||
distinct.Add(directory);
|
||||
@ -726,14 +731,14 @@ public partial class DlibDotNet
|
||||
if (item.Property?.Id is null || item.Property.DateTimeOriginal is null)
|
||||
continue;
|
||||
dateTimes = item.Property.GetDateTimes();
|
||||
(isWrongYear, _) = Shared.Models.Stateless.Methods.IProperty.IsWrongYear(item.ImageFileHolder, item.Property.DateTimeOriginal, dateTimes);
|
||||
(isWrongYear, _) = Shared.Models.Stateless.Methods.IProperty.IsWrongYear(item.FilePath, item.Property.DateTimeOriginal, dateTimes);
|
||||
if (isWrongYear is null || !isWrongYear.Value)
|
||||
continue;
|
||||
// Remove-Item -LiteralPath "\\?\D:\Tmp\a\EX-Z70 "
|
||||
model = string.IsNullOrEmpty(item.Property.Model) ? "Unknown" : CameraRegex().Replace(item.Property.Model.Trim(), "_");
|
||||
directory = Path.Combine($"{eDistanceContentDirectory[..^1]}{nameof(Item)})", item.Property.DateTimeOriginal.Value.Year.ToString(), model);
|
||||
fileName = item.IsNotUniqueAndNeedsReview is not null && item.IsNotUniqueAndNeedsReview.Value ? Path.Combine(directory, $"{item.ImageFileHolder.Name} {item.ImageFileHolder.Length}.lnk") : Path.Combine(directory, $"{item.ImageFileHolder.Name}.lnk");
|
||||
collection.Add((item.ImageFileHolder.FullName, directory, fileName));
|
||||
fileName = item.IsNotUniqueAndNeedsReview is not null && item.IsNotUniqueAndNeedsReview.Value ? Path.Combine(directory, $"{item.FilePath.Name} {item.FilePath.Length}.lnk") : Path.Combine(directory, $"{item.FilePath.Name}.lnk");
|
||||
collection.Add((item.FilePath.FullName, directory, fileName));
|
||||
if (distinct.Contains(directory))
|
||||
continue;
|
||||
distinct.Add(directory);
|
||||
@ -804,13 +809,13 @@ public partial class DlibDotNet
|
||||
private void LogItemPropertyIsNull(Item item)
|
||||
{
|
||||
if (!item.SourceDirectoryFileHolder.Exists)
|
||||
_Logger?.LogInformation(string.Concat("NoJson <", item.ImageFileHolder.FullName, '>'));
|
||||
_Logger?.LogInformation(string.Concat("NoJson <", item.FilePath.FullName, '>'));
|
||||
else if (item.FileSizeChanged.HasValue && item.FileSizeChanged.Value)
|
||||
_Logger?.LogInformation(string.Concat("FileSizeChanged <", item.ImageFileHolder.FullName, '>'));
|
||||
_Logger?.LogInformation(string.Concat("FileSizeChanged <", item.FilePath.FullName, '>'));
|
||||
else if (item.LastWriteTimeChanged.HasValue && item.LastWriteTimeChanged.Value)
|
||||
_Logger?.LogInformation(string.Concat("LastWriteTimeChanged <", item.ImageFileHolder.FullName, '>'));
|
||||
_Logger?.LogInformation(string.Concat("LastWriteTimeChanged <", item.FilePath.FullName, '>'));
|
||||
else if (item.Moved.HasValue && item.Moved.Value)
|
||||
_Logger?.LogInformation(string.Concat("Moved <", item.ImageFileHolder.FullName, '>'));
|
||||
_Logger?.LogInformation(string.Concat("Moved <", item.FilePath.FullName, '>'));
|
||||
}
|
||||
|
||||
private int GetNotMappedCountAndUpdateMappingFromPersonThenSetMapping(MapLogic mapLogic, Item item, bool? isFocusRelativePath, ReadOnlyCollection<LocationContainer> locationContainers, MappingFromItem mappingFromItem, List<MappingFromPhotoPrism>? mappingFromPhotoPrismCollection, List<Shared.Models.Face> faces)
|
||||
@ -987,7 +992,6 @@ public partial class DlibDotNet
|
||||
subFileTuples.Add(new Tuple<string, DateTime>(nameof(A_Property), item.SourceDirectoryFileHolder.LastWriteTime.Value));
|
||||
else
|
||||
subFileTuples.Add(new Tuple<string, DateTime>(nameof(A_Property), new FileInfo(item.SourceDirectoryFileHolder.FullName).LastWriteTime));
|
||||
FilePath filePath = FilePath.Get(_Configuration.PropertyConfiguration, item.ImageFileHolder, index: null);
|
||||
if (resizedFileHolder.Exists && item.Property.Width is not null && item.Property.Width.Value > 4 && _Configuration.SaveBlurHashForOutputResolutions.Contains(outputResolution))
|
||||
{
|
||||
string? file = _BlurHasher.GetFile(item.FilePath);
|
||||
|
27
Instance/Models/Identifier.cs
Normal file
27
Instance/Models/Identifier.cs
Normal file
@ -0,0 +1,27 @@
|
||||
using System.Text.Json;
|
||||
using System.Text.Json.Serialization;
|
||||
|
||||
namespace View_by_Distance.Instance.Models;
|
||||
|
||||
internal record Identifier(int Id, string PaddedId)
|
||||
{
|
||||
|
||||
public override string ToString()
|
||||
{
|
||||
string result = JsonSerializer.Serialize(this, IdentifierSourceGenerationContext.Default.Identifier);
|
||||
return result;
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
[JsonSourceGenerationOptions(WriteIndented = true)]
|
||||
[JsonSerializable(typeof(Identifier))]
|
||||
internal partial class IdentifierSourceGenerationContext : JsonSerializerContext
|
||||
{
|
||||
}
|
||||
|
||||
[JsonSourceGenerationOptions(WriteIndented = true)]
|
||||
[JsonSerializable(typeof(Identifier[]))]
|
||||
internal partial class IdentifierCollectionSourceGenerationContext : JsonSerializerContext
|
||||
{
|
||||
}
|
@ -33,7 +33,7 @@ internal class F_Random
|
||||
List<string>? relativePaths;
|
||||
foreach (Shared.Models.Mapping mapping in mappingCollection)
|
||||
{
|
||||
if (mapping.MappingFromItem.ImageFileHolder.DirectoryName is null || mapping.MappingFromPerson is null)
|
||||
if (mapping.MappingFromItem.FilePath.DirectoryName is null || mapping.MappingFromPerson is null)
|
||||
continue;
|
||||
if (!idToPersonKeys.TryGetValue(mapping.MappingFromItem.Id, out personKeys))
|
||||
continue;
|
||||
@ -54,7 +54,7 @@ internal class F_Random
|
||||
return new(results);
|
||||
}
|
||||
|
||||
internal void Random(Property.Models.Configuration configuration, int radomUseBirthdayMinimum, string[] validKeyWordsToIgnoreInRandom, string outputResolution, ReadOnlyDictionary<long, List<int>> personKeyToIds, ReadOnlyCollection<int>? notNineCollection, ReadOnlyCollection<Shared.Models.Mapping> mappingCollection)
|
||||
internal void Random(Property.Models.Configuration configuration, int radomUseBirthdayMinimum, string[] validKeyWordsToIgnoreInRandom, ReadOnlyDictionary<long, List<int>> personKeyToIds, ReadOnlyCollection<int>? notNineCollection, ReadOnlyCollection<Shared.Models.Mapping> mappingCollection)
|
||||
{
|
||||
string key;
|
||||
string json;
|
||||
@ -75,7 +75,7 @@ internal class F_Random
|
||||
{
|
||||
if (distinctCollection.Contains(mapping.MappingFromItem.Id))
|
||||
continue;
|
||||
if (mapping.MappingFromItem.ImageFileHolder.DirectoryName is null)
|
||||
if (mapping.MappingFromItem.FilePath.DirectoryName is null)
|
||||
continue;
|
||||
if (notNineCollection is not null && notNineCollection.Contains(mapping.MappingFromItem.Id))
|
||||
continue;
|
||||
|
@ -160,17 +160,17 @@ public partial class MapLogic : Shared.Models.Methods.IMapLogic
|
||||
(season, _) = IProperty.GetSeason(dateTime.DayOfYear);
|
||||
weekOfYear = calendar.GetWeekOfYear(dateTime, CalendarWeekRule.FirstDay, DayOfWeek.Sunday).ToString("00");
|
||||
directory = Path.Combine($"{eDistanceContentDirectory}---", "Date Shortcuts", $"{dateTime.Year}.{season}-MM{dateTime.Month:00}-WW{weekOfYear}");
|
||||
fileName = Path.Combine(directory, $"{mapping.MappingFromItem.ImageFileHolder.Name}.lnk");
|
||||
results.Add(new(mapping.MappingFromItem.ImageFileHolder.FullName, directory, dateTime, fileName, description, MakeAllHidden: false));
|
||||
if (mapping.MappingFromItem.ImageFileHolder.DirectoryName is null)
|
||||
fileName = Path.Combine(directory, $"{mapping.MappingFromItem.FilePath.Name}.lnk");
|
||||
results.Add(new(mapping.MappingFromItem.FilePath.FullName, directory, dateTime, fileName, description, MakeAllHidden: false));
|
||||
if (mapping.MappingFromItem.FilePath.DirectoryName is null)
|
||||
continue;
|
||||
directoryName = Path.GetFileName(mapping.MappingFromItem.ImageFileHolder.DirectoryName);
|
||||
directoryName = Path.GetFileName(mapping.MappingFromItem.FilePath.DirectoryName);
|
||||
if (!string.IsNullOrEmpty(mapping.MappingFromItem.Model) && !string.IsNullOrEmpty(mapping.MappingFromItem.Model.Trim()))
|
||||
{
|
||||
// Remove-Item -LiteralPath "\\?\D:\Tmp\a\EX-Z70 "
|
||||
directory = Path.Combine($"{eDistanceContentDirectory}---", "Model Shortcuts", FileSystemSafe().Replace(mapping.MappingFromItem.Model.Trim(), "_"), directoryName);
|
||||
fileName = Path.Combine(directory, $"{mapping.MappingFromItem.ImageFileHolder.Name}.lnk");
|
||||
results.Add(new(mapping.MappingFromItem.ImageFileHolder.FullName, directory, dateTime, fileName, description, MakeAllHidden: false));
|
||||
fileName = Path.Combine(directory, $"{mapping.MappingFromItem.FilePath.Name}.lnk");
|
||||
results.Add(new(mapping.MappingFromItem.FilePath.FullName, directory, dateTime, fileName, description, MakeAllHidden: false));
|
||||
}
|
||||
if (mapping.MappingFromPerson is null)
|
||||
continue;
|
||||
@ -180,13 +180,13 @@ public partial class MapLogic : Shared.Models.Methods.IMapLogic
|
||||
continue;
|
||||
personKeyFormatted = IPersonBirthday.GetFormatted(_Configuration.PersonBirthdayFormat, mapping.MappingFromPerson.PersonKey);
|
||||
directory = Path.Combine($"{eDistanceContentDirectory}---", "Person Key Shortcuts", personKeyFormatted, directoryName);
|
||||
fileName = Path.Combine(directory, $"{mapping.MappingFromItem.ImageFileHolder.Name}.lnk");
|
||||
results.Add(new(mapping.MappingFromItem.ImageFileHolder.FullName, directory, mapping.MappingFromItem.GetDateTimeOriginalThenMinimumDateTime(), fileName, description, MakeAllHidden: false));
|
||||
fileName = Path.Combine(directory, $"{mapping.MappingFromItem.FilePath.Name}.lnk");
|
||||
results.Add(new(mapping.MappingFromItem.FilePath.FullName, directory, mapping.MappingFromItem.GetDateTimeOriginalThenMinimumDateTime(), fileName, description, MakeAllHidden: false));
|
||||
if (IPerson.IsDefaultName(mapping.MappingFromPerson))
|
||||
continue;
|
||||
directory = Path.Combine($"{eDistanceContentDirectory}---", "Name Shortcuts", mapping.MappingFromPerson.DisplayDirectoryName, directoryName);
|
||||
fileName = Path.Combine(directory, $"{mapping.MappingFromItem.ImageFileHolder.Name}.lnk");
|
||||
results.Add(new(mapping.MappingFromItem.ImageFileHolder.FullName, directory, mapping.MappingFromItem.GetDateTimeOriginalThenMinimumDateTime(), fileName, description, MakeAllHidden: false));
|
||||
fileName = Path.Combine(directory, $"{mapping.MappingFromItem.FilePath.Name}.lnk");
|
||||
results.Add(new(mapping.MappingFromItem.FilePath.FullName, directory, mapping.MappingFromItem.GetDateTimeOriginalThenMinimumDateTime(), fileName, description, MakeAllHidden: false));
|
||||
}
|
||||
return results;
|
||||
}
|
||||
@ -436,16 +436,16 @@ public partial class MapLogic : Shared.Models.Methods.IMapLogic
|
||||
{
|
||||
string checkFile;
|
||||
string facesDirectory = Stateless.MapLogic.GetFacesDirectory(_PropertyConfiguration, dFacesContentDirectory, mapping.FilePath, mapping.MappingFromItem);
|
||||
FileHolder faceFileHolder = IFileHolder.Get(Path.Combine(facesDirectory, $"{mapping.MappingFromLocation.DeterministicHashCodeKey}{mapping.MappingFromItem.ImageFileHolder.ExtensionLowered}{_Configuration.FacesFileNameExtension}"));
|
||||
FileHolder faceFileHolder = IFileHolder.Get(Path.Combine(facesDirectory, $"{mapping.MappingFromLocation.DeterministicHashCodeKey}{mapping.MappingFromItem.FilePath.ExtensionLowered}{_Configuration.FacesFileNameExtension}"));
|
||||
if (!faceFileHolder.Exists)
|
||||
result = null;
|
||||
else
|
||||
{
|
||||
string shortcutFile = string.Empty;
|
||||
string facePartsDirectory = Stateless.MapLogic.GetFacePartsDirectory(_PropertyConfiguration, d2FacePartsContentDirectory, mapping.FilePath, mapping.MappingFromItem);
|
||||
checkFile = Path.Combine(directory, $"{mapping.MappingFromLocation.DeterministicHashCodeKey}{mapping.MappingFromItem.ImageFileHolder.ExtensionLowered}");
|
||||
FileHolder hiddenFaceFileHolder = IFileHolder.Get(Path.Combine(facesDirectory, $"{mapping.MappingFromLocation.DeterministicHashCodeKey}{mapping.MappingFromItem.ImageFileHolder.ExtensionLowered}{_Configuration.FacesHiddenFileNameExtension}"));
|
||||
FileHolder facePartsFileHolder = IFileHolder.Get(Path.Combine(facePartsDirectory, $"{mapping.MappingFromLocation.DeterministicHashCodeKey}{mapping.MappingFromItem.ImageFileHolder.ExtensionLowered}{_Configuration.FacePartsFileNameExtension}"));
|
||||
checkFile = Path.Combine(directory, $"{mapping.MappingFromLocation.DeterministicHashCodeKey}{mapping.MappingFromItem.FilePath.ExtensionLowered}");
|
||||
FileHolder hiddenFaceFileHolder = IFileHolder.Get(Path.Combine(facesDirectory, $"{mapping.MappingFromLocation.DeterministicHashCodeKey}{mapping.MappingFromItem.FilePath.ExtensionLowered}{_Configuration.FacesHiddenFileNameExtension}"));
|
||||
FileHolder facePartsFileHolder = IFileHolder.Get(Path.Combine(facePartsDirectory, $"{mapping.MappingFromLocation.DeterministicHashCodeKey}{mapping.MappingFromItem.FilePath.ExtensionLowered}{_Configuration.FacePartsFileNameExtension}"));
|
||||
result = new(checkFile, directory, faceFileHolder, hiddenFaceFileHolder, facePartsFileHolder, mapping.MappingFromItem.ResizedFileHolder, shortcutFile);
|
||||
}
|
||||
}
|
||||
@ -621,18 +621,18 @@ public partial class MapLogic : Shared.Models.Methods.IMapLogic
|
||||
results.Add(new(Path.Combine(directory, "Maybe")));
|
||||
}
|
||||
facesDirectory = Stateless.MapLogic.GetFacesDirectory(_PropertyConfiguration, dFacesContentDirectory, mapping.FilePath, mapping.MappingFromItem);
|
||||
faceFileHolder = IFileHolder.Get(Path.Combine(facesDirectory, $"{mapping.MappingFromLocation.DeterministicHashCodeKey}{mapping.MappingFromItem.ImageFileHolder.ExtensionLowered}{_Configuration.FacesFileNameExtension}"));
|
||||
faceFileHolder = IFileHolder.Get(Path.Combine(facesDirectory, $"{mapping.MappingFromLocation.DeterministicHashCodeKey}{mapping.MappingFromItem.FilePath.ExtensionLowered}{_Configuration.FacesFileNameExtension}"));
|
||||
if (!faceFileHolder.Exists)
|
||||
continue;
|
||||
if (isByMapping)
|
||||
{
|
||||
checkFile = Path.Combine(record.PersonDirectory, $"{mapping.MappingFromLocation.DeterministicHashCodeKey}{mapping.MappingFromItem.ImageFileHolder.ExtensionLowered}");
|
||||
checkFile = Path.Combine(record.PersonDirectory, $"{mapping.MappingFromLocation.DeterministicHashCodeKey}{mapping.MappingFromItem.FilePath.ExtensionLowered}");
|
||||
saveContainer = new(checkFile, directory, faceFileHolder);
|
||||
}
|
||||
else if (saveIndividually)
|
||||
{
|
||||
facePartsDirectory = Stateless.MapLogic.GetFacePartsDirectory(_PropertyConfiguration, d2FacePartsContentDirectory, mapping.FilePath, mapping.MappingFromItem);
|
||||
facePartsFileHolder = IFileHolder.Get(Path.Combine(facePartsDirectory, $"{mapping.MappingFromLocation.DeterministicHashCodeKey}{mapping.MappingFromItem.ImageFileHolder.ExtensionLowered}{_Configuration.FacePartsFileNameExtension}"));
|
||||
facePartsFileHolder = IFileHolder.Get(Path.Combine(facePartsDirectory, $"{mapping.MappingFromLocation.DeterministicHashCodeKey}{mapping.MappingFromItem.FilePath.ExtensionLowered}{_Configuration.FacePartsFileNameExtension}"));
|
||||
(saveContainer, SaveContainer? extraSaveContainer) = Stateless.MapLogic.GetContainers(_Configuration.FacesFileNameExtension, _Configuration.FacePartsFileNameExtension, directory, faceFileHolder, facePartsFileHolder, mapping);
|
||||
if (extraSaveContainer is not null)
|
||||
results.Add(extraSaveContainer);
|
||||
@ -640,10 +640,10 @@ public partial class MapLogic : Shared.Models.Methods.IMapLogic
|
||||
else
|
||||
{
|
||||
facePartsDirectory = Stateless.MapLogic.GetFacePartsDirectory(_PropertyConfiguration, d2FacePartsContentDirectory, mapping.FilePath, mapping.MappingFromItem);
|
||||
shortcutFile = Path.Combine(record.PersonDirectory, $"{mapping.MappingFromLocation.DeterministicHashCodeKey}{mapping.MappingFromItem.ImageFileHolder.ExtensionLowered}.lnk");
|
||||
checkFile = Path.Combine(directory, $"{mapping.MappingFromLocation.DeterministicHashCodeKey}{mapping.MappingFromItem.ImageFileHolder.ExtensionLowered}");
|
||||
hiddenFaceFileHolder = IFileHolder.Get(Path.Combine(facesDirectory, $"{mapping.MappingFromLocation.DeterministicHashCodeKey}{mapping.MappingFromItem.ImageFileHolder.ExtensionLowered}{_Configuration.FacesHiddenFileNameExtension}"));
|
||||
facePartsFileHolder = IFileHolder.Get(Path.Combine(facePartsDirectory, $"{mapping.MappingFromLocation.DeterministicHashCodeKey}{mapping.MappingFromItem.ImageFileHolder.ExtensionLowered}{_Configuration.FacePartsFileNameExtension}"));
|
||||
shortcutFile = Path.Combine(record.PersonDirectory, $"{mapping.MappingFromLocation.DeterministicHashCodeKey}{mapping.MappingFromItem.FilePath.ExtensionLowered}.lnk");
|
||||
checkFile = Path.Combine(directory, $"{mapping.MappingFromLocation.DeterministicHashCodeKey}{mapping.MappingFromItem.FilePath.ExtensionLowered}");
|
||||
hiddenFaceFileHolder = IFileHolder.Get(Path.Combine(facesDirectory, $"{mapping.MappingFromLocation.DeterministicHashCodeKey}{mapping.MappingFromItem.FilePath.ExtensionLowered}{_Configuration.FacesHiddenFileNameExtension}"));
|
||||
facePartsFileHolder = IFileHolder.Get(Path.Combine(facePartsDirectory, $"{mapping.MappingFromLocation.DeterministicHashCodeKey}{mapping.MappingFromItem.FilePath.ExtensionLowered}{_Configuration.FacePartsFileNameExtension}"));
|
||||
saveContainer = new(checkFile, directory, faceFileHolder, hiddenFaceFileHolder, facePartsFileHolder, mapping.MappingFromItem.ResizedFileHolder, shortcutFile);
|
||||
}
|
||||
results.Add(saveContainer);
|
||||
@ -832,12 +832,12 @@ public partial class MapLogic : Shared.Models.Methods.IMapLogic
|
||||
if (_Configuration.SaveIndividually && question.MappingFromLocation.WholePercentages == question.MappingFromLocation.WholePercentages)
|
||||
results.Add(new(Path.Combine(directory, "Maybe")));
|
||||
facesDirectory = Stateless.MapLogic.GetFacesDirectory(_PropertyConfiguration, dFacesContentDirectory, question.FilePath, question.MappingFromItem);
|
||||
faceFileHolder = IFileHolder.Get(Path.Combine(facesDirectory, $"{question.MappingFromLocation.DeterministicHashCodeKey}{question.MappingFromItem.ImageFileHolder.ExtensionLowered}{_Configuration.FacesFileNameExtension}"));
|
||||
faceFileHolder = IFileHolder.Get(Path.Combine(facesDirectory, $"{question.MappingFromLocation.DeterministicHashCodeKey}{question.MappingFromItem.FilePath.ExtensionLowered}{_Configuration.FacesFileNameExtension}"));
|
||||
facePartsDirectory = Stateless.MapLogic.GetFacePartsDirectory(_PropertyConfiguration, d2FacePartsContentDirectory, question.FilePath, question.MappingFromItem);
|
||||
shortcutFile = Path.Combine(record.PersonDirectory, $"{question.MappingFromLocation.DeterministicHashCodeKey}{question.MappingFromItem.ImageFileHolder.ExtensionLowered}.lnk");
|
||||
checkFile = Path.Combine(directory, $"{question.MappingFromLocation.DeterministicHashCodeKey}{question.MappingFromItem.ImageFileHolder.ExtensionLowered}");
|
||||
hiddenFaceFileHolder = IFileHolder.Get(Path.Combine(facesDirectory, $"{question.MappingFromLocation.DeterministicHashCodeKey}{question.MappingFromItem.ImageFileHolder.ExtensionLowered}{_Configuration.FacesHiddenFileNameExtension}"));
|
||||
facePartsFileHolder = IFileHolder.Get(Path.Combine(facePartsDirectory, $"{question.MappingFromLocation.DeterministicHashCodeKey}{question.MappingFromItem.ImageFileHolder.ExtensionLowered}{_Configuration.FacePartsFileNameExtension}"));
|
||||
shortcutFile = Path.Combine(record.PersonDirectory, $"{question.MappingFromLocation.DeterministicHashCodeKey}{question.MappingFromItem.FilePath.ExtensionLowered}.lnk");
|
||||
checkFile = Path.Combine(directory, $"{question.MappingFromLocation.DeterministicHashCodeKey}{question.MappingFromItem.FilePath.ExtensionLowered}");
|
||||
hiddenFaceFileHolder = IFileHolder.Get(Path.Combine(facesDirectory, $"{question.MappingFromLocation.DeterministicHashCodeKey}{question.MappingFromItem.FilePath.ExtensionLowered}{_Configuration.FacesHiddenFileNameExtension}"));
|
||||
facePartsFileHolder = IFileHolder.Get(Path.Combine(facePartsDirectory, $"{question.MappingFromLocation.DeterministicHashCodeKey}{question.MappingFromItem.FilePath.ExtensionLowered}{_Configuration.FacePartsFileNameExtension}"));
|
||||
saveContainer = new(checkFile, directory, faceFileHolder, hiddenFaceFileHolder, facePartsFileHolder, question.MappingFromItem.ResizedFileHolder, shortcutFile);
|
||||
results.Add(saveContainer);
|
||||
if (!_Configuration.SaveIndividually && isBySorting && question.MappingFromPerson is null)
|
||||
@ -1044,11 +1044,11 @@ public partial class MapLogic : Shared.Models.Methods.IMapLogic
|
||||
return results;
|
||||
}
|
||||
|
||||
private (int, FileHolder, int, string, string, string, string)[] GetCollectionForSaveFilteredOriginalImagesFromJLinks(string[] jLinks, string a2PeopleContentDirectory, ReadOnlyCollection<PersonContainer> personContainers, ReadOnlyCollection<Mapping> mappingCollection, ReadOnlyDictionary<long, List<int>> personKeyToIds)
|
||||
private (int, FilePath, int, string, string, string, string)[] GetCollectionForSaveFilteredOriginalImagesFromJLinks(string[] jLinks, string a2PeopleContentDirectory, ReadOnlyCollection<PersonContainer> personContainers, ReadOnlyCollection<Mapping> mappingCollection, ReadOnlyDictionary<long, List<int>> personKeyToIds)
|
||||
{
|
||||
if (_Configuration is null)
|
||||
throw new NullReferenceException(nameof(_Configuration));
|
||||
(int, FileHolder, int, string, string, string, string)[] results;
|
||||
(int, FilePath, int, string, string, string, string)[] results;
|
||||
int count = 0;
|
||||
int group = 65;
|
||||
string checkFile;
|
||||
@ -1059,7 +1059,7 @@ public partial class MapLogic : Shared.Models.Methods.IMapLogic
|
||||
List<int> distinctCollection = [];
|
||||
bool usePersonKeyAndDeterministicHashCodeKey = false;
|
||||
List<string> personKeyFormattedCollection = GetPersonKeyFormattedCollection(jLinks, a2PeopleContentDirectory, personContainers, personKeyToIds);
|
||||
List<(int Id, FileHolder ImageFileHolder, int ApproximateYears, string PersonKeyFormatted, string CheckFile, string Directory, string PersonDirectory)> collection = [];
|
||||
List<(int Id, FilePath FilePath, int ApproximateYears, string PersonKeyFormatted, string CheckFile, string Directory, string PersonDirectory)> collection = [];
|
||||
foreach (Mapping mapping in mappingCollection)
|
||||
{
|
||||
if (distinctCollection.Contains(mapping.MappingFromItem.Id))
|
||||
@ -1089,15 +1089,15 @@ public partial class MapLogic : Shared.Models.Methods.IMapLogic
|
||||
}
|
||||
directory = Path.Combine(_EDistanceContentTicksDirectory, ((char)group).ToString());
|
||||
personDirectory = Path.Combine(directory, mapping.MappingFromPerson.DisplayDirectoryName);
|
||||
checkFile = Path.Combine(directory, $"{mapping.MappingFromItem.Id}{mapping.MappingFromItem.ImageFileHolder.ExtensionLowered}");
|
||||
checkFile = Path.Combine(directory, $"{mapping.MappingFromItem.Id}{mapping.MappingFromItem.FilePath.ExtensionLowered}");
|
||||
}
|
||||
else
|
||||
{
|
||||
directory = Path.Combine(_EDistanceContentTicksDirectory, "Images", personKeyFormatted);
|
||||
personDirectory = Path.Combine(directory, mapping.MappingFromPerson.DisplayDirectoryName);
|
||||
checkFile = Path.Combine(directory, $"{mapping.MappingFromLocation.DeterministicHashCodeKey}{mapping.MappingFromItem.ImageFileHolder.ExtensionLowered}");
|
||||
checkFile = Path.Combine(directory, $"{mapping.MappingFromLocation.DeterministicHashCodeKey}{mapping.MappingFromItem.FilePath.ExtensionLowered}");
|
||||
}
|
||||
collection.Add(new(mapping.MappingFromItem.Id, mapping.MappingFromItem.ImageFileHolder, mapping.MappingFromPerson.ApproximateYears.Value, personKeyFormatted, directory, personDirectory, checkFile));
|
||||
collection.Add(new(mapping.MappingFromItem.Id, mapping.MappingFromItem.FilePath, mapping.MappingFromPerson.ApproximateYears.Value, personKeyFormatted, directory, personDirectory, checkFile));
|
||||
distinctCollection.Add(mapping.MappingFromItem.Id);
|
||||
count += 1;
|
||||
}
|
||||
@ -1109,14 +1109,16 @@ public partial class MapLogic : Shared.Models.Methods.IMapLogic
|
||||
{
|
||||
if (_Configuration is null)
|
||||
throw new NullReferenceException(nameof(_Configuration));
|
||||
FileHolder fileHolder;
|
||||
SaveContainer? saveContainer;
|
||||
List<SaveContainer> saveContainers = [];
|
||||
(int, FileHolder, int, string, string, string, string)[] collection = GetCollectionForSaveFilteredOriginalImagesFromJLinks(jLinks, a2PeopleContentDirectory, personContainers, mappingCollection, personKeyToIds);
|
||||
foreach ((int id, FileHolder imageFileHolder, int approximateYears, string personKeyFormatted, string directory, string personDirectory, string checkFile) in collection)
|
||||
(int, FilePath, int, string, string, string, string)[] collection = GetCollectionForSaveFilteredOriginalImagesFromJLinks(jLinks, a2PeopleContentDirectory, personContainers, mappingCollection, personKeyToIds);
|
||||
foreach ((int id, FilePath filePath, int approximateYears, string personKeyFormatted, string directory, string personDirectory, string checkFile) in collection)
|
||||
{
|
||||
fileHolder = FileHolder.Get(filePath);
|
||||
saveContainer = new(personDirectory);
|
||||
saveContainers.Add(saveContainer);
|
||||
saveContainer = new(imageFileHolder, checkFile, directory);
|
||||
saveContainer = new(fileHolder, checkFile, directory);
|
||||
saveContainers.Add(saveContainer);
|
||||
}
|
||||
SaveContainers(null, saveContainers);
|
||||
@ -1189,12 +1191,12 @@ public partial class MapLogic : Shared.Models.Methods.IMapLogic
|
||||
directoryName = Path.GetDirectoryName(face.Mapping.MappingFromItem.RelativePath);
|
||||
if (directoryName is null)
|
||||
throw new NotSupportedException();
|
||||
if (item.ResizedFileHolder?.DirectoryName is null || !item.ResizedFileHolder.Exists || item.ImageFileHolder.LastWriteTime is null)
|
||||
if (item.ResizedFileHolder?.DirectoryName is null || !item.ResizedFileHolder.Exists)
|
||||
continue;
|
||||
directory = Path.Combine(item.ResizedFileHolder.DirectoryName, $"{_PropertyConfiguration.ResultAllInOne}Shortcuts", _PropertyConfiguration.ResultAllInOne);
|
||||
personDirectory = Path.Combine(directory, "No Faces");
|
||||
fileName = Path.Combine(personDirectory, $"{item.ResizedFileHolder.Name}.lnk");
|
||||
collection.Add(new(item.ResizedFileHolder.FullName, personDirectory, item.ImageFileHolder.LastWriteTime.Value, fileName, face.Mapping.MappingFromItem.Id.ToString(), MakeAllHidden: false));
|
||||
collection.Add(new(item.ResizedFileHolder.FullName, personDirectory, new(item.FilePath.LastWriteTicks), fileName, face.Mapping.MappingFromItem.Id.ToString(), MakeAllHidden: false));
|
||||
if (face.Mapping.MappingFromItem.ContainerDateTimes.Length > 0 && !distinct.Contains(item.ResizedFileHolder.DirectoryName))
|
||||
{
|
||||
distinct.Add(item.ResizedFileHolder.DirectoryName);
|
||||
@ -1223,7 +1225,7 @@ public partial class MapLogic : Shared.Models.Methods.IMapLogic
|
||||
facesDirectory = Stateless.MapLogic.GetFacesDirectory(_PropertyConfiguration, dFacesContentDirectory, mapping.FilePath, mapping.MappingFromItem);
|
||||
if (mapping.MappingFromLocation is null)
|
||||
continue;
|
||||
fullName = Path.Combine(facesDirectory, $"{mapping.MappingFromLocation.DeterministicHashCodeKey}{mapping.MappingFromItem.ImageFileHolder.ExtensionLowered}{_Configuration.FacesFileNameExtension}");
|
||||
fullName = Path.Combine(facesDirectory, $"{mapping.MappingFromLocation.DeterministicHashCodeKey}{mapping.MappingFromItem.FilePath.ExtensionLowered}{_Configuration.FacesFileNameExtension}");
|
||||
fileName = Path.Combine(personDirectory, $"{mapping.MappingFromLocation.DeterministicHashCodeKey}{mapping.MappingFromItem.ResizedFileHolder.ExtensionLowered}{_Configuration.FacesFileNameExtension}.lnk");
|
||||
collection.Add(new(fullName, personDirectory, mapping.MappingFromItem.GetDateTimeOriginalThenMinimumDateTime(), fileName, mapping.MappingFromLocation.DeterministicHashCodeKey, MakeAllHidden: true));
|
||||
}
|
||||
|
@ -235,7 +235,7 @@ internal abstract class MapLogic
|
||||
{
|
||||
string result;
|
||||
(string directoryName, _) = IPath.GetDirectoryNameAndIndex(propertyConfiguration, filePath);
|
||||
result = Path.Combine(dFacesContentDirectory, directoryName, mappingFromItem.ImageFileHolder.NameWithoutExtension);
|
||||
result = Path.Combine(dFacesContentDirectory, directoryName, mappingFromItem.FilePath.NameWithoutExtension);
|
||||
return result;
|
||||
}
|
||||
|
||||
@ -605,16 +605,16 @@ internal abstract class MapLogic
|
||||
result = null;
|
||||
else
|
||||
{
|
||||
string checkFile = Path.Combine(directory, $"{keyMapping.MappingFromItem.ImageFileHolder.Name}{facePartsFileNameExtension}");
|
||||
string checkFile = Path.Combine(directory, $"{keyMapping.MappingFromItem.FilePath.Name}{facePartsFileNameExtension}");
|
||||
result = new(checkFile, directory, IFileHolder.Get(facePartsContentCollectionFile));
|
||||
}
|
||||
string facesDirectory = GetFacesDirectory(propertyConfiguration, dFacesContentDirectory, keyMapping.FilePath, keyMapping.MappingFromItem);
|
||||
FileHolder faceFileHolder = IFileHolder.Get(Path.Combine(facesDirectory, $"{keyMapping.MappingFromLocation.DeterministicHashCodeKey}{keyMapping.MappingFromItem.ImageFileHolder.ExtensionLowered}{facesFileNameExtension}"));
|
||||
FileHolder faceFileHolder = IFileHolder.Get(Path.Combine(facesDirectory, $"{keyMapping.MappingFromLocation.DeterministicHashCodeKey}{keyMapping.MappingFromItem.FilePath.ExtensionLowered}{facesFileNameExtension}"));
|
||||
if (!faceFileHolder.Exists)
|
||||
saveContainer = null;
|
||||
else
|
||||
{
|
||||
string checkFile = Path.Combine(directory, $"{keyMapping.MappingFromLocation.DeterministicHashCodeKey}{keyMapping.MappingFromItem.ImageFileHolder.ExtensionLowered}{facesFileNameExtension}");
|
||||
string checkFile = Path.Combine(directory, $"{keyMapping.MappingFromLocation.DeterministicHashCodeKey}{keyMapping.MappingFromItem.FilePath.ExtensionLowered}{facesFileNameExtension}");
|
||||
saveContainer = new(checkFile, directory, faceFileHolder);
|
||||
}
|
||||
}
|
||||
@ -975,7 +975,7 @@ internal abstract class MapLogic
|
||||
if (directoryName is null)
|
||||
result = null;
|
||||
else
|
||||
result = Path.Combine($"{d2FacePartsContentCollectionDirectory}{directoryName}", $"{mappingFromItem.ImageFileHolder.Name}{extension}");
|
||||
result = Path.Combine($"{d2FacePartsContentCollectionDirectory}{directoryName}", $"{mappingFromItem.FilePath.Name}{extension}");
|
||||
return result;
|
||||
}
|
||||
|
||||
@ -983,7 +983,7 @@ internal abstract class MapLogic
|
||||
{
|
||||
string result;
|
||||
(string directoryName, _) = IPath.GetDirectoryNameAndIndex(propertyConfiguration, filePath);
|
||||
result = Path.Combine(d2FacePartsContentDirectory, directoryName, mappingFromItem.ImageFileHolder.NameWithoutExtension);
|
||||
result = Path.Combine(d2FacePartsContentDirectory, directoryName, mappingFromItem.FilePath.NameWithoutExtension);
|
||||
return result;
|
||||
}
|
||||
|
||||
@ -995,9 +995,9 @@ internal abstract class MapLogic
|
||||
throw new NullReferenceException(nameof(sortingContainer.Source.MappingFromLocation));
|
||||
FileHolder faceFileHolder = IFileHolder.Get($"C:/{sortingContainer.Sorting.Id}.{sortingContainer.Sorting.WholePercentages}");
|
||||
if (keyMapping.MappingFromPerson is not null && keyMapping.MappingFromLocation is not null)
|
||||
shortcutFile = Path.Combine(directory, $"{keyMapping.MappingFromLocation.DeterministicHashCodeKey}{keyMapping.MappingFromItem.ImageFileHolder.ExtensionLowered}.{sortingContainer.Sorting.DistancePermyriad}.lnk");
|
||||
shortcutFile = Path.Combine(directory, $"{keyMapping.MappingFromLocation.DeterministicHashCodeKey}{keyMapping.MappingFromItem.FilePath.ExtensionLowered}.{sortingContainer.Sorting.DistancePermyriad}.lnk");
|
||||
else
|
||||
shortcutFile = Path.Combine(directory, $"{sortingContainer.Source.MappingFromLocation.DeterministicHashCodeKey}{sortingContainer.Source.MappingFromItem.ImageFileHolder.ExtensionLowered}.{sortingContainer.Sorting.DistancePermyriad}.lnk");
|
||||
shortcutFile = Path.Combine(directory, $"{sortingContainer.Source.MappingFromLocation.DeterministicHashCodeKey}{sortingContainer.Source.MappingFromItem.FilePath.ExtensionLowered}.{sortingContainer.Sorting.DistancePermyriad}.lnk");
|
||||
result = new(directory, faceFileHolder, sortingContainer.Source.MappingFromItem.ResizedFileHolder, shortcutFile);
|
||||
return result;
|
||||
}
|
||||
@ -1008,9 +1008,9 @@ internal abstract class MapLogic
|
||||
SaveContainer? saveContainer;
|
||||
if (mapping.MappingFromLocation is null)
|
||||
throw new NullReferenceException(nameof(mapping.MappingFromLocation));
|
||||
checkFile = Path.Combine(directory, $"{mapping.MappingFromItem.ImageFileHolder.Name}{facePartsFileNameExtension}");
|
||||
checkFile = Path.Combine(directory, $"{mapping.MappingFromItem.FilePath.Name}{facePartsFileNameExtension}");
|
||||
saveContainer = !facePartsFileHolder.Exists ? null : new(checkFile, directory, facePartsFileHolder);
|
||||
checkFile = Path.Combine(directory, $"{mapping.MappingFromLocation.DeterministicHashCodeKey}{mapping.MappingFromItem.ImageFileHolder.ExtensionLowered}{facesFileNameExtension}");
|
||||
checkFile = Path.Combine(directory, $"{mapping.MappingFromLocation.DeterministicHashCodeKey}{mapping.MappingFromItem.FilePath.ExtensionLowered}{facesFileNameExtension}");
|
||||
return (new(checkFile, directory, faceFileHolder), saveContainer);
|
||||
}
|
||||
|
||||
|
@ -48,7 +48,7 @@ public class B_Metadata : IMetadata<MetadataExtractor.Directory>
|
||||
ExifDirectory? result = null;
|
||||
List<DateTime> dateTimes = (from l in subFileTuples where changesFrom.Contains(l.Item1) select l.Item2).ToList();
|
||||
(_, int directoryIndex) = Shared.Models.Stateless.Methods.IPath.GetDirectoryNameAndIndex(_PropertyConfiguration, filePath);
|
||||
FileInfo fileInfo = new(Path.Combine(_FileGroups[_PropertyConfiguration.ResultSingleton][directoryIndex], $"{mappingFromItem.ImageFileHolder.NameWithoutExtension}{mappingFromItem.ImageFileHolder.ExtensionLowered}.json"));
|
||||
FileInfo fileInfo = new(Path.Combine(_FileGroups[_PropertyConfiguration.ResultSingleton][directoryIndex], $"{mappingFromItem.FilePath.NameWithoutExtension}{mappingFromItem.FilePath.ExtensionLowered}.json"));
|
||||
if (_ForceMetadataLastWriteTimeToCreationTime && !fileInfo.Exists && File.Exists(Path.ChangeExtension(fileInfo.FullName, ".delete")))
|
||||
{
|
||||
File.Move(Path.ChangeExtension(fileInfo.FullName, ".delete"), fileInfo.FullName);
|
||||
@ -104,7 +104,7 @@ public class B_Metadata : IMetadata<MetadataExtractor.Directory>
|
||||
return result;
|
||||
}
|
||||
|
||||
(DateTime?, DateTime?[]) IMetadata<MetadataExtractor.Directory>.GetDateTimes(FileHolder fileHolder, IReadOnlyList<MetadataExtractor.Directory> directories)
|
||||
(DateTime?, DateTime?[]) IMetadata<MetadataExtractor.Directory>.GetDateTimes(FilePath filePath, IReadOnlyList<MetadataExtractor.Directory> directories)
|
||||
{
|
||||
List<DateTime?> results = [];
|
||||
DateTime? result = null;
|
||||
@ -112,8 +112,8 @@ public class B_Metadata : IMetadata<MetadataExtractor.Directory>
|
||||
DateTime checkDateTime;
|
||||
string dateTimeFormat = Property.Models.Stateless.IProperty.DateTimeFormat();
|
||||
MetadataExtractor.Formats.Exif.ExifDirectoryBase? exifDirectoryBase = directories.OfType<MetadataExtractor.Formats.Exif.ExifDirectoryBase>().FirstOrDefault();
|
||||
results.Add(fileHolder.CreationTime);
|
||||
results.Add(fileHolder.LastWriteTime);
|
||||
results.Add(new DateTime(filePath.CreationTicks));
|
||||
results.Add(new DateTime(filePath.LastWriteTicks));
|
||||
if (exifDirectoryBase is not null)
|
||||
{
|
||||
if (exifDirectoryBase.TryGetDateTime(MetadataExtractor.Formats.Exif.ExifDirectoryBase.TagDateTime, out checkDateTime))
|
||||
|
@ -128,7 +128,7 @@ public class MoveById
|
||||
if (filePath.IsIntelligentIdFormat || filePath.SortOrder is not null)
|
||||
continue;
|
||||
}
|
||||
(_, _, id, message) = Property.Models.Stateless.IProperty.Get(_PropertyConfiguration.PopulatePropertyId, fileHolder, isIgnoreExtension, isValidImageFormatExtension, asciiEncoding);
|
||||
(_, _, id, message) = Property.Models.Stateless.IProperty.Get(_PropertyConfiguration, _PropertyConfiguration.PopulatePropertyId, fileHolder, isIgnoreExtension, isValidImageFormatExtension, asciiEncoding);
|
||||
if (id is null)
|
||||
continue;
|
||||
matches = (from l in allFiles where l.Contains($"{id}{fileHolder.ExtensionLowered}") select l).ToArray();
|
||||
|
@ -85,7 +85,7 @@ public class OffsetDateTimeOriginal
|
||||
fileHolder = Shared.Models.Stateless.Methods.IFileHolder.Get(file);
|
||||
isValidImageFormatExtension = _PropertyConfiguration.ValidImageFormatExtensions.Contains(fileHolder.ExtensionLowered);
|
||||
isIgnoreExtension = isValidImageFormatExtension && _PropertyConfiguration.IgnoreExtensions.Contains(fileHolder.ExtensionLowered);
|
||||
(dateTimeOriginal, dateTimes, id, message) = Property.Models.Stateless.IProperty.Get(_PropertyConfiguration.PopulatePropertyId, fileHolder, isIgnoreExtension, isValidImageFormatExtension, asciiEncoding);
|
||||
(dateTimeOriginal, dateTimes, id, message) = Property.Models.Stateless.IProperty.Get(_PropertyConfiguration, _PropertyConfiguration.PopulatePropertyId, fileHolder, isIgnoreExtension, isValidImageFormatExtension, asciiEncoding);
|
||||
if (message is not null)
|
||||
throw new Exception(message);
|
||||
if (id is null || dateTimeOriginal is null)
|
||||
@ -141,7 +141,7 @@ public class OffsetDateTimeOriginal
|
||||
bitmap.SetPropertyItem(propertyItem);
|
||||
bitmap.Save(checkFile);
|
||||
bitmap.Dispose();
|
||||
(_, _, id, message) = Property.Models.Stateless.IProperty.Get(_PropertyConfiguration.PopulatePropertyId, record.FileHolder, record.IsIgnoreExtension, record.IsValidImageFormatExtension, asciiEncoding);
|
||||
(_, _, id, message) = Property.Models.Stateless.IProperty.Get(_PropertyConfiguration, _PropertyConfiguration.PopulatePropertyId, record.FileHolder, record.IsIgnoreExtension, record.IsValidImageFormatExtension, asciiEncoding);
|
||||
if (message is not null)
|
||||
throw new Exception(message);
|
||||
if (id is null || id.Value != record.Id)
|
||||
@ -200,12 +200,12 @@ public class OffsetDateTimeOriginal
|
||||
targetIsIgnoreExtension = targetIsValidImageFormatExtension && _PropertyConfiguration.IgnoreExtensions.Contains(targetFileHolder.ExtensionLowered);
|
||||
DateTime minimumDateTime = DateTime.ParseExact(Path.GetFileName(minimumDirectory.First()), format, CultureInfo.InvariantCulture, DateTimeStyles.None);
|
||||
DateTime maximumDateTime = DateTime.ParseExact(Path.GetFileName(maximumDirectory.First()), format, CultureInfo.InvariantCulture, DateTimeStyles.None).AddHours(23);
|
||||
(badDateTimeOriginal, badDateTimes, badId, badMessage) = Property.Models.Stateless.IProperty.Get(_PropertyConfiguration.PopulatePropertyId, badFileHolder, badIsIgnoreExtension, badIsValidImageFormatExtension, asciiEncoding);
|
||||
(badDateTimeOriginal, badDateTimes, badId, badMessage) = Property.Models.Stateless.IProperty.Get(_PropertyConfiguration, _PropertyConfiguration.PopulatePropertyId, badFileHolder, badIsIgnoreExtension, badIsValidImageFormatExtension, asciiEncoding);
|
||||
if (badMessage is not null)
|
||||
throw new Exception(badMessage);
|
||||
if (badDateTimes.Length == 0 || badId is null)
|
||||
throw new Exception(badMessage);
|
||||
(targetDateTimeOriginal, targetDateTimes, targetId, targetMessage) = Property.Models.Stateless.IProperty.Get(_PropertyConfiguration.PopulatePropertyId, targetFileHolder, targetIsIgnoreExtension, targetIsValidImageFormatExtension, asciiEncoding);
|
||||
(targetDateTimeOriginal, targetDateTimes, targetId, targetMessage) = Property.Models.Stateless.IProperty.Get(_PropertyConfiguration, _PropertyConfiguration.PopulatePropertyId, targetFileHolder, targetIsIgnoreExtension, targetIsValidImageFormatExtension, asciiEncoding);
|
||||
if (targetMessage is not null)
|
||||
throw new Exception(targetMessage);
|
||||
if (targetDateTimes.Length == 0 || targetId is null)
|
||||
|
@ -54,11 +54,11 @@ public class A_Property
|
||||
string angleBracket = _AngleBracketCollection[0];
|
||||
bool populateId = _Configuration.PopulatePropertyId;
|
||||
if (!item.IsUniqueFileName)
|
||||
fileInfo = new(Path.Combine(angleBracket.Replace("<>", _PropertyConfiguration.ResultSingleton), $"{item.ImageFileHolder.NameWithoutExtension}{item.ImageFileHolder.ExtensionLowered}.json"));
|
||||
fileInfo = new(Path.Combine(angleBracket.Replace("<>", _PropertyConfiguration.ResultSingleton), $"{item.FilePath.NameWithoutExtension}{item.FilePath.ExtensionLowered}.json"));
|
||||
else
|
||||
{
|
||||
(_, int directoryIndex) = Shared.Models.Stateless.Methods.IPath.GetDirectoryNameAndIndex(_PropertyConfiguration, item.FilePath);
|
||||
fileInfo = new(Path.Combine(_FileGroups[_PropertyConfiguration.ResultSingleton][directoryIndex], $"{item.ImageFileHolder.NameWithoutExtension}{item.ImageFileHolder.ExtensionLowered}.json"));
|
||||
fileInfo = new(Path.Combine(_FileGroups[_PropertyConfiguration.ResultSingleton][directoryIndex], $"{item.FilePath.NameWithoutExtension}{item.FilePath.ExtensionLowered}.json"));
|
||||
}
|
||||
List<DateTime> dateTimes = (from l in sourceDirectoryFileTuples where l is not null && changesFrom.Contains(l.Item1) select l.Item2).ToList();
|
||||
if (_Configuration.ForcePropertyLastWriteTimeToCreationTime && !fileInfo.Exists && File.Exists(Path.ChangeExtension(fileInfo.FullName, ".delete")))
|
||||
@ -99,19 +99,19 @@ public class A_Property
|
||||
id = result?.Id;
|
||||
result = null;
|
||||
}
|
||||
if (!isIgnoreExtension && item.IsValidImageFormatExtension && populateId && result is not null && result.LastWriteTime != item.ImageFileHolder.LastWriteTime)
|
||||
if (!isIgnoreExtension && item.IsValidImageFormatExtension && populateId && result is not null && result.LastWriteTime.Ticks != item.FilePath.LastWriteTicks)
|
||||
{
|
||||
id = null;
|
||||
result = null;
|
||||
}
|
||||
if (!isIgnoreExtension && item.IsValidImageFormatExtension && result?.Width is not null && result.Height is not null && result.Width.Value == result.Height.Value && item.ImageFileHolder.Exists)
|
||||
if (!isIgnoreExtension && item.IsValidImageFormatExtension && result?.Width is not null && result.Height is not null && result.Width.Value == result.Height.Value)
|
||||
{
|
||||
id = result.Id;
|
||||
result = null;
|
||||
if (result?.Width is not null && result.Height is not null && result.Width.Value != result.Height.Value)
|
||||
throw new Exception("Was square!");
|
||||
}
|
||||
if (!isIgnoreExtension && item.IsValidImageFormatExtension && result is not null && result.FileSize != item.ImageFileHolder.Length)
|
||||
if (!isIgnoreExtension && item.IsValidImageFormatExtension && result is not null && result.FileSize != item.FilePath.Length)
|
||||
{
|
||||
id = result.Id;
|
||||
result = null;
|
||||
@ -135,7 +135,7 @@ public class A_Property
|
||||
if (result is null)
|
||||
{
|
||||
id ??= item.FilePath.Id;
|
||||
(_, _, result) = Stateless.Property.GetProperty(populateId, metadata, item.ImageFileHolder, result, isIgnoreExtension, item.IsValidImageFormatExtension, id, _ASCIIEncoding);
|
||||
(_, _, result) = Stateless.Property.GetProperty(populateId, metadata, item.FilePath, result, isIgnoreExtension, item.IsValidImageFormatExtension, id, _ASCIIEncoding);
|
||||
json = JsonSerializer.Serialize(result, PropertyGenerationContext.Default.Property);
|
||||
if (populateId && Shared.Models.Stateless.Methods.IPath.WriteAllText(fileInfo.FullName, json, updateDateWhenMatches: true, compareBeforeWrite: true))
|
||||
{
|
||||
@ -183,10 +183,10 @@ public class A_Property
|
||||
{
|
||||
Shared.Models.Property property;
|
||||
List<string> parseExceptions = [];
|
||||
bool isIgnoreExtension = item.IsValidImageFormatExtension && _PropertyConfiguration.IgnoreExtensions.Contains(item.ImageFileHolder.ExtensionLowered);
|
||||
string filteredSourceDirectoryFileExtensionLowered = Path.Combine(sourceDirectory, $"{item.ImageFileHolder.NameWithoutExtension}{item.ImageFileHolder.ExtensionLowered}");
|
||||
if (item.IsValidImageFormatExtension && item.ImageFileHolder.FullName.Length == filteredSourceDirectoryFileExtensionLowered.Length && item.ImageFileHolder.FullName != filteredSourceDirectoryFileExtensionLowered)
|
||||
File.Move(item.ImageFileHolder.FullName, filteredSourceDirectoryFileExtensionLowered);
|
||||
bool isIgnoreExtension = item.IsValidImageFormatExtension && _PropertyConfiguration.IgnoreExtensions.Contains(item.FilePath.ExtensionLowered);
|
||||
string filteredSourceDirectoryFileExtensionLowered = Path.Combine(sourceDirectory, $"{item.FilePath.NameWithoutExtension}{item.FilePath.ExtensionLowered}");
|
||||
if (item.IsValidImageFormatExtension && item.FilePath.FullName.Length == filteredSourceDirectoryFileExtensionLowered.Length && item.FilePath.FullName != filteredSourceDirectoryFileExtensionLowered)
|
||||
File.Move(item.FilePath.FullName, filteredSourceDirectoryFileExtensionLowered);
|
||||
if (item.FileSizeChanged is null || item.FileSizeChanged.Value || item.LastWriteTimeChanged is null || item.LastWriteTimeChanged.Value || item.Property is null)
|
||||
{
|
||||
property = GetImageProperty(metadata, item, sourceDirectoryFileTuples, parseExceptions, isIgnoreExtension);
|
||||
@ -277,11 +277,11 @@ public class A_Property
|
||||
bool angleBracketCollectionAny = _AngleBracketCollection.Count != 0;
|
||||
if (!angleBracketCollectionAny)
|
||||
{
|
||||
if (item.ImageFileHolder.DirectoryName is null)
|
||||
throw new NullReferenceException(nameof(item.ImageFileHolder.DirectoryName));
|
||||
SetAngleBracketCollection(item.ImageFileHolder.DirectoryName, !item.IsUniqueFileName);
|
||||
if (item.FilePath.DirectoryName is null)
|
||||
throw new NullReferenceException(nameof(item.FilePath.DirectoryName));
|
||||
SetAngleBracketCollection(item.FilePath.DirectoryName, !item.IsUniqueFileName);
|
||||
}
|
||||
bool isIgnoreExtension = item.IsValidImageFormatExtension && _PropertyConfiguration.IgnoreExtensions.Contains(item.ImageFileHolder.ExtensionLowered);
|
||||
bool isIgnoreExtension = item.IsValidImageFormatExtension && _PropertyConfiguration.IgnoreExtensions.Contains(item.FilePath.ExtensionLowered);
|
||||
result = GetImageProperty(metadata, item, sourceDirectoryFileTuples, parseExceptions, isIgnoreExtension);
|
||||
if (!angleBracketCollectionAny)
|
||||
_AngleBracketCollection.Clear();
|
||||
|
@ -1,7 +1,9 @@
|
||||
using System.Drawing.Imaging;
|
||||
using System.Reflection;
|
||||
using System.Text;
|
||||
using View_by_Distance.Shared.Models;
|
||||
using View_by_Distance.Shared.Models.Methods;
|
||||
using View_by_Distance.Shared.Models.Properties;
|
||||
|
||||
namespace View_by_Distance.Property.Models.Stateless;
|
||||
|
||||
@ -28,19 +30,29 @@ public interface IProperty
|
||||
static PropertyItem GetPropertyItem(ConstructorInfo constructorInfo, int id, short type, string value) =>
|
||||
Property.GetPropertyItem(constructorInfo, id, type, value);
|
||||
|
||||
(string?, DateTime[], Shared.Models.Property) TestStatic_GetProperty(bool populateId, IMetadata<MetadataExtractor.Directory>? metadata, Shared.Models.FileHolder fileHolder, Shared.Models.Property? property, bool isIgnoreExtension, bool isValidImageFormatExtension, int? id, ASCIIEncoding asciiEncoding) =>
|
||||
GetProperty(populateId, metadata, fileHolder, property, isIgnoreExtension, isValidImageFormatExtension, id, asciiEncoding);
|
||||
static (string?, DateTime[], Shared.Models.Property) GetProperty(bool populateId, IMetadata<MetadataExtractor.Directory>? metadata, Shared.Models.FileHolder fileHolder, Shared.Models.Property? property, bool isIgnoreExtension, bool isValidImageFormatExtension, int? id, ASCIIEncoding asciiEncoding) =>
|
||||
Property.GetProperty(populateId, metadata, fileHolder, property, isIgnoreExtension, isValidImageFormatExtension, id, asciiEncoding);
|
||||
(string?, DateTime[], Shared.Models.Property) TestStatic_GetProperty(bool populateId, IMetadata<MetadataExtractor.Directory>? metadata, FilePath filePath, Shared.Models.Property? property, bool isIgnoreExtension, bool isValidImageFormatExtension, int? id, ASCIIEncoding asciiEncoding) =>
|
||||
GetProperty(populateId, metadata, filePath, property, isIgnoreExtension, isValidImageFormatExtension, id, asciiEncoding);
|
||||
static (string?, DateTime[], Shared.Models.Property) GetProperty(bool populateId, IMetadata<MetadataExtractor.Directory>? metadata, FilePath filePath, Shared.Models.Property? property, bool isIgnoreExtension, bool isValidImageFormatExtension, int? id, ASCIIEncoding asciiEncoding) =>
|
||||
Property.GetProperty(populateId, metadata, filePath, property, isIgnoreExtension, isValidImageFormatExtension, id, asciiEncoding);
|
||||
|
||||
(DateTime?, DateTime[], int?, string?) TestStatic_Get(bool populateId, Shared.Models.FileHolder fileHolder, bool isIgnoreExtension, bool isValidImageFormatExtension, ASCIIEncoding asciiEncoding) =>
|
||||
Get(populateId, fileHolder, isIgnoreExtension, isValidImageFormatExtension, asciiEncoding);
|
||||
static (DateTime?, DateTime[], int?, string?) Get(bool populateId, Shared.Models.FileHolder fileHolder, bool isIgnoreExtension, bool isValidImageFormatExtension, ASCIIEncoding asciiEncoding) =>
|
||||
Property.Get(populateId, null, fileHolder, isIgnoreExtension, isValidImageFormatExtension, asciiEncoding);
|
||||
(DateTime?, DateTime[], int?, string?) TestStatic_Get(IPropertyConfiguration propertyConfiguration, bool populateId, FileHolder fileHolder, bool isIgnoreExtension, bool isValidImageFormatExtension, ASCIIEncoding asciiEncoding) =>
|
||||
Get(propertyConfiguration, populateId, fileHolder, isIgnoreExtension, isValidImageFormatExtension, asciiEncoding);
|
||||
static (DateTime?, DateTime[], int?, string?) Get(IPropertyConfiguration propertyConfiguration, bool populateId, FileHolder fileHolder, bool isIgnoreExtension, bool isValidImageFormatExtension, ASCIIEncoding asciiEncoding) =>
|
||||
Property.Get(populateId, null, FilePath.Get(propertyConfiguration, fileHolder, index: null), isIgnoreExtension, isValidImageFormatExtension, asciiEncoding);
|
||||
|
||||
(DateTime?, DateTime[], int?, string?) TestStatic_Get(bool populateId, IMetadata<MetadataExtractor.Directory>? metadata, Shared.Models.FileHolder fileHolder, bool isIgnoreExtension, bool isValidImageFormatExtension, ASCIIEncoding asciiEncoding) =>
|
||||
Get(populateId, metadata, fileHolder, isIgnoreExtension, isValidImageFormatExtension, asciiEncoding);
|
||||
static (DateTime?, DateTime[], int?, string?) Get(bool populateId, IMetadata<MetadataExtractor.Directory>? metadata, Shared.Models.FileHolder fileHolder, bool isIgnoreExtension, bool isValidImageFormatExtension, ASCIIEncoding asciiEncoding) =>
|
||||
Property.Get(populateId, metadata, fileHolder, isIgnoreExtension, isValidImageFormatExtension, asciiEncoding);
|
||||
(DateTime?, DateTime[], int?, string?) TestStatic_Get(bool populateId, FilePath filePath, bool isIgnoreExtension, bool isValidImageFormatExtension, ASCIIEncoding asciiEncoding) =>
|
||||
Get(populateId, filePath, isIgnoreExtension, isValidImageFormatExtension, asciiEncoding);
|
||||
static (DateTime?, DateTime[], int?, string?) Get(bool populateId, FilePath filePath, bool isIgnoreExtension, bool isValidImageFormatExtension, ASCIIEncoding asciiEncoding) =>
|
||||
Property.Get(populateId, null, filePath, isIgnoreExtension, isValidImageFormatExtension, asciiEncoding);
|
||||
|
||||
(DateTime?, DateTime[], int?, string?) TestStatic_Get(bool populateId, IMetadata<MetadataExtractor.Directory>? metadata, FilePath filePath, bool isIgnoreExtension, bool isValidImageFormatExtension, ASCIIEncoding asciiEncoding) =>
|
||||
Get(populateId, metadata, filePath, isIgnoreExtension, isValidImageFormatExtension, asciiEncoding);
|
||||
static (DateTime?, DateTime[], int?, string?) Get(bool populateId, IMetadata<MetadataExtractor.Directory>? metadata, FilePath filePath, bool isIgnoreExtension, bool isValidImageFormatExtension, ASCIIEncoding asciiEncoding) =>
|
||||
Property.Get(populateId, metadata, filePath, isIgnoreExtension, isValidImageFormatExtension, asciiEncoding);
|
||||
|
||||
(DateTime?, DateTime[], int?, string?) TestStatic_Get(IPropertyConfiguration propertyConfiguration, bool populateId, IMetadata<MetadataExtractor.Directory>? metadata, FileHolder fileHolder, bool isIgnoreExtension, bool isValidImageFormatExtension, ASCIIEncoding asciiEncoding) =>
|
||||
Get(propertyConfiguration, populateId, metadata, fileHolder, isIgnoreExtension, isValidImageFormatExtension, asciiEncoding);
|
||||
static (DateTime?, DateTime[], int?, string?) Get(IPropertyConfiguration propertyConfiguration, bool populateId, IMetadata<MetadataExtractor.Directory>? metadata, FileHolder fileHolder, bool isIgnoreExtension, bool isValidImageFormatExtension, ASCIIEncoding asciiEncoding) =>
|
||||
Property.Get(populateId, metadata, FilePath.Get(propertyConfiguration, fileHolder, index: null), isIgnoreExtension, isValidImageFormatExtension, asciiEncoding);
|
||||
|
||||
}
|
@ -47,10 +47,10 @@ internal partial class Property
|
||||
return results;
|
||||
}
|
||||
|
||||
private static List<DateTime> GetDateTimes(FileHolder fileHolder, DateTime?[] dateTimes)
|
||||
private static List<DateTime> GetDateTimes(FilePath filePath, DateTime?[] dateTimes)
|
||||
{
|
||||
List<DateTime> results = [];
|
||||
string[] digits = Digit().Split(fileHolder.FullName);
|
||||
string[] digits = Digit().Split(filePath.FullName);
|
||||
foreach (string digit in digits)
|
||||
{
|
||||
if (digit.Length != 4 || digit[..2] is not "19" and not "20" || !int.TryParse(digit, out int year))
|
||||
@ -75,7 +75,7 @@ internal partial class Property
|
||||
return results;
|
||||
}
|
||||
|
||||
internal static DateTime? GetDateTimeFromName(FileHolder fileHolder)
|
||||
internal static DateTime? GetDateTimeFromName(FilePath filePath)
|
||||
{
|
||||
DateTime? result = null;
|
||||
int length;
|
||||
@ -90,7 +90,7 @@ internal partial class Property
|
||||
[string.Empty, "yyyyMMdd_", ticksExample],
|
||||
[string.Empty, "yyyy-MM-dd_", ticksExample],
|
||||
[string.Empty, "yyyy-MM-dd.", ticksExample],
|
||||
[string.Empty, "yyyy-MM-dd.", $"{ticksExample}.{fileHolder.Length}"],
|
||||
[string.Empty, "yyyy-MM-dd.", $"{ticksExample}.{filePath.Length}"],
|
||||
[string.Empty, "yyyy-MM-dd HH.mm.ss", string.Empty],
|
||||
[string.Empty, "yyyyMMdd_HHmmss", "_LLS"],
|
||||
[string.Empty, "yyyyMMdd_HHmmss", "_HDR"],
|
||||
@ -106,17 +106,17 @@ internal partial class Property
|
||||
if (dateFormat.Length != 3)
|
||||
throw new Exception();
|
||||
fullFormat = string.Join(string.Empty, dateFormat);
|
||||
if (fileHolder.NameWithoutExtension.Length != fullFormat.Length)
|
||||
if (filePath.NameWithoutExtension.Length != fullFormat.Length)
|
||||
continue;
|
||||
format = dateFormat[1];
|
||||
length = dateFormat[0].Length + dateFormat[1].Length;
|
||||
for (int i = dateFormat[0].Length; i < length; i++)
|
||||
_ = value.Append(fileHolder.NameWithoutExtension[i]);
|
||||
_ = value.Append(filePath.NameWithoutExtension[i]);
|
||||
if (value.Length != format.Length)
|
||||
continue;
|
||||
if (DateTime.TryParseExact(value.ToString(), format, CultureInfo.InvariantCulture, DateTimeStyles.None, out DateTime checkDateTime))
|
||||
{
|
||||
if (fileHolder.NameWithoutExtension.Length < ticksExample.Length || !long.TryParse(fileHolder.NameWithoutExtension[^ticksExample.Length..], out long ticks))
|
||||
if (filePath.NameWithoutExtension.Length < ticksExample.Length || !long.TryParse(filePath.NameWithoutExtension[^ticksExample.Length..], out long ticks))
|
||||
result = checkDateTime;
|
||||
else
|
||||
result = new DateTime(ticks);
|
||||
@ -183,12 +183,11 @@ internal partial class Property
|
||||
|
||||
#pragma warning disable CA1416
|
||||
|
||||
internal static (string?, DateTime[], Shared.Models.Property) GetProperty(bool populateId, IMetadata<MetadataExtractor.Directory>? metadata, FileHolder fileHolder, Shared.Models.Property? property, bool isIgnoreExtension, bool isValidImageFormatExtension, int? id, ASCIIEncoding asciiEncoding)
|
||||
internal static (string?, DateTime[], Shared.Models.Property) GetProperty(bool populateId, IMetadata<MetadataExtractor.Directory>? metadata, FilePath filePath, Shared.Models.Property? property, bool isIgnoreExtension, bool isValidImageFormatExtension, int? id, ASCIIEncoding asciiEncoding)
|
||||
{
|
||||
Shared.Models.Property result;
|
||||
byte[] bytes;
|
||||
string value;
|
||||
long fileLength;
|
||||
string? message;
|
||||
int? width = null;
|
||||
int? height = null;
|
||||
@ -206,27 +205,27 @@ internal partial class Property
|
||||
DateTime? dateTimeOriginal = null;
|
||||
DateTime? dateTimeDigitized = null;
|
||||
DateTime? dateTimeOriginalByLogic = null;
|
||||
DateTime? dateTimeFromName = GetDateTimeFromName(fileHolder);
|
||||
if (!isValidImageFormatExtension && fileHolder.Exists && metadata is not null)
|
||||
DateTime? dateTimeFromName = GetDateTimeFromName(filePath);
|
||||
if (!isValidImageFormatExtension && metadata is not null)
|
||||
{
|
||||
try
|
||||
{
|
||||
IReadOnlyList<MetadataExtractor.Directory> directories = MetadataExtractor.ImageMetadataReader.ReadMetadata(fileHolder.FullName);
|
||||
(dateTimeOriginalByLogic, DateTime?[] metadataDateTimes) = metadata.GetDateTimes(fileHolder, directories);
|
||||
IReadOnlyList<MetadataExtractor.Directory> directories = MetadataExtractor.ImageMetadataReader.ReadMetadata(filePath.FullName);
|
||||
(dateTimeOriginalByLogic, DateTime?[] metadataDateTimes) = metadata.GetDateTimes(filePath, directories);
|
||||
dateTimesByLogic = GetDateTimes(metadataDateTimes);
|
||||
message = null;
|
||||
}
|
||||
catch (Exception)
|
||||
{
|
||||
dateTimesByLogic = [];
|
||||
message = string.Concat(new StackFrame().GetMethod()?.Name, " <", fileHolder.FullName, ">");
|
||||
message = string.Concat(new StackFrame().GetMethod()?.Name, " <", filePath.FullName, ">");
|
||||
}
|
||||
}
|
||||
else if (!isIgnoreExtension && isValidImageFormatExtension && fileHolder.Exists)
|
||||
else if (!isIgnoreExtension && isValidImageFormatExtension)
|
||||
{
|
||||
try
|
||||
{
|
||||
using Image image = Image.FromFile(fileHolder.FullName);
|
||||
using Image image = Image.FromFile(filePath.FullName);
|
||||
width = image.Width;
|
||||
height = image.Height;
|
||||
if (populateId && id is null)
|
||||
@ -320,51 +319,41 @@ internal partial class Property
|
||||
}
|
||||
}
|
||||
message = null;
|
||||
dateTimes = [fileHolder.LastWriteTime, fileHolder.CreationTime, dateTime, dateTimeDigitized, dateTimeOriginal, gpsDateStamp];
|
||||
dateTimes = [new(filePath.LastWriteTicks), new(filePath.CreationTicks), dateTime, dateTimeDigitized, dateTimeOriginal, gpsDateStamp];
|
||||
}
|
||||
catch (Exception)
|
||||
{
|
||||
dateTimes = [];
|
||||
message = string.Concat(new StackFrame().GetMethod()?.Name, " <", fileHolder.FullName, ">");
|
||||
message = string.Concat(new StackFrame().GetMethod()?.Name, " <", filePath.FullName, ">");
|
||||
}
|
||||
if (metadata is not null && dateTimeOriginal is null)
|
||||
{
|
||||
try
|
||||
{
|
||||
IReadOnlyList<MetadataExtractor.Directory> directories = MetadataExtractor.ImageMetadataReader.ReadMetadata(fileHolder.FullName);
|
||||
(dateTimeOriginalByLogic, DateTime?[] metadataDateTimes) = metadata.GetDateTimes(fileHolder, directories);
|
||||
IReadOnlyList<MetadataExtractor.Directory> directories = MetadataExtractor.ImageMetadataReader.ReadMetadata(filePath.FullName);
|
||||
(dateTimeOriginalByLogic, DateTime?[] metadataDateTimes) = metadata.GetDateTimes(filePath, directories);
|
||||
dateTimesByLogic = GetDateTimes(dateTimes, metadataDateTimes);
|
||||
message = null;
|
||||
}
|
||||
catch (Exception) { message = string.Concat(new StackFrame().GetMethod()?.Name, " <", fileHolder.FullName, ">"); }
|
||||
catch (Exception) { message = string.Concat(new StackFrame().GetMethod()?.Name, " <", filePath.FullName, ">"); }
|
||||
}
|
||||
if (dateTimeFromName is null)
|
||||
(dateTimeOriginalByLogic, dateTimesByLogic) = (dateTimeOriginal, GetDateTimes(fileHolder, dateTimes));
|
||||
(dateTimeOriginalByLogic, dateTimesByLogic) = (dateTimeOriginal, GetDateTimes(filePath, dateTimes));
|
||||
else
|
||||
(dateTimeOriginalByLogic, dateTimesByLogic) = (dateTimeOriginal, GetDateTimes(dateTimeFromName.Value, dateTimes));
|
||||
}
|
||||
else
|
||||
(message, dateTimeOriginalByLogic, dateTimesByLogic) = (null, null, []);
|
||||
if (fileHolder.Length is null)
|
||||
fileLength = 0;
|
||||
if (property is not null)
|
||||
result = new(property.CreationTime, dateTime, dateTimeDigitized, dateTimeFromName, dateTimeOriginalByLogic, filePath.Length, gpsDateStamp, height, id, keywords, property.LastWriteTime, make, model, orientation?.ToString(), width);
|
||||
else
|
||||
fileLength = fileHolder.Length.Value;
|
||||
if (fileHolder.CreationTime is null && property?.CreationTime is null)
|
||||
throw new NullReferenceException(nameof(fileHolder.CreationTime));
|
||||
if (fileHolder.LastWriteTime is null && property?.LastWriteTime is null)
|
||||
throw new NullReferenceException(nameof(fileHolder.LastWriteTime));
|
||||
if (fileHolder.CreationTime is not null && fileHolder.LastWriteTime is not null)
|
||||
result = new(fileHolder.CreationTime.Value, dateTime, dateTimeDigitized, dateTimeFromName, dateTimeOriginalByLogic, fileLength, gpsDateStamp, height, id, keywords, fileHolder.LastWriteTime.Value, make, model, orientation?.ToString(), width);
|
||||
else if (property is not null)
|
||||
result = new(property.CreationTime, dateTime, dateTimeDigitized, dateTimeFromName, dateTimeOriginalByLogic, fileLength, gpsDateStamp, height, id, keywords, property.LastWriteTime, make, model, orientation?.ToString(), width);
|
||||
else
|
||||
throw new NullReferenceException(nameof(property));
|
||||
result = new(new(filePath.CreationTicks), dateTime, dateTimeDigitized, dateTimeFromName, dateTimeOriginalByLogic, filePath.Length, gpsDateStamp, height, id, keywords, new(filePath.LastWriteTicks), make, model, orientation?.ToString(), width);
|
||||
return (message, dateTimesByLogic.ToArray(), result);
|
||||
}
|
||||
|
||||
#pragma warning restore CA1416
|
||||
|
||||
internal static (DateTime?, DateTime[], int?, string?) Get(bool populateId, IMetadata<MetadataExtractor.Directory>? metadata, FileHolder fileHolder, bool isIgnoreExtension, bool isValidImageFormatExtension, ASCIIEncoding asciiEncoding)
|
||||
internal static (DateTime?, DateTime[], int?, string?) Get(bool populateId, IMetadata<MetadataExtractor.Directory>? metadata, FilePath filePath, bool isIgnoreExtension, bool isValidImageFormatExtension, ASCIIEncoding asciiEncoding)
|
||||
{
|
||||
int? id = null;
|
||||
string? message;
|
||||
@ -373,7 +362,7 @@ internal partial class Property
|
||||
if (isIgnoreExtension || !isValidImageFormatExtension)
|
||||
(message, dateTimes, property) = (null, [], null);
|
||||
else
|
||||
(message, dateTimes, property) = GetProperty(populateId, metadata, fileHolder, property, isIgnoreExtension, isValidImageFormatExtension, id, asciiEncoding);
|
||||
(message, dateTimes, property) = GetProperty(populateId, metadata, filePath, property, isIgnoreExtension, isValidImageFormatExtension, id, asciiEncoding);
|
||||
return new(property?.DateTimeOriginal, dateTimes, property?.Id, message);
|
||||
}
|
||||
|
||||
|
@ -268,7 +268,7 @@ public class Rename
|
||||
if (fileHolder.DirectoryName is null)
|
||||
continue;
|
||||
}
|
||||
(dateTimeOriginal, dateTimes, id, message) = Property.Models.Stateless.IProperty.Get(_PropertyConfiguration.PopulatePropertyId, metadata, fileHolder, isIgnoreExtension, isValidImageFormatExtension, asciiEncoding);
|
||||
(dateTimeOriginal, dateTimes, id, message) = Property.Models.Stateless.IProperty.Get(_PropertyConfiguration, _PropertyConfiguration.PopulatePropertyId, metadata, fileHolder, isIgnoreExtension, isValidImageFormatExtension, asciiEncoding);
|
||||
if (ffmpegFiles is not null)
|
||||
{
|
||||
fileHolder = Shared.Models.Stateless.Methods.IFileHolder.Get(files[i]);
|
||||
@ -402,7 +402,7 @@ public class Rename
|
||||
{
|
||||
if (record.Id is null)
|
||||
continue;
|
||||
paddedId = IId.GetPaddedId(_PropertyConfiguration, record.Id.Value, record.Index);
|
||||
paddedId = IId.GetPaddedId(_PropertyConfiguration, record.Id.Value, ignore: null, record.Index);
|
||||
checkFileExtension = fileHolder.ExtensionLowered == jpeg ? jpg : fileHolder.ExtensionLowered;
|
||||
checkFile = Path.Combine(seasonDirectory, $"{paddedId}{checkFileExtension}");
|
||||
if (checkFile == fileHolder.FullName)
|
||||
|
@ -193,7 +193,7 @@ public class C_Resize
|
||||
{
|
||||
Bitmap bitmap;
|
||||
int outputResolutionWidth = resize[_OutputResolutionWidthIndex];
|
||||
using Bitmap temp = new(mappingFromItem.ImageFileHolder.FullName, useIcm: false);
|
||||
using Bitmap temp = new(mappingFromItem.FilePath.FullName, useIcm: false);
|
||||
int outputResolutionHeight = resize[_OutputResolutionHeightIndex];
|
||||
PropertyItem[] propertyItems = temp.PropertyItems;
|
||||
int outputResolutionOrientation = resize[_OutputResolutionOrientationIndex];
|
||||
@ -236,7 +236,7 @@ public class C_Resize
|
||||
private void SaveResizedSubfile5(MappingFromItem mappingFromItem, int[] resize, byte[] bytes)
|
||||
{
|
||||
Bitmap bitmap;
|
||||
using Bitmap temp = new(mappingFromItem.ImageFileHolder.FullName, useIcm: false);
|
||||
using Bitmap temp = new(mappingFromItem.FilePath.FullName, useIcm: false);
|
||||
PropertyItem[] propertyItems = temp.PropertyItems;
|
||||
int tempResolutionWidth = resize[_TempResolutionWidth];
|
||||
int tempResolutionHeight = resize[_TempResolutionHeight];
|
||||
@ -337,7 +337,7 @@ public class C_Resize
|
||||
{
|
||||
// if (fileInfo.Exists)
|
||||
// File.Delete(fileInfo.FullName);
|
||||
// File.Copy(mappingFromItem.ImageFileHolder.FullName, fileInfo.FullName);
|
||||
// File.Copy(mappingFromItem.FilePath.FullName, fileInfo.FullName);
|
||||
// item.SetResizedFileHolder(_FileNameExtension, Shared.Models.Stateless.Methods.IFileHolder.Refresh(mappingFromItem.ResizedFileHolder));
|
||||
// subFileTuples.Add(new Tuple<string, DateTime>(nameof(C_Resize), DateTime.Now));
|
||||
}
|
||||
@ -429,10 +429,10 @@ public class C_Resize
|
||||
}
|
||||
|
||||
public FileHolder GetResizedFileHolder(string cResultsFullGroupDirectory, Item item, bool outputResolutionHasNumber) =>
|
||||
GetResizedFileHolder(cResultsFullGroupDirectory, item.FilePath, outputResolutionHasNumber, item.ImageFileHolder.Name);
|
||||
GetResizedFileHolder(cResultsFullGroupDirectory, item.FilePath, outputResolutionHasNumber, item.FilePath.Name);
|
||||
|
||||
public FileHolder GetResizedFileHolder(string cResultsFullGroupDirectory, Item item, bool outputResolutionHasNumber, int id) =>
|
||||
GetResizedFileHolder(cResultsFullGroupDirectory, item.FilePath, outputResolutionHasNumber, $"{id}{item.ImageFileHolder.ExtensionLowered}");
|
||||
GetResizedFileHolder(cResultsFullGroupDirectory, item.FilePath, outputResolutionHasNumber, $"{id}{item.FilePath.ExtensionLowered}");
|
||||
|
||||
public Dictionary<string, int[]> GetResizeKeyValuePairs(Configuration configuration, string cResultsFullGroupDirectory, FilePath filePath, List<Tuple<string, DateTime>> subFileTuples, List<string> parseExceptions, Shared.Models.Property property, MappingFromItem mappingFromItem)
|
||||
{
|
||||
@ -441,7 +441,7 @@ public class C_Resize
|
||||
string[] changesFrom = [nameof(A_Property), nameof(B_Metadata)];
|
||||
List<DateTime> dateTimes = (from l in subFileTuples where changesFrom.Contains(l.Item1) select l.Item2).ToList();
|
||||
(_, int directoryIndex) = Shared.Models.Stateless.Methods.IPath.GetDirectoryNameAndIndex(_PropertyConfiguration, filePath);
|
||||
FileInfo fileInfo = new(Path.Combine(_FileGroups[_PropertyConfiguration.ResultSingleton][directoryIndex], $"{mappingFromItem.ImageFileHolder.NameWithoutExtension}{mappingFromItem.ImageFileHolder.ExtensionLowered}.json"));
|
||||
FileInfo fileInfo = new(Path.Combine(_FileGroups[_PropertyConfiguration.ResultSingleton][directoryIndex], $"{mappingFromItem.FilePath.NameWithoutExtension}{mappingFromItem.FilePath.ExtensionLowered}.json"));
|
||||
if (_ForceResizeLastWriteTimeToCreationTime && !fileInfo.Exists && File.Exists(Path.ChangeExtension(fileInfo.FullName, ".delete")))
|
||||
{
|
||||
File.Move(Path.ChangeExtension(fileInfo.FullName, ".delete"), fileInfo.FullName);
|
||||
|
@ -86,7 +86,7 @@ public class SetCreatedDate
|
||||
isIgnoreExtension = isValidImageFormatExtension && _PropertyConfiguration.IgnoreExtensions.Contains(fileHolder.ExtensionLowered);
|
||||
if (isIgnoreExtension || !isValidImageFormatExtension)
|
||||
continue;
|
||||
(dateTimeOriginal, dateTimes, id, message) = Property.Models.Stateless.IProperty.Get(_PropertyConfiguration.PopulatePropertyId, metadata, fileHolder, isIgnoreExtension, isValidImageFormatExtension, asciiEncoding);
|
||||
(dateTimeOriginal, dateTimes, id, message) = Property.Models.Stateless.IProperty.Get(_PropertyConfiguration, _PropertyConfiguration.PopulatePropertyId, metadata, fileHolder, isIgnoreExtension, isValidImageFormatExtension, asciiEncoding);
|
||||
if (dateTimeOriginal is null)
|
||||
results.Add(new(fileHolder, false, dateTimes.Min()));
|
||||
else
|
||||
|
@ -48,6 +48,21 @@ public record FileHolder(DateTime? CreationTime,
|
||||
return result;
|
||||
}
|
||||
|
||||
public static FileHolder Get(FilePath filePath)
|
||||
{
|
||||
FileHolder result;
|
||||
result = new(new(filePath.CreationTicks),
|
||||
filePath.DirectoryName,
|
||||
true,
|
||||
filePath.ExtensionLowered,
|
||||
filePath.FullName,
|
||||
new(filePath.LastWriteTicks),
|
||||
filePath.Length,
|
||||
filePath.Name,
|
||||
Path.GetFileNameWithoutExtension(filePath.FullName));
|
||||
return result;
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
[JsonSourceGenerationOptions(WriteIndented = true)]
|
||||
|
@ -10,6 +10,7 @@ public record FilePath(long CreationTicks,
|
||||
string FileNameFirstSegment,
|
||||
string FullName,
|
||||
int? Id,
|
||||
bool? IsIgnore,
|
||||
bool IsIntelligentIdFormat,
|
||||
long LastWriteTicks,
|
||||
long Length,
|
||||
@ -38,14 +39,15 @@ public record FilePath(long CreationTicks,
|
||||
string fileNameFirstSegment = fileHolder.Name.Split('.')[0];
|
||||
int sortOrderOnlyLengthIndex = propertyConfiguration.Offset.ToString().Length;
|
||||
string fileDirectoryName = fileHolder.DirectoryName ?? throw new NullReferenceException();
|
||||
bool fileNameFirstSegmentIsIntelligentIdFormat = IId.NameWithoutExtensionIsIntelligentIdFormat(propertyConfiguration, fileNameFirstSegment);
|
||||
bool fileNameFirstSegmentIsPaddedIntelligentIdFormat = IId.NameWithoutExtensionIsPaddedIntelligentIdFormat(propertyConfiguration, sortOrderOnlyLengthIndex, fileNameFirstSegment);
|
||||
bool fileNameFirstSegmentIsIdFormat = !fileNameFirstSegmentIsPaddedIntelligentIdFormat && !fileNameFirstSegmentIsIntelligentIdFormat && IId.NameWithoutExtensionIsIdFormat(propertyConfiguration, fileHolder);
|
||||
if (!fileNameFirstSegmentIsIdFormat && !fileNameFirstSegmentIsIntelligentIdFormat && !fileNameFirstSegmentIsPaddedIntelligentIdFormat)
|
||||
bool isIntelligentIdFormat = IId.NameWithoutExtensionIsIntelligentIdFormat(propertyConfiguration, fileNameFirstSegment);
|
||||
bool isPaddedIntelligentIdFormat = IId.NameWithoutExtensionIsPaddedIntelligentIdFormat(propertyConfiguration, sortOrderOnlyLengthIndex, fileNameFirstSegment);
|
||||
bool fileNameFirstSegmentIsIdFormat = !isPaddedIntelligentIdFormat && !isIntelligentIdFormat && IId.NameWithoutExtensionIsIdFormat(propertyConfiguration, fileHolder);
|
||||
bool? isIgnore = !isIntelligentIdFormat && !isPaddedIntelligentIdFormat ? null : fileNameFirstSegment[^1] is '2' or '8';
|
||||
if (!fileNameFirstSegmentIsIdFormat && !isIntelligentIdFormat && !isPaddedIntelligentIdFormat)
|
||||
(id, sortOder) = (null, null);
|
||||
else if (fileNameFirstSegmentIsIntelligentIdFormat)
|
||||
else if (isIntelligentIdFormat)
|
||||
(id, sortOder) = (IId.GetId(propertyConfiguration, fileNameFirstSegment), null);
|
||||
else if (fileNameFirstSegmentIsPaddedIntelligentIdFormat)
|
||||
else if (isPaddedIntelligentIdFormat)
|
||||
{
|
||||
if (!int.TryParse(fileNameFirstSegment[..sortOrderOnlyLengthIndex], out int absoluteValueOfSortOrder))
|
||||
(id, sortOder) = (null, null);
|
||||
@ -68,7 +70,8 @@ public record FilePath(long CreationTicks,
|
||||
fileNameFirstSegment,
|
||||
fileHolder.FullName,
|
||||
id,
|
||||
fileNameFirstSegmentIsIntelligentIdFormat,
|
||||
isIgnore,
|
||||
isIntelligentIdFormat,
|
||||
fileHolder.LastWriteTime.Value.Ticks,
|
||||
fileHolder.Length.Value,
|
||||
fileHolder.Name,
|
||||
|
@ -9,7 +9,6 @@ public class Item : Properties.IItem
|
||||
protected List<Face> _Faces;
|
||||
protected readonly bool? _FileSizeChanged;
|
||||
protected readonly FilePath _FilePath;
|
||||
protected readonly FileHolder _ImageFileHolder;
|
||||
protected bool? _IsNotUniqueAndNeedsReview;
|
||||
protected bool _IsUniqueFileName;
|
||||
protected bool _IsValidImageFormatExtension;
|
||||
@ -22,7 +21,6 @@ public class Item : Properties.IItem
|
||||
public List<Face> Faces => _Faces;
|
||||
public bool? FileSizeChanged => _FileSizeChanged;
|
||||
public FilePath FilePath => _FilePath;
|
||||
public FileHolder ImageFileHolder => _ImageFileHolder;
|
||||
public bool? IsNotUniqueAndNeedsReview => _IsNotUniqueAndNeedsReview;
|
||||
public bool IsUniqueFileName => _IsUniqueFileName;
|
||||
public bool IsValidImageFormatExtension => _IsValidImageFormatExtension;
|
||||
@ -34,12 +32,11 @@ public class Item : Properties.IItem
|
||||
public FileHolder SourceDirectoryFileHolder => _SourceDirectoryFileHolder;
|
||||
|
||||
[JsonConstructor]
|
||||
public Item(List<Face> faces, FilePath filePath, bool? fileSizeChanged, FileHolder imageFileHolder, bool? isNotUniqueAndNeedsReview, bool isUniqueFileName, bool isValidImageFormatExtension, bool? lastWriteTimeChanged, bool? moved, Property? property, string relativePath, FileHolder? resizedFileHolder, FileHolder sourceDirectoryFileHolder)
|
||||
public Item(List<Face> faces, FilePath filePath, bool? fileSizeChanged, bool? isNotUniqueAndNeedsReview, bool isUniqueFileName, bool isValidImageFormatExtension, bool? lastWriteTimeChanged, bool? moved, Property? property, string relativePath, FileHolder? resizedFileHolder, FileHolder sourceDirectoryFileHolder)
|
||||
{
|
||||
_Faces = faces;
|
||||
_FilePath = filePath;
|
||||
_FileSizeChanged = fileSizeChanged;
|
||||
_ImageFileHolder = imageFileHolder;
|
||||
_IsNotUniqueAndNeedsReview = isNotUniqueAndNeedsReview;
|
||||
_IsUniqueFileName = isUniqueFileName;
|
||||
_IsValidImageFormatExtension = isValidImageFormatExtension;
|
||||
@ -51,17 +48,17 @@ public class Item : Properties.IItem
|
||||
_SourceDirectoryFileHolder = sourceDirectoryFileHolder;
|
||||
}
|
||||
|
||||
public Item(FilePath filePath, FileHolder sourceDirectoryFileHolder, string relativePath, FileHolder imageFileInfo, bool? isNotUniqueAndNeedsReview, bool isUniqueFileName, bool isValidImageFormatExtension, Property? property, bool? abandoned, bool? fileSizeChanged, bool? lastWriteTimeChanged) :
|
||||
this([], filePath, fileSizeChanged, imageFileInfo, isNotUniqueAndNeedsReview, isUniqueFileName, isValidImageFormatExtension, lastWriteTimeChanged, null, property, relativePath, null, sourceDirectoryFileHolder)
|
||||
public Item(FilePath filePath, FileHolder sourceDirectoryFileHolder, string relativePath, bool? isNotUniqueAndNeedsReview, bool isUniqueFileName, bool isValidImageFormatExtension, Property? property, bool? abandoned, bool? fileSizeChanged, bool? lastWriteTimeChanged) :
|
||||
this([], filePath, fileSizeChanged, isNotUniqueAndNeedsReview, isUniqueFileName, isValidImageFormatExtension, lastWriteTimeChanged, null, property, relativePath, null, sourceDirectoryFileHolder)
|
||||
{
|
||||
if (relativePath.EndsWith(".json"))
|
||||
throw new ArgumentException("Can not be a *.json file!");
|
||||
if (imageFileInfo is not null && imageFileInfo.ExtensionLowered is ".json")
|
||||
if (filePath is not null && filePath.ExtensionLowered is ".json")
|
||||
throw new ArgumentException("Can not be a *.json file!");
|
||||
}
|
||||
|
||||
public Item(FilePath filePath, FileHolder sourceDirectoryFileHolder, string relativePath, bool isValidImageFormatExtension) :
|
||||
this(filePath, sourceDirectoryFileHolder, relativePath, sourceDirectoryFileHolder, null, false, isValidImageFormatExtension, null, null, null, null)
|
||||
this(filePath, sourceDirectoryFileHolder, relativePath, null, false, isValidImageFormatExtension, null, null, null, null)
|
||||
{ }
|
||||
|
||||
public override string ToString()
|
||||
|
@ -7,7 +7,7 @@ public record MappingFromItem(DateTime[] ContainerDateTimes,
|
||||
DateTime? DateTimeDigitized,
|
||||
DateTime? DateTimeOriginal,
|
||||
int Id,
|
||||
FileHolder ImageFileHolder,
|
||||
FilePath FilePath,
|
||||
bool? IsWrongYear,
|
||||
string[] Keywords,
|
||||
DateTime MinimumDateTime,
|
||||
@ -34,8 +34,8 @@ public record MappingFromItem(DateTime[] ContainerDateTimes,
|
||||
throw new NotSupportedException();
|
||||
List<DateTime> dateTimes = item.Property.GetDateTimes();
|
||||
DateTime minimumDateTime = Stateless.Methods.IProperty.GetMinimumDateTime(item.Property);
|
||||
(bool? isWrongYear, _) = Stateless.Methods.IProperty.IsWrongYear(item.ImageFileHolder, item.Property.DateTimeOriginal, dateTimes);
|
||||
result = new(containerDateTimes, item.Property.DateTimeDigitized, item.Property.DateTimeOriginal, item.Property.Id.Value, item.ImageFileHolder, isWrongYear, item.Property.Keywords ?? [], minimumDateTime, item.Property.Model, item.RelativePath, resizedFileHolder);
|
||||
(bool? isWrongYear, _) = Stateless.Methods.IProperty.IsWrongYear(item.FilePath, item.Property.DateTimeOriginal, dateTimes);
|
||||
result = new(containerDateTimes, item.Property.DateTimeDigitized, item.Property.DateTimeOriginal, item.Property.Id.Value, item.FilePath, isWrongYear, item.Property.Keywords ?? [], minimumDateTime, item.Property.Model, item.RelativePath, resizedFileHolder);
|
||||
return result;
|
||||
}
|
||||
|
||||
|
@ -3,6 +3,6 @@ namespace View_by_Distance.Shared.Models.Methods;
|
||||
public interface IMetadata<T>
|
||||
{
|
||||
|
||||
(DateTime?, DateTime?[]) GetDateTimes(FileHolder fileHolder, IReadOnlyList<T> directories);
|
||||
(DateTime?, DateTime?[]) GetDateTimes(FilePath filePath, IReadOnlyList<T> directories);
|
||||
|
||||
}
|
@ -6,7 +6,6 @@ public interface IItem
|
||||
public bool? FileSizeChanged { get; }
|
||||
public List<Face> Faces { get; }
|
||||
public FilePath FilePath { get; }
|
||||
public FileHolder ImageFileHolder { get; }
|
||||
public bool? IsNotUniqueAndNeedsReview { get; }
|
||||
public bool IsUniqueFileName { get; }
|
||||
public bool IsValidImageFormatExtension { get; }
|
||||
|
@ -11,17 +11,9 @@ internal abstract class Container
|
||||
internal static DateTime[] GetContainerDateTimes(IEnumerable<Models.Item> items)
|
||||
{
|
||||
DateTime[] results;
|
||||
DateTime? containerMinimumDateTime;
|
||||
DateTime? containerMaximumDateTime;
|
||||
containerMinimumDateTime = (from l in items select l.ImageFileHolder.LastWriteTime).Min();
|
||||
if (containerMinimumDateTime is null)
|
||||
containerMaximumDateTime = null;
|
||||
else
|
||||
containerMaximumDateTime = (from l in items select l.ImageFileHolder.LastWriteTime).Max();
|
||||
if (containerMinimumDateTime is null || containerMaximumDateTime is null)
|
||||
results = [];
|
||||
else
|
||||
results = [containerMinimumDateTime.Value, containerMaximumDateTime.Value];
|
||||
long containerMinimumTicks = (from l in items select l.FilePath.LastWriteTicks).Min();
|
||||
long containerMaximumTicks = (from l in items select l.FilePath.LastWriteTicks).Max();
|
||||
results = [new(containerMinimumTicks), new(containerMaximumTicks)];
|
||||
return results;
|
||||
}
|
||||
|
||||
@ -30,9 +22,8 @@ internal abstract class Container
|
||||
List<Models.Item> results = [];
|
||||
foreach (Models.Item item in container.Items)
|
||||
{
|
||||
if (item.ImageFileHolder is not null
|
||||
&& item.IsValidImageFormatExtension
|
||||
&& !propertyConfiguration.IgnoreExtensions.Contains(item.ImageFileHolder.ExtensionLowered))
|
||||
if (item.IsValidImageFormatExtension
|
||||
&& !propertyConfiguration.IgnoreExtensions.Contains(item.FilePath.ExtensionLowered))
|
||||
results.Add(item);
|
||||
}
|
||||
return results.ToArray();
|
||||
@ -87,12 +78,23 @@ internal abstract class Container
|
||||
FilePath filePath = FilePath.Get(propertyConfiguration, imageFileInfo, index: null);
|
||||
bool? fileSizeChanged = property is not null ? property.FileSize != filePath.Length : null;
|
||||
bool isValidImageFormatExtension = propertyConfiguration.ValidImageFormatExtensions.Contains(filePath.ExtensionLowered);
|
||||
if (property is not null && property.Keywords is not null && !IId.IsIgnore(filePath) && propertyConfiguration.IgnoreRulesKeyWords.Any(l => property.Keywords.Contains(l)))
|
||||
if (property is not null && property.Keywords is not null)
|
||||
{
|
||||
if (filePath.DirectoryName.Contains("Results") && filePath.DirectoryName.Contains("Resize"))
|
||||
File.Delete(filePath.FullName);
|
||||
else
|
||||
throw new NotSupportedException($"Rename File! <{filePath.FileNameFirstSegment}>");
|
||||
if (filePath.IsIgnore is null)
|
||||
throw new NullReferenceException();
|
||||
bool shouldIgnore = propertyConfiguration.IgnoreRulesKeyWords.Any(l => property.Keywords.Contains(l));
|
||||
if (shouldIgnore)
|
||||
{
|
||||
if (shouldIgnore)
|
||||
{ }
|
||||
}
|
||||
if (filePath.IsIgnore.Value != shouldIgnore)
|
||||
{
|
||||
if (filePath.DirectoryName.Contains("Results") && filePath.DirectoryName.Contains("Resize"))
|
||||
File.Delete(filePath.FullName);
|
||||
else
|
||||
throw new NotSupportedException($"Rename File! <{filePath.FileNameFirstSegment}>");
|
||||
}
|
||||
}
|
||||
string relativePath = IPath.GetRelativePath(filePair.Path, rootDirectoryLength, forceExtensionToLower: true);
|
||||
bool? lastWriteTimeChanged = property is not null ? propertyConfiguration.PropertiesChangedForProperty || property.LastWriteTime.Ticks != filePath.LastWriteTicks : null;
|
||||
@ -111,17 +113,19 @@ internal abstract class Container
|
||||
File.SetCreationTime(sourceDirectoryFileHolder.FullName, new(filePath.LastWriteTicks));
|
||||
File.SetLastWriteTime(sourceDirectoryFileHolder.FullName, sourceDirectoryFileHolder.LastWriteTime.Value);
|
||||
}
|
||||
Models.Item item = new(filePath, sourceDirectoryFileHolder, relativePath, imageFileInfo, filePair.IsNotUniqueAndNeedsReview, filePair.IsUnique, isValidImageFormatExtension, property, abandoned, fileSizeChanged, lastWriteTimeChanged);
|
||||
Models.Item item = new(filePath, sourceDirectoryFileHolder, relativePath, filePair.IsNotUniqueAndNeedsReview, filePair.IsUnique, isValidImageFormatExtension, property, abandoned, fileSizeChanged, lastWriteTimeChanged);
|
||||
lock (results)
|
||||
results.Add(new(filePair.IsUnique, filePair.Collection, filePath, item));
|
||||
}
|
||||
|
||||
private static List<FilePair> GetFilePairs(Properties.IPropertyConfiguration propertyConfiguration, string aPropertySingletonDirectory, string filesCollectionDirectory, string extension, List<Models.FilePair> filePairs)
|
||||
private static List<FilePair> GetFilePairs(Properties.IPropertyConfiguration propertyConfiguration, string aPropertySingletonDirectory, string filesCollectionDirectory, ReadOnlyCollection<string[]> filesCollection, string directorySearchFilter)
|
||||
{
|
||||
List<FilePair> results = [];
|
||||
const string extension = ".json";
|
||||
int maxDegreeOfParallelism = Environment.ProcessorCount;
|
||||
int filesCollectionDirectoryLength = filesCollectionDirectory.Length;
|
||||
ParallelOptions parallelOptions = new() { MaxDegreeOfParallelism = maxDegreeOfParallelism };
|
||||
List<Models.FilePair> filePairs = GetFilePairs(propertyConfiguration, directorySearchFilter, extension, aPropertySingletonDirectory, filesCollection);
|
||||
_ = Parallel.For(0, filePairs.Count, parallelOptions, (i, state) => ParallelFor(propertyConfiguration, aPropertySingletonDirectory, extension, filesCollectionDirectoryLength, filePairs[i], results));
|
||||
return results;
|
||||
}
|
||||
@ -133,7 +137,6 @@ internal abstract class Container
|
||||
List<Models.Item>? items;
|
||||
Models.Container container;
|
||||
List<string> directories = [];
|
||||
const string extension = ".json";
|
||||
Dictionary<string, List<Models.Item>> directoryToItems = [];
|
||||
foreach (string[] files in filesCollection)
|
||||
{
|
||||
@ -151,9 +154,8 @@ internal abstract class Container
|
||||
throw new Exception();
|
||||
}
|
||||
}
|
||||
List<Models.FilePair> filePairs = GetFilePairs(propertyConfiguration, directorySearchFilter, extension, aPropertySingletonDirectory, filesCollection);
|
||||
List<FilePair> collection = GetFilePairs(propertyConfiguration, aPropertySingletonDirectory, filesCollectionDirectory, extension, filePairs);
|
||||
foreach (FilePair filePair in collection)
|
||||
List<FilePair> filePairs = GetFilePairs(propertyConfiguration, aPropertySingletonDirectory, filesCollectionDirectory, filesCollection, directorySearchFilter);
|
||||
foreach (FilePair filePair in filePairs)
|
||||
{
|
||||
if (!directoryToItems.TryGetValue(filePair.FilePath.DirectoryName, out items))
|
||||
{
|
||||
@ -170,7 +172,7 @@ internal abstract class Container
|
||||
container = new(keyValuePair.Key, keyValuePair.Value);
|
||||
results.Add(container);
|
||||
}
|
||||
return (collection.Count, results.ToArray());
|
||||
return (filePairs.Count, results.ToArray());
|
||||
}
|
||||
|
||||
internal static (int, Models.Container[]) GetContainers(Properties.IPropertyConfiguration propertyConfiguration, string aPropertySingletonDirectory, string filesCollectionDirectory, ReadOnlyCollection<string[]> filesCollection)
|
||||
|
@ -3,9 +3,9 @@ namespace View_by_Distance.Shared.Models.Stateless.Methods;
|
||||
public interface IId
|
||||
{ // ...
|
||||
|
||||
string TestStatic_GetIntelligentId(Properties.IPropertyConfiguration propertyConfiguration, long id, bool ignore) =>
|
||||
string TestStatic_GetIntelligentId(Properties.IPropertyConfiguration propertyConfiguration, long id, bool? ignore) =>
|
||||
GetIntelligentId(propertyConfiguration, id, ignore);
|
||||
static string GetIntelligentId(Properties.IPropertyConfiguration propertyConfiguration, long id, bool ignore) =>
|
||||
static string GetIntelligentId(Properties.IPropertyConfiguration propertyConfiguration, long id, bool? ignore) =>
|
||||
Id.GetIntelligentId(propertyConfiguration, id, ignore);
|
||||
|
||||
int TestStatic_GetId(Properties.IPropertyConfiguration propertyConfiguration, string intelligentId) =>
|
||||
@ -13,15 +13,10 @@ public interface IId
|
||||
static int GetId(Properties.IPropertyConfiguration propertyConfiguration, string intelligentId) =>
|
||||
Id.GetId(propertyConfiguration, intelligentId);
|
||||
|
||||
string TestStatic_GetPaddedId(Properties.IPropertyConfiguration propertyConfiguration, int id, int? index) =>
|
||||
GetPaddedId(propertyConfiguration, id, index);
|
||||
static string GetPaddedId(Properties.IPropertyConfiguration propertyConfiguration, int id, int? index) =>
|
||||
Id.GetPaddedId(propertyConfiguration, id, index);
|
||||
|
||||
bool TestStatic_IsIgnore(FilePath filePath) =>
|
||||
IsIgnore(filePath);
|
||||
static bool IsIgnore(FilePath filePath) =>
|
||||
filePath.FileNameFirstSegment[^1] is '2' or '8';
|
||||
string TestStatic_GetPaddedId(Properties.IPropertyConfiguration propertyConfiguration, int id, bool? ignore, int? index) =>
|
||||
GetPaddedId(propertyConfiguration, id, ignore, index);
|
||||
static string GetPaddedId(Properties.IPropertyConfiguration propertyConfiguration, int id, bool? ignore, int? index) =>
|
||||
Id.GetPaddedId(propertyConfiguration, id, ignore, index);
|
||||
|
||||
string TestStatic_GetIgnoreFullPath(FilePath filePath, Models.FileHolder fileHolder) =>
|
||||
GetIgnoreFullPath(filePath, fileHolder);
|
||||
|
@ -33,10 +33,10 @@ public interface IProperty
|
||||
static (bool?, string[]) IsWrongYear(string[] segments, string year) =>
|
||||
Property.IsWrongYear(segments, year);
|
||||
|
||||
(bool?, string[]) TestStatic_IsWrongYear(Models.FileHolder fileHolder, DateTime? dateTimeOriginal, List<DateTime> dateTimes) =>
|
||||
IsWrongYear(fileHolder, dateTimeOriginal, dateTimes);
|
||||
static (bool?, string[]) IsWrongYear(Models.FileHolder fileHolder, DateTime? dateTimeOriginal, List<DateTime> dateTimes) =>
|
||||
Property.IsWrongYear(fileHolder, dateTimeOriginal, dateTimes);
|
||||
(bool?, string[]) TestStatic_IsWrongYear(FilePath filePath, DateTime? dateTimeOriginal, List<DateTime> dateTimes) =>
|
||||
IsWrongYear(filePath, dateTimeOriginal, dateTimes);
|
||||
static (bool?, string[]) IsWrongYear(FilePath filePath, DateTime? dateTimeOriginal, List<DateTime> dateTimes) =>
|
||||
Property.IsWrongYear(filePath, dateTimeOriginal, dateTimes);
|
||||
|
||||
List<DateTime> TestStatic_GetDateTimes(Models.Property property) =>
|
||||
GetDateTimes(property);
|
||||
|
@ -35,7 +35,7 @@ internal abstract class Id
|
||||
return result;
|
||||
}
|
||||
|
||||
internal static string GetIntelligentId(Properties.IPropertyConfiguration propertyConfiguration, long id, bool ignore)
|
||||
internal static string GetIntelligentId(Properties.IPropertyConfiguration propertyConfiguration, long id, bool? ignore)
|
||||
{
|
||||
string result;
|
||||
StringBuilder stringBuilder = new();
|
||||
@ -46,12 +46,12 @@ internal abstract class Id
|
||||
List<char> resultAllInOneSubdirectoryChars = [];
|
||||
if (id > -1)
|
||||
{
|
||||
key = ignore ? 8 : 9;
|
||||
key = ignore is not null && ignore.Value ? 8 : 9;
|
||||
value = id.ToString().PadLeft(propertyConfiguration.IntMinValueLength, '0');
|
||||
}
|
||||
else
|
||||
{
|
||||
key = ignore ? 2 : 1;
|
||||
key = ignore is not null && ignore.Value ? 2 : 1;
|
||||
value = id.ToString()[1..].PadLeft(propertyConfiguration.IntMinValueLength, '0');
|
||||
}
|
||||
for (int i = value.Length - propertyConfiguration.ResultAllInOneSubdirectoryLength - 1; i > -1; i--)
|
||||
@ -62,14 +62,14 @@ internal abstract class Id
|
||||
return result;
|
||||
}
|
||||
|
||||
internal static string GetPaddedId(Properties.IPropertyConfiguration propertyConfiguration, int id, int? index)
|
||||
internal static string GetPaddedId(Properties.IPropertyConfiguration propertyConfiguration, int id, bool? ignore, int? index)
|
||||
{
|
||||
string result;
|
||||
if (propertyConfiguration.Offset < 0)
|
||||
result = Guid.NewGuid().ToString();
|
||||
else
|
||||
{
|
||||
string intelligentId = GetIntelligentId(propertyConfiguration, id, ignore: false);
|
||||
string intelligentId = GetIntelligentId(propertyConfiguration, id, ignore);
|
||||
int check = GetId(propertyConfiguration, intelligentId);
|
||||
if (check != id)
|
||||
throw new NotSupportedException();
|
||||
|
@ -10,11 +10,11 @@ internal abstract class Item
|
||||
foreach (Models.Item item in itemsA)
|
||||
{
|
||||
results.Add(item);
|
||||
collection.Add(item.ImageFileHolder.FullName);
|
||||
collection.Add(item.FilePath.FullName);
|
||||
}
|
||||
foreach (Models.Item item in itemsB)
|
||||
{
|
||||
if (collection.Contains(item.ImageFileHolder.FullName))
|
||||
if (collection.Contains(item.FilePath.FullName))
|
||||
continue;
|
||||
results.Add(item);
|
||||
}
|
||||
|
@ -47,7 +47,7 @@ internal abstract class Property
|
||||
return new(result, results);
|
||||
}
|
||||
|
||||
internal static (bool?, string[]) IsWrongYear(Models.FileHolder fileHolder, DateTime? dateTimeOriginal, List<DateTime> dateTimes)
|
||||
internal static (bool?, string[]) IsWrongYear(FilePath filePath, DateTime? dateTimeOriginal, List<DateTime> dateTimes)
|
||||
{
|
||||
string[] results = [];
|
||||
bool? result = null;
|
||||
@ -55,8 +55,8 @@ internal abstract class Property
|
||||
string directoryName;
|
||||
string[] directorySegments;
|
||||
List<DateTime> collection = [];
|
||||
string? check = Path.GetFullPath(fileHolder.FullName);
|
||||
string? pathRoot = Path.GetPathRoot(fileHolder.FullName);
|
||||
string? check = Path.GetFullPath(filePath.FullName);
|
||||
string? pathRoot = Path.GetPathRoot(filePath.FullName);
|
||||
if (string.IsNullOrEmpty(pathRoot))
|
||||
throw new Exception();
|
||||
if (dateTimeOriginal is not null)
|
||||
|
@ -291,7 +291,6 @@ internal abstract partial class XDirectory
|
||||
FileInfo fileInfo;
|
||||
FilePath filePath;
|
||||
int directoryIndex;
|
||||
bool ignore = false;
|
||||
string paddedIdFile;
|
||||
bool wrapped = false;
|
||||
string intelligentId;
|
||||
@ -324,7 +323,7 @@ internal abstract partial class XDirectory
|
||||
}
|
||||
if (ifCanUseId && filePath.IsIntelligentIdFormat && filePath.Id is not null && filePath.DirectoryName is not null)
|
||||
{
|
||||
paddedId = IId.GetPaddedId(propertyConfiguration, filePath.Id.Value, i);
|
||||
paddedId = IId.GetPaddedId(propertyConfiguration, filePath.Id.Value, filePath.IsIgnore, i);
|
||||
paddedIdFile = Path.Combine(filePath.DirectoryName, $"{paddedId}{filePath.ExtensionLowered}");
|
||||
if (!File.Exists(paddedIdFile))
|
||||
{
|
||||
@ -342,7 +341,7 @@ internal abstract partial class XDirectory
|
||||
{
|
||||
if (filePath.Id is null)
|
||||
throw new NullReferenceException(nameof(filePath.Id));
|
||||
intelligentId = IId.GetIntelligentId(propertyConfiguration, filePath.Id.Value, ignore);
|
||||
intelligentId = IId.GetIntelligentId(propertyConfiguration, filePath.Id.Value, filePath.IsIgnore);
|
||||
checkFile = Path.Combine(directory, $"{intelligentId}{filePath.ExtensionLowered}");
|
||||
}
|
||||
if ((filePath.Id is not null && distinctIds.Contains(filePath.Id.Value)) || distinct.Contains(checkFile))
|
||||
@ -396,10 +395,9 @@ internal abstract partial class XDirectory
|
||||
fileInfo = new(to);
|
||||
if (fileInfo.Exists)
|
||||
{
|
||||
if (filePath.Length != fileInfo.Length || filePath.LastWriteTicks != fileInfo.LastWriteTime.Ticks)
|
||||
fileInfo.Delete();
|
||||
else
|
||||
if (filePath.Length == fileInfo.Length && filePath.LastWriteTicks == fileInfo.LastWriteTime.Ticks)
|
||||
continue;
|
||||
fileInfo.Delete();
|
||||
}
|
||||
results.Add(filePath.NameWithoutExtension);
|
||||
try
|
||||
|
@ -165,8 +165,7 @@ public class UnitTestResize
|
||||
resize.SetAngleBracketCollection(cResultsFullGroupDirectory, sourceDirectory);
|
||||
resize.Update(cResultsFullGroupDirectory);
|
||||
blurHasher.Update(cResultsFullGroupDirectory);
|
||||
item = new(filePath, sourceDirectoryFileHolder, relativePath, fileHolder, isNotUniqueAndNeedsReview, isUniqueFileName, isValidImageFormatExtension, property, false, false, false);
|
||||
Assert.IsNotNull(item.ImageFileHolder);
|
||||
item = new(filePath, sourceDirectoryFileHolder, relativePath, isNotUniqueAndNeedsReview, isUniqueFileName, isValidImageFormatExtension, property, false, false, false);
|
||||
if (item.Property is null)
|
||||
{
|
||||
property = propertyLogic.GetProperty(metadata, item, subFileTuples, parseExceptions);
|
||||
|
@ -238,8 +238,7 @@ public class UnitTestFace
|
||||
resize.SetAngleBracketCollection(cResultsFullGroupDirectory, sourceDirectory);
|
||||
resize.Update(cResultsFullGroupDirectory);
|
||||
blurHasher.Update(cResultsFullGroupDirectory);
|
||||
item = new(filePath, sourceDirectoryFileHolder, relativePath, fileHolder, isNotUniqueAndNeedsReview, isUniqueFileName, isValidImageFormatExtension, property, false, false, false);
|
||||
Assert.IsNotNull(item.ImageFileHolder);
|
||||
item = new(filePath, sourceDirectoryFileHolder, relativePath, isNotUniqueAndNeedsReview, isUniqueFileName, isValidImageFormatExtension, property, false, false, false);
|
||||
if (item.Property is null)
|
||||
{
|
||||
property = propertyLogic.GetProperty(metadata, item, subFileTuples, parseExceptions);
|
||||
|
Reference in New Issue
Block a user