-
Notifications
You must be signed in to change notification settings - Fork 20
Commit
This commit does not belong to any branch on this repository, and may belong to a fork outside of the repository.
Merge pull request #322 from UchuServer/fix/linux-dotnet-paths
Fix Configuration Paths on Linux with .NET
- Loading branch information
Showing
5 changed files
with
185 additions
and
25 deletions.
There are no files selected for viewing
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,80 @@ | ||
using System.Collections.Generic; | ||
using NUnit.Framework; | ||
using Uchu.Core.Config; | ||
|
||
namespace Uchu.Core.Test.Config | ||
{ | ||
public class TestConfiguration | ||
{ | ||
public string TestString { get; set; } = "test"; | ||
[ConfigurationPath] | ||
public string TestPath1 { get; set; } = "test1"; | ||
[ConfigurationPath] | ||
public string TestPath2 { get; set; } = "test1/test2"; | ||
[ConfigurationPath] | ||
public string TestPath3 { get; set; } = "/test"; | ||
[ConfigurationPath] | ||
public string[] TestPaths1 { get; set; } = new string[] | ||
{ | ||
"test1", | ||
"test1/test2", | ||
"/test", | ||
}; | ||
[ConfigurationPath] | ||
public List<string> TestPaths2 { get; set; } = new List<string> | ||
{ | ||
"test1", | ||
"test1/test2", | ||
"/test", | ||
}; | ||
} | ||
|
||
public class ConfigurationPathAttributeTest | ||
{ | ||
/// <summary> | ||
/// Asserts 2 paths are the same. | ||
/// </summary> | ||
/// <param name="expected">Expected path.</param> | ||
/// <param name="actual">Actual path.</param> | ||
public static void AssertPath(string expected, string actual) | ||
{ | ||
Assert.AreEqual(expected.Replace('\\', '/'), actual.Replace('\\', '/')); | ||
} | ||
|
||
/// <summary> | ||
/// Tests replacing a null object to verify it doesn't fail. | ||
/// </summary> | ||
[Test] | ||
public void TestNull() | ||
{ | ||
ConfigurationPathAttribute.ReplaceFilePaths("", null); | ||
} | ||
|
||
/// <summary> | ||
/// Tests replacing paths on Linux. | ||
/// </summary> | ||
[Test] | ||
public void TestPaths() | ||
{ | ||
// Replace the configuration paths. | ||
var configuration = new TestConfiguration(); | ||
ConfigurationPathAttribute.ReplaceFilePaths("/test1/test2/config.xml", configuration); | ||
|
||
// Assert the strings are correct. | ||
AssertPath(configuration.TestString, "test"); | ||
AssertPath(configuration.TestPath1, "/test1/test2/test1"); | ||
AssertPath(configuration.TestPath2, "/test1/test2/test1/test2"); | ||
AssertPath(configuration.TestPath3, "/test"); | ||
|
||
// Assert the array of strings is correct. | ||
AssertPath(configuration.TestPaths1[0], "/test1/test2/test1"); | ||
AssertPath(configuration.TestPaths1[1], "/test1/test2/test1/test2"); | ||
AssertPath(configuration.TestPaths1[2], "/test"); | ||
|
||
// Assert the list of strings is correct. | ||
AssertPath(configuration.TestPaths2[0], "/test1/test2/test1"); | ||
AssertPath(configuration.TestPaths2[1], "/test1/test2/test1/test2"); | ||
AssertPath(configuration.TestPaths2[2], "/test"); | ||
} | ||
} | ||
} |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,79 @@ | ||
using System; | ||
using System.Collections.Generic; | ||
using System.IO; | ||
using System.Reflection; | ||
|
||
namespace Uchu.Core.Config | ||
{ | ||
[AttributeUsage(AttributeTargets.Property)] | ||
public class ConfigurationPathAttribute : Attribute | ||
{ | ||
/// <summary> | ||
/// Returns an absolute path relative to a configuration path. | ||
/// </summary> | ||
/// <param name="configurationLocation">File location of the configuration.</param> | ||
/// <param name="relativePath">Relative path to make absolute.</param> | ||
/// <returns>Absolute path of the relative path.</returns> | ||
public static string ReplaceRelativePath(string configurationLocation, string relativePath) | ||
{ | ||
// Normalize the relative path. | ||
configurationLocation ??= ""; | ||
relativePath ??= ""; | ||
relativePath = relativePath.Replace(configurationLocation.Contains('/', StringComparison.CurrentCulture) ? "\\" : "/", configurationLocation.Contains('/', StringComparison.CurrentCulture) ? "/" : "\\", StringComparison.CurrentCulture); | ||
|
||
// Return the replaced path. | ||
if (Path.IsPathRooted(relativePath)) return relativePath; | ||
return Path.Join(Path.GetDirectoryName(configurationLocation), relativePath); | ||
} | ||
|
||
/// <summary> | ||
/// Replaces local configuration paths relative to the configuration file. | ||
/// </summary> | ||
/// <param name="configurationLocation">File location of the configuration.</param> | ||
/// <param name="configurationObject">Object to replace the paths in.</param> | ||
public static void ReplaceFilePaths(string configurationLocation, object configurationObject) | ||
{ | ||
// Return if there is no object to replace. | ||
if (configurationObject == null) | ||
{ | ||
return; | ||
} | ||
|
||
// Iterate over the properties. | ||
foreach (var property in configurationObject.GetType().GetProperties()) | ||
{ | ||
if (property.GetIndexParameters().Length != 0) continue; | ||
var value = property.GetValue(configurationObject); | ||
if (value == null) continue; | ||
if (property.GetCustomAttribute<ConfigurationPathAttribute>() != null) | ||
{ | ||
// Replace the strings or list of strings. | ||
if (property.PropertyType == typeof(string)) | ||
{ | ||
property.SetValue(configurationObject, ReplaceRelativePath(configurationLocation, (string) value)); | ||
} | ||
else if (property.PropertyType == typeof(string[])) | ||
{ | ||
var paths = (string[]) value; | ||
for (var i = 0; i < paths.Length; i++) | ||
{ | ||
paths[i] = ReplaceRelativePath(configurationLocation, paths[i]); | ||
} | ||
} | ||
else if (property.PropertyType == typeof(List<string>)) | ||
{ | ||
var paths = (List<string>) value; | ||
for (var i = 0; i < paths.Count; i++) | ||
{ | ||
paths[i] = ReplaceRelativePath(configurationLocation, paths[i]); | ||
} | ||
} | ||
} | ||
else | ||
{ | ||
ReplaceFilePaths(configurationLocation, value); | ||
} | ||
} | ||
} | ||
} | ||
} |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters