using System;
using System.IO;
namespace TrackedFolders.Utilities
{
///
/// Various extensions for dealing with subpaths.
///
/// https://stackoverflow.com/questions/5617320/given-full-path-check-if-path-is-subdirectory-of-some-other-path-or-otherwise
public static class Subpaths
{
#region Public Methods
public static string NormalizePath(this string path)
{
return Path.GetFullPath(path.Replace('/', '\\')
.WithEnding("\\"));
}
///
/// Returns true if starts with the path .
/// The comparison is case-insensitive, handles / and \ slashes as folder separators and
/// only matches if the base dir folder name is matched exactly ("c:\foobar\file.txt" is not a sub path of "c:\foo").
///
public static bool IsSubPathOf(this string path, string baseDirPath)
{
var normalizedPath = NormalizePath(path);
var normalizedBaseDirPath = NormalizePath(baseDirPath);
return normalizedPath.StartsWith(normalizedBaseDirPath, StringComparison.OrdinalIgnoreCase);
}
public static bool IsPathEqual(this string path, string that)
{
return string.Equals(NormalizePath(path), NormalizePath(that), StringComparison.OrdinalIgnoreCase);
}
#endregion
#region Private Methods
///
/// Returns with the minimal concatenation of (starting from end)
/// that
/// results in satisfying .EndsWith(ending).
///
/// "hel".WithEnding("llo") returns "hello", which is the result of "hel" + "lo".
private static string WithEnding(this string str, string ending)
{
if (str == null)
{
return ending;
}
var result = str;
// Right() is 1-indexed, so include these cases
// * Append no characters
// * Append up to N characters, where N is ending length
for (var i = 0; i <= ending.Length; i++)
{
var tmp = result + ending.Right(i);
if (tmp.EndsWith(ending))
{
return tmp;
}
}
return result;
}
/// Gets the rightmost characters from a string.
/// The string to retrieve the substring from.
/// The number of characters to retrieve.
/// The substring.
private static string Right(this string value, int length)
{
if (value == null)
{
throw new ArgumentNullException("value");
}
if (length < 0)
{
throw new ArgumentOutOfRangeException("length", length, "Length is less than zero");
}
return length < value.Length ? value.Substring(value.Length - length) : value;
}
#endregion
}
}