Warning: file_get_contents(/data/phpspider/zhask/data//catemap/1/dart/3.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
C# 自定义AssemblyLoadContext无法加载Microsoft.AspNetCore.Components_C#_Asp.net Core_.net Core - Fatal编程技术网

C# 自定义AssemblyLoadContext无法加载Microsoft.AspNetCore.Components

C# 自定义AssemblyLoadContext无法加载Microsoft.AspNetCore.Components,c#,asp.net-core,.net-core,C#,Asp.net Core,.net Core,编辑:我已将该问题的源代码上载到GitHub,如果您想下载: 我有一个.NET Core 3.0控制台应用程序,它引用了一个带有单个接口的.NET标准2.0类库(IModule)。我还有一个ASP.NET Core 3.0应用程序,它引用了相同的.NET标准2.0类库并实现了接口(模块:IModule) 我正在尝试使用自定义AssemblyLoadContext和公共类库接口(IModule)从.NET Core控制台应用程序加载ASP.NET Core程序集。。。一个简单的插件系统 不幸的是,

编辑:我已将该问题的源代码上载到GitHub,如果您想下载:

我有一个.NET Core 3.0控制台应用程序,它引用了一个带有单个接口的.NET标准2.0类库(IModule)。我还有一个ASP.NET Core 3.0应用程序,它引用了相同的.NET标准2.0类库并实现了接口(模块:IModule)

我正在尝试使用自定义AssemblyLoadContext和公共类库接口(IModule)从.NET Core控制台应用程序加载ASP.NET Core程序集。。。一个简单的插件系统

不幸的是,ASP.NET核心模块/插件在加载(AssemblyName)的ALC覆盖功能中失败,出现以下异常:

无法加载文件或程序集“Microsoft.AspNetCore.Components,版本=3.0.0.0,区域性=中性,PublicKeyToken=adb9793829ddae60”。系统找不到指定的文件。

当我尝试使用不同的项目类型(例如.NET核心控制台应用程序或.NET标准2.0类库)时,模块/插件会按预期加载

以下是控制台应用程序代码:


using NetStandardCommon;
using System;
using System.IO;

namespace NetCoreConsoleApp
{
    class Program
    {
        static void Main(string[] args)
        {
            LoadNetCoreModule();
            LoadAspNetCoreModule();
        }

        static void LoadNetCoreModule()
        {
            //Works!
            FileInfo asm = new FileInfo(@"..\..\..\..\NetCoreModule\bin\debug\netcoreapp3.0\NetCoreModule.dll");
            var moduleDirectory = asm.DirectoryName;

            ModuleAssemblyLoadContext context = new ModuleAssemblyLoadContext(asm.Name, moduleDirectory, typeof(IModule));
            context.Scan();

            foreach (var module in context.GetImplementations<IModule>())
            {
                module.Start();
            }
        }

        static void LoadAspNetCoreModule()
        {
            //Fails!
            FileInfo asm = new FileInfo(@"..\..\..\..\AspNetCoreApp\bin\debug\netcoreapp3.0\AspNetCoreApp.dll");
            var moduleDirectory = asm.DirectoryName;

            ModuleAssemblyLoadContext context = new ModuleAssemblyLoadContext(asm.Name, moduleDirectory, typeof(IModule));
            context.Scan();

            foreach (var module in context.GetImplementations<IModule>())
            {
                module.Start();
            }
        }
    }
}



对于为.net核心插件系统加载/卸载程序集的可能性,我感到很兴奋,但我正在努力克服这个障碍。我缺少什么?

大约一个月前,我在将程序集加载到SQL server时遇到了这个问题。是否使用虚拟驱动器存储程序集?我发现我们的共享驱动器实际驱动器路径是E驱动器,而不是映射到我的计算机上的P驱动器。我实际上是连接到它的,所以我必须给出真正的驱动器路径,该路径以E而不是P开头。此外,您的程序可能也将其映射到了错误的驱动器。我会检查这一点,如果这对我没有帮助的话,我还有3-4件事情要做,以解决这个问题

大约一个月前,我在将程序集加载到SQL server时遇到了这个问题。是否使用虚拟驱动器存储程序集?我发现我们的共享驱动器实际驱动器路径是E驱动器,而不是映射到我的计算机上的P驱动器。我实际上是连接到它的,所以我必须给出真正的驱动器路径,该路径以E而不是P开头。此外,您的程序可能也将其映射到了错误的驱动器。我会检查这一点,如果这对我没有帮助的话,我还有3-4件事情要做,以解决这个问题

我相信库可能还需要在目标框架设置为.NetCore 3.0(netcoreapp3.0)的情况下构建。

我相信库可能还需要在目标框架设置为.NetCore 3.0(netcoreapp3.0)的情况下构建。

想法不错,但所有项目/程序集都在本地C驱动程序上,但是所有项目/程序集都在本地C驱动器上。我尝试将公共库(ClassLibrary1)切换到目标netcoreapp3.0,而不是netstandard2.0。不幸的是,出现了相同的错误。我尝试将公共库(ClassLibrary1)切换到目标netcoreapp3.0,而不是netstandard2.0。不幸的是,同样的错误也发生了。
using System;
using System.Collections.Generic;
using System.IO;
using System.Reflection;
using System.Runtime.Loader;
using System.Linq;

namespace NetCoreConsoleApp
{
    public class ModuleAssemblyLoadContext : AssemblyLoadContext
    {
        private List<Assembly> _loaded;
        private Dictionary<string, Assembly> _shared;

        private string _path;

        private AssemblyDependencyResolver _resolver;

        public ModuleAssemblyLoadContext(string name, string path, params Type[] sharedTypes) : base(name)
        {
            _path = path;
            _resolver = new AssemblyDependencyResolver(_path);

            _loaded = new List<Assembly>();
            _shared = new Dictionary<string, Assembly>();

            if (sharedTypes != null)
            {
                foreach (Type sharedType in sharedTypes)
                {
                    _shared[Path.GetFileName(sharedType.Assembly.Location)] = sharedType.Assembly;
                }
            }
        }

        public void Scan()
        {
            foreach (string dll in Directory.EnumerateFiles(_path, "*.dll"))
            {
                var file = Path.GetFileName(dll);

                if (_shared.ContainsKey(file))
                {
                    continue;
                }

                var asm = this.LoadFromAssemblyPath(dll);

                _loaded.Add(asm);
            }
        }

        public IEnumerable<T> GetImplementations<T>()
        {
            return _loaded
                .SelectMany(a => a.GetTypes())
                .Where(t => typeof(T).IsAssignableFrom(t))
                .Select(t => Activator.CreateInstance(t))
                .Cast<T>();
        }

        protected override Assembly Load(AssemblyName assemblyName)
        {
            string filename = $"{assemblyName.Name}.dll";
            if (_shared.ContainsKey(filename))
            {
                return _shared[filename];
            }

            string assemblyPath = _resolver.ResolveAssemblyToPath(assemblyName);
            if (assemblyPath != null)
            {
                return LoadFromAssemblyPath(assemblyPath);
            }

            return null;
        }

        protected override IntPtr LoadUnmanagedDll(string unmanagedDllName)
        {
            string libraryPath = _resolver.ResolveUnmanagedDllToPath(unmanagedDllName);
            if (libraryPath != null)
            {
                return LoadUnmanagedDllFromPath(libraryPath);
            }

            return IntPtr.Zero;
        }
    }
}


        protected override Assembly Load(AssemblyName assemblyName)
        {
            string filename = $"{assemblyName.Name}.dll";
            if (_shared.ContainsKey(filename))
            {
                return _shared[filename];
            }

            try
            {
                if (File.Exists(@"C:\Program Files (x86)\dotnet\shared\Microsoft.AspNetCore.App\3.0.0\" + filename))
                {
                    return Assembly.LoadFrom(@"C:\Program Files (x86)\dotnet\shared\Microsoft.AspNetCore.App\3.0.0\" + filename);
                }
            }
            catch (Exception ex)
            {
                //Message displayed is 'An attempt was made to load a program with an incorrect format. (0x8007000B)'
                Console.WriteLine(ex.Message);
            }

            return Assembly.Load(assemblyName);
        }