fix: Fixes assembly loading. (#759)

* `AssemblyHandler.Assemblies` will now only contain assemblies listed in `assemblies.json`
* `assemblies.json` has been updated to only contain asssemblies directly loaded by the server. Namely, only `UOContent.dll`.
  * Specifically assemblies loaded by assemblies.json are subject to check for `Configure` and `Initialize` methods.
* `modernuo.json` now has a new property called `assemblyDirectories`. This will be automatically set to `Distribution/Assemblies` (absolute path on your machine).
  * You can add more directories to this list.
* All assemblies in assemblies.json _AND_ dependents of any assembly will be searched for in the directories specified by `assemblyDirectories`.
This commit is contained in:
Kamron Batman 2021-09-03 23:35:44 -07:00 committed by GitHub
parent 0d1fffd9fc
commit 54e56d2fc1
No known key found for this signature in database
GPG key ID: 4AEE18F83AFDEB23
5 changed files with 67 additions and 9 deletions

View file

@ -29,13 +29,71 @@ namespace Server
private static TypeCache m_NullCache;
public static Assembly[] Assemblies { get; set; }
public static void LoadScripts(string[] files)
internal static Assembly AssemblyResolver(object sender, ResolveEventArgs args) =>
LoadAssemblyByAssemblyName(args.Name);
private static void EnsureAssemblyDirectories()
{
if (ServerConfiguration.AssemblyDirectories.Count == 0)
{
ServerConfiguration.AssemblyDirectories.Add(Path.Combine(Core.BaseDirectory, "Assemblies"));
ServerConfiguration.Save();
}
}
public static Assembly LoadAssemblyByAssemblyName(string fullAssemblyName)
{
var assemblyName = new AssemblyName(fullAssemblyName);
var assemblyFile = $"{assemblyName.Name}.dll";
EnsureAssemblyDirectories();
var assemblyDirectories = ServerConfiguration.AssemblyDirectories;
foreach (var assemblyDir in assemblyDirectories)
{
var assemblyPath = Path.Combine(assemblyDir, assemblyFile);
if (File.Exists(assemblyPath))
{
var assemblyNameCheck = AssemblyName.GetAssemblyName(assemblyPath);
if (assemblyNameCheck.FullName == assemblyName.FullName)
{
return AssemblyLoadContext.Default.LoadFromAssemblyPath(assemblyPath);
}
}
}
return null;
}
public static Assembly LoadAssemblyByFileName(string assemblyFile)
{
EnsureAssemblyDirectories();
var assemblyDirectories = ServerConfiguration.AssemblyDirectories;
foreach (var assemblyDir in assemblyDirectories)
{
var assemblyPath = Path.Combine(assemblyDir, assemblyFile);
if (File.Exists(assemblyPath))
{
return AssemblyLoadContext.Default.LoadFromAssemblyPath(assemblyPath);
}
}
return null;
}
public static void LoadAssemblies(string[] files)
{
var assemblies = new Assembly[files.Length];
for (var i = 0; i < files.Length; i++)
{
assemblies[i] = AssemblyLoadContext.Default.LoadFromAssemblyPath(files[i]);
var assembly = LoadAssemblyByFileName(files[i]);
if (assembly == null)
{
throw new FileNotFoundException($"Could not load {files[i]}");
}
assemblies[i] = LoadAssemblyByFileName(files[i]);
}
Assemblies = assemblies;