我正在开发一些支持使用报告模块的软件。基本上,我们不想默认发布所有报告,因为它只会造成不必要的膨胀,因此我正在寻找一种有效的方法来检查当前的exe和dll中是否有可以在运行时动态添加的有效模块。到目前为止,我已经尝试在AssemblyInfo中设置自定义属性,并用作标志,如下所示:
private void GetReportModules() {
try {
var dlls = Directory.GetFiles(Directory.GetCurrentDirectory()).Where(x => Path.GetExtension(x) == ".dll" || Path.GetExtension(x) == ".exe");
dlls = dlls.OrderBy(x => Path.GetFullPath(x)).Where(x => {
try {
return null != System.Reflection.Assembly.LoadFrom(x);
} catch (Exception) {
Console.WriteLine("Skipping {0} - does not load using reflection.", Path.GetFileName(x));
return false;
}
});
foreach (var dll in dlls) {
System.Reflection.Assembly assembly = System.Reflection.Assembly.LoadFrom(dll);
object[] attributes = assembly.GetCustomAttributes(typeof(ReportNameAttribute), false);
if (attributes.Count() > 0) {
// dynamically include the assembly as a menu item
}
}
} catch (Exception ex) { throw new GenericException(ex); }
}
问题是我实际上必须加载每个 dll 和 exe 两次,这似乎不是很有效。谁能提出一种他们以前已经完成类似事情的方法,或者一种改进我正在做的事情的方法?
如果我可以在不需要先加载程序集的情况下检查属性,那就太棒了。
反射是有代价的。 通常,如果您执行一次,则不会太昂贵(请记住缓存结果。 如果需要不时刷新它们,则可以为此使用计时器)。
如果不想加载所有程序集并进行检查,则可以使用配置文件,其中用户必须显式定义应加载的内容。
您还可以设置一个特殊的文件夹,根据定义,该文件夹应仅包含与此内容相关的dll-此文件夹中的任何内容都是您要加载的内容。