You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

如何让FusionLoader从非AppBase路径加载XML Serializer程序集?

解决XML序列化程序集跨目录加载问题

问题概述

主程序Application.exe运行于C:\App\Bin目录,从C:\App\COMDLL加载C# COM组件。该COM组件依赖的COMDLL.XmlSerializers.dll已通过sgen.exe生成并存放于C:\App\COMDLL,但Fusion加载器始终仅在AppBase(C:\App\Bin)目录查找该序列化程序集。无法将序列化程序集移至AppBase目录,也无法修改Application.exe代码,仅能修改COMDLL项目。此前尝试的AssemblyResolve事件处理未生效,probing配置因目标路径非AppBase子目录无法使用。

可行解决方案

方案1:修正AssemblyResolve事件实现

原事件处理存在两处错误:返回类型不符合要求、程序集加载方式错误,修正后即可生效:

public static void RedirectDependency()
{
    // 避免重复注册事件
    if (!LibLoaded)
    {
        AppDomain.CurrentDomain.AssemblyResolve += ResolveHandler;
        LibLoaded = true;
    }
}

private static bool LibLoaded = false;

// 返回类型改为Assembly,符合事件委托要求
public static Assembly ResolveHandler(object sender, ResolveEventArgs args)
{
    var libName = new AssemblyName(args.Name);
    // 忽略大小写匹配序列化程序集名称
    if (libName.Name.EndsWith("XmlSerializers", StringComparison.OrdinalIgnoreCase))
    {
        var libPath = @"C:\App\COMDLL\COMDLL.XmlSerializers.dll";
        if (File.Exists(libPath))
        {
            // 使用LoadFrom加载指定路径的程序集
            return Assembly.LoadFrom(libPath);
        }
    }
    return null;
}

注意:需在COM组件的初始化阶段调用RedirectDependency,例如在COM类的静态构造函数中:

[ComVisible(true)]
public class YourComImplementation
{
    static YourComImplementation()
    {
        RedirectDependency();
    }

    // 你的COM方法定义...
}

方案2:使用codeBase配置元素

若允许创建或修改Application.exe.config,可添加codeBase元素直接指定序列化程序集的物理路径:

<configuration>
  <runtime>
    <assemblyBinding xmlns="urn:schemas-microsoft-com:asm.v1">
      <dependentAssembly>
        <assemblyIdentity name="COMDLL.XmlSerializers" 
                          publicKeyToken="替换为你的程序集公钥令牌" 
                          culture="neutral" />
        <codeBase version="替换为你的程序集版本号" 
                  href="file:///C:/App/COMDLL/COMDLL.XmlSerializers.dll" />
      </dependentAssembly>
    </assemblyBinding>
  </runtime>
</configuration>

可通过ildasm.exe打开COMDLL.XmlSerializers.dll查看公钥令牌和版本号。

方案3:预加载序列化程序集

在COM组件初始化时直接加载序列化程序集,提前将其载入当前AppDomain,避免后续Fusion加载器的查找操作:

[ComVisible(true)]
public class YourComImplementation
{
    static YourComImplementation()
    {
        var serializerPath = @"C:\App\COMDLL\COMDLL.XmlSerializers.dll";
        if (File.Exists(serializerPath))
        {
            Assembly.LoadFrom(serializerPath);
        }
    }

    // 你的COM方法定义...
}

方案选择建议

  • 方案1是最通用的解决方案,只要事件注册成功即可拦截所有序列化程序集的解析请求,不受配置权限限制
  • 方案2操作最简单,但需要具备修改主程序配置文件的权限
  • 方案3适合序列化程序集路径固定、版本稳定的场景,实现成本低

内容的提问来源于stack exchange,提问作者user3017167

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.06.19 13:47:30