This is as close as I could get using Uri built-in functionality
string file;
string basePath = "c:/someUri/";
Uri baseUri = new Uri(basePath); // fake or real
var list = new List<string>()
{
"./file1.bin",
"././file2.bin",
"file3.bin",
"folder/f/file4.bin",
"a/b/c/../f.bin",
"./f/../data.bin",
"./f/../../../d.bin"
};
foreach (string relative in list)
{
if (Uri.TryCreate(baseUri, relative, out Uri retUri))
{
Console.WriteLine("Original: " + relative);
Console.WriteLine("New : " + retUri.AbsolutePath);
if (retUri.AbsolutePath.StartsWith(basePath))
Console.WriteLine("Normal. : " + retUri.AbsolutePath.Substring(basePath.Length));
else
Console.WriteLine("Normal. : " + retUri.AbsolutePath);
file = Path.GetFileName(relative);
Console.WriteLine("FileName: " + file);
Console.WriteLine("----------------------");
}
else
Console.WriteLine(relative + ": NOPE");
}
Result
Original: ./file1.bin
New : c:/someUri/file1.bin
Normal. : file1.bin
YOUR Res: file1.bin
Success : YES
FileName: file1.bin
----------------------
Original: ././file2.bin
New : c:/someUri/file2.bin
Normal. : file2.bin
YOUR Res: file2.bin
Success : YES
FileName: file2.bin
----------------------
Original: file3.bin
New : c:/someUri/file3.bin
Normal. : file3.bin
YOUR Res: file3.bin
Success : YES
FileName: file3.bin
----------------------
Original: folder/f/file4.bin
New : c:/someUri/folder/f/file4.bin
Normal. : folder/f/file4.bin
YOUR Res: folder/f/file4.binn
Success : YES
FileName: file4.bin
----------------------
Original: a/b/c/../f.bin
New : c:/someUri/a/b/f.bin
Normal. : a/b/f.bin
YOUR Res: a/b/f.bin
Success : YES
FileName: f.bin
----------------------
Original: ./f/../data.bin
New : c:/someUri/data.bin
Normal. : data.bin
YOUR Res: data.bin
Success : YES
FileName: data.bin
----------------------
Original: ./f/../../../d.bin
New : c:/d.bin
Normal. : c:/d.bin
YOUR Res: d.bin
Success : NO !!!!!!
FileName: d.bin