Example #1
0
        public static IEnumerable <string> FindPluginAssemblies(string pluginFolder, bool includeFramework = false)
        {
            // Storage to ensure not loading the same assembly twice and optimize calls to GetAssemblies()
            IDictionary <string, bool> loaded = new ConcurrentDictionary <string, bool>();

            CacheAlreadyLoadedAssemblies(loaded, includeFramework);

            if (!IsPluginFolderNameSupplied())
            {
                yield break;
            }

            pluginFolder = Path.GetFullPath(pluginFolder);

            if (!Directory.Exists(pluginFolder))
            {
                _logger.Debug($"Plugin folder '{pluginFolder}' does not exist. No plugins will be loaded.");
                yield break;
            }

            var assemblies = Directory.GetFiles(pluginFolder, "*.dll", SearchOption.AllDirectories);

            var pluginAssemblyLoadContext = new PluginAssemblyLoadContext();

            try
            {
                foreach (var assemblyPath in assemblies)
                {
                    var assembly = pluginAssemblyLoadContext.LoadFromAssemblyPath(assemblyPath);

                    if (!HasPlugin(assembly))
                    {
                        continue;
                    }

                    string assemblyDirectory = Path.GetDirectoryName(assemblyPath);
                    var    assemblyMetadata  = ReadAssemblyMetadata(assembly);

                    if (IsExtensionAssembly(assemblyMetadata))
                    {
                        var validator        = GetExtensionValidator();
                        var validationResult = validator.ValidateObject(assemblyDirectory);

                        if (!validationResult.Any())
                        {
                            yield return(assembly.Location);
                        }
                        else
                        {
                            _logger.Warn($"Assembly: {assembly.GetName()} - {string.Join(",", validationResult)}");
                        }
                    }
                    else if (IsProfileAssembly(assemblyMetadata))
                    {
                        yield return(assembly.Location);
                    }
                }
            }
            finally
            {
                pluginAssemblyLoadContext.Unload();
            }