gpt4 book ai didi

c# - 在运行时编译代码,加载到当前 appdomain 但 Type.GetType 看不到它

转载 作者:太空狗 更新时间:2023-10-29 23:04:05 26 4
gpt4 key购买 nike

我在运行时编译一些代码,然后将程序集加载到当前的应用程序域中,但是当我尝试执行 Type.GetType 时,它​​找不到类型...

下面是我编译代码的方式...

public static Assembly CompileCode(string code)
{
Microsoft.CSharp.CSharpCodeProvider provider = new CSharpCodeProvider();
ICodeCompiler compiler = provider.CreateCompiler();
CompilerParameters compilerparams = new CompilerParameters();
compilerparams.GenerateExecutable = false;
compilerparams.GenerateInMemory = false;

foreach (Assembly assembly in AppDomain.CurrentDomain.GetAssemblies())
{
try
{
string location = assembly.Location;
if (!String.IsNullOrEmpty(location))
{
compilerparams.ReferencedAssemblies.Add(location);
}
}
catch (NotSupportedException)
{
// this happens for dynamic assemblies, so just ignore it.
}
}
CompilerResults results =
compiler.CompileAssemblyFromSource(compilerparams, code);
if (results.Errors.HasErrors)
{
StringBuilder errors = new StringBuilder("Compiler Errors :\r\n");
foreach (CompilerError error in results.Errors)
{
errors.AppendFormat("Line {0},{1}\t: {2}\n",
error.Line, error.Column, error.ErrorText);
}
throw new Exception(errors.ToString());
}
else
{
AppDomain.CurrentDomain.Load(results.CompiledAssembly.GetName());
return results.CompiledAssembly;
}
}

从编译好的程序集中获取类型后,这个位就失败了,它似乎无法使用 Type.GetType 找到它....

Assembly assem = RuntimeCodeCompiler.CompileCode(code);
string typeName =
String.Format("Peverel.AppFramework.Web.GenCode.ObjectDataSourceProxy_{0}",
safeTypeName);



Type t = assem.GetType(typeName); //This works just fine..
Type doesntWork = Type.GetType(t.AssemblyQualifiedName);
Type doesntWork2 = Type.GetType(t.Name);



....

最佳答案

找到 this一段不错的代码,可确保无论您如何加载程序集,它始终可从 Type.GetType 获得。

我用于将代码编译到当前应用程序域的类现在看起来像:

public static class RuntimeCodeCompiler
{
private static volatile Dictionary<string, Assembly> cache = new Dictionary<string, Assembly>();
private static object syncRoot = new object();
static Dictionary<string, Assembly> assemblies = new Dictionary<string, Assembly>();
static RuntimeCodeCompiler()
{
AppDomain.CurrentDomain.AssemblyLoad += (sender, e) =>
{
assemblies[e.LoadedAssembly.FullName] = e.LoadedAssembly;
};
AppDomain.CurrentDomain.AssemblyResolve += (sender, e) =>
{
Assembly assembly = null;
assemblies.TryGetValue(e.Name, out assembly);
return assembly;
};

}


public static Assembly CompileCode(string code)
{

Microsoft.CSharp.CSharpCodeProvider provider = new CSharpCodeProvider();
ICodeCompiler compiler = provider.CreateCompiler();
CompilerParameters compilerparams = new CompilerParameters();
compilerparams.GenerateExecutable = false;
compilerparams.GenerateInMemory = false;



foreach (Assembly assembly in AppDomain.CurrentDomain.GetAssemblies())
{
try
{
string location = assembly.Location;
if (!String.IsNullOrEmpty(location))
{
compilerparams.ReferencedAssemblies.Add(location);
}
}
catch (NotSupportedException)
{
// this happens for dynamic assemblies, so just ignore it.
}
}


CompilerResults results =
compiler.CompileAssemblyFromSource(compilerparams, code);
if (results.Errors.HasErrors)
{
StringBuilder errors = new StringBuilder("Compiler Errors :\r\n");
foreach (CompilerError error in results.Errors)
{
errors.AppendFormat("Line {0},{1}\t: {2}\n",
error.Line, error.Column, error.ErrorText);
}
throw new Exception(errors.ToString());
}
else
{

AppDomain.CurrentDomain.Load(results.CompiledAssembly.GetName());
return results.CompiledAssembly;
}

}

public static Assembly CompileCodeOrGetFromCache(string code, string key)
{
bool exists = cache.ContainsKey(key);

if (!exists)
{

lock (syncRoot)
{
exists = cache.ContainsKey(key);

if (!exists)
{
cache.Add(key, CompileCode(code));
}
}
}

return cache[key];
}


}

关于c# - 在运行时编译代码,加载到当前 appdomain 但 Type.GetType 看不到它,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/3023900/

26 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com