using System;
using System.IO;
using SabreTools.Hashing;
using SabreTools.Text.Extensions;
namespace SabreTools.Metadata.DatFiles
{
///
/// Depot information wrapper
///
public class DepotInformation : ICloneable
{
///
/// Name or path of the Depot
///
public string? Name { get; }
///
/// Whether to use this Depot or not
///
public bool IsActive { get; }
///
/// Depot byte-depth
///
public int Depth { get; }
///
/// Maximum depth allowed for path generation
///
private static readonly int MaximumDepth = HashType.SHA1.ZeroBytes.Length;
///
/// Constructor
///
/// Set active state
/// Set depth between 0 and SHA-1's byte length
public DepotInformation(bool isActive, int depth)
: this(null, isActive, depth)
{
}
///
/// Constructor
///
/// Identifier for the depot
/// Set active state
/// Set depth between 0 and SHA-1's byte length
public DepotInformation(string? name, bool isActive, int depth)
{
Name = name;
IsActive = isActive;
Depth = depth;
// Limit depth value
if (Depth == int.MinValue)
Depth = 4;
else if (Depth < 0)
Depth = 0;
else if (Depth > MaximumDepth)
Depth = MaximumDepth;
}
#region Cloning
///
/// Clone the current object
///
public object Clone() => new DepotInformation(Name, IsActive, Depth);
#endregion
#region Path Generation
///
/// Get a proper romba subpath
///
/// SHA-1 hash to get the path for
/// Positive value representing the depth of the depot
/// Subfolder path for the given hash, including the filename and .gz extension
public string? GetDepotPath(byte[]? hash)
{
string? sha1 = hash.ToHexString();
return GetDepotPath(sha1);
}
///
/// Get a proper romba subpath
///
/// SHA-1 hash to get the path for
/// Subfolder path for the given hash, including the filename and .gz extension
public string? GetDepotPath(string? hash)
{
// If the hash is null, then we return null
if (hash is null)
return null;
// If the hash isn't the right size, then we return null
if (hash.Length != HashType.SHA1.ZeroString.Length)
return null;
// Cap the depth between 0 and 20, for now
int depth = Depth;
if (depth < 0)
depth = 0;
else if (depth > MaximumDepth)
depth = MaximumDepth;
// Loop through and generate the subdirectory
string path = string.Empty;
for (int i = 0; i < depth; i++)
{
path += hash.Substring(i * 2, 2) + Path.DirectorySeparatorChar;
}
// Now append the filename
path += $"{hash}.gz";
return path;
}
#endregion
}
}