From d62669794225537cecd9b74221863c23adc50a74 Mon Sep 17 00:00:00 2001 From: Natalia Portillo Date: Thu, 5 Oct 2023 13:47:51 +0100 Subject: [PATCH] Move most of `PluginBase` logic into `Aaru.Commontypes`. --- Aaru.CommonTypes.csproj | 1 + PluginRegister.cs | 199 ++++++++++++++++++++++++++++++++++++++++ 2 files changed, 200 insertions(+) create mode 100644 PluginRegister.cs diff --git a/Aaru.CommonTypes.csproj b/Aaru.CommonTypes.csproj index e073009..36105ec 100644 --- a/Aaru.CommonTypes.csproj +++ b/Aaru.CommonTypes.csproj @@ -43,6 +43,7 @@ + diff --git a/PluginRegister.cs b/PluginRegister.cs new file mode 100644 index 0000000..ed15d05 --- /dev/null +++ b/PluginRegister.cs @@ -0,0 +1,199 @@ +// /*************************************************************************** +// Aaru Data Preservation Suite +// ---------------------------------------------------------------------------- +// +// Filename : PluginRegister.cs +// Author(s) : Natalia Portillo +// +// Component : Common types. +// +// --[ Description ] ---------------------------------------------------------- +// +// Gets lists of all known plugins. +// +// --[ License ] -------------------------------------------------------------- +// +// This program is free software: you can redistribute it and/or modify +// it under the terms of the GNU General Public License as +// published by the Free Software Foundation, either version 3 of the +// License, or (at your option) any later version. +// +// This program is distributed in the hope that it will be useful, +// but WITHOUT ANY WARRANTY; without even the implied warranty of +// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +// GNU General Public License for more details. +// +// You should have received a copy of the GNU General Public License +// along with this program. If not, see . +// +// ---------------------------------------------------------------------------- +// Copyright © 2011-2023 Natalia Portillo +// ****************************************************************************/ + +using System; +using System.Collections.Generic; +using System.Linq; +using Aaru.CommonTypes.Interfaces; +using Microsoft.Extensions.DependencyInjection; + +namespace Aaru.CommonTypes; + +public class PluginRegister +{ + static PluginRegister _instance; + /// List of all archive formats + public readonly SortedDictionary Archives; + /// List of byte addressable image plugins + public readonly SortedDictionary ByteAddressableImages; + /// List of all filesystem plugins + public readonly SortedDictionary Filesystems; + /// List of filter plugins + public readonly SortedDictionary Filters; + /// List of floppy image plugins + public readonly SortedDictionary FloppyImages; + /// List of all media image plugins + public readonly SortedDictionary MediaImages; + /// List of all partition plugins + public readonly SortedDictionary Partitions; + /// List of read-only filesystem plugins + public readonly SortedDictionary ReadOnlyFilesystems; + /// List of writable floppy image plugins + public readonly SortedDictionary WritableFloppyImages; + /// List of writable media image plugins + public readonly SortedDictionary WritableImages; + IServiceProvider _serviceProvider; + IServiceCollection _services; + + PluginRegister() + { + Filters = new SortedDictionary(); + Filesystems = new SortedDictionary(); + ReadOnlyFilesystems = new SortedDictionary(); + Partitions = new SortedDictionary(); + MediaImages = new SortedDictionary(); + WritableImages = new SortedDictionary(); + FloppyImages = new SortedDictionary(); + WritableFloppyImages = new SortedDictionary(); + Archives = new SortedDictionary(); + ByteAddressableImages = new SortedDictionary(); + } + + /// List of checksum plugins + public SortedDictionary Checksums + { + get + { + SortedDictionary checksums = new(); + foreach(IChecksum plugin in _serviceProvider.GetServices()) + checksums.Add(plugin.Name.ToLower(), plugin); + + return checksums; + } + } + + /// Gets a singleton with all the known plugins + public static PluginRegister Singleton + { + get + { + if(_instance != null) + return _instance; + + _instance = new PluginRegister + { + _services = new ServiceCollection() + }; + + _instance._serviceProvider = _instance._services.BuildServiceProvider(); + + return _instance; + } + } + + + /// + /// Replaces registered plugins list of this instance with the new ones provided by the providen registrators. + /// + /// List of plugin registrators as obtained from the assemblies that implement them. + public void InitPlugins(IEnumerable registrators) + { + _services = new ServiceCollection(); + + foreach(IPluginRegister registrator in registrators) + AddPlugins(registrator); + + _instance._serviceProvider = _instance._services.BuildServiceProvider(); + } + + /// Adds plugins to the central plugin register + /// Plugin register + void AddPlugins(IPluginRegister pluginRegister) + { + pluginRegister.RegisterChecksumPlugins(_services); + + foreach(Type type in pluginRegister.GetAllFilesystemPlugins() ?? Enumerable.Empty()) + { + if(Activator.CreateInstance(type) is IFilesystem plugin && !Filesystems.ContainsKey(plugin.Name.ToLower())) + Filesystems.Add(plugin.Name.ToLower(), type); + } + + foreach(Type type in pluginRegister.GetAllFilterPlugins() ?? Enumerable.Empty()) + { + if(Activator.CreateInstance(type) is IFilter plugin && !Filters.ContainsKey(plugin.Name.ToLower())) + Filters.Add(plugin.Name.ToLower(), type); + } + + foreach(Type type in pluginRegister.GetAllFloppyImagePlugins() ?? Enumerable.Empty()) + { + if(Activator.CreateInstance(type) is IFloppyImage plugin && + !FloppyImages.ContainsKey(plugin.Name.ToLower())) + FloppyImages.Add(plugin.Name.ToLower(), type); + } + + foreach(Type type in pluginRegister.GetAllMediaImagePlugins() ?? Enumerable.Empty()) + { + if(Activator.CreateInstance(type) is IMediaImage plugin && !MediaImages.ContainsKey(plugin.Name.ToLower())) + MediaImages.Add(plugin.Name.ToLower(), type); + } + + foreach(Type type in pluginRegister.GetAllPartitionPlugins() ?? Enumerable.Empty()) + { + if(Activator.CreateInstance(type) is IPartition plugin && !Partitions.ContainsKey(plugin.Name.ToLower())) + Partitions.Add(plugin.Name.ToLower(), type); + } + + foreach(Type type in pluginRegister.GetAllReadOnlyFilesystemPlugins() ?? Enumerable.Empty()) + { + if(Activator.CreateInstance(type) is IReadOnlyFilesystem plugin && + !ReadOnlyFilesystems.ContainsKey(plugin.Name.ToLower())) + ReadOnlyFilesystems.Add(plugin.Name.ToLower(), type); + } + + foreach(Type type in pluginRegister.GetAllWritableFloppyImagePlugins() ?? Enumerable.Empty()) + { + if(Activator.CreateInstance(type) is IWritableFloppyImage plugin && + !WritableFloppyImages.ContainsKey(plugin.Name.ToLower())) + WritableFloppyImages.Add(plugin.Name.ToLower(), type); + } + + foreach(Type type in pluginRegister.GetAllWritableImagePlugins() ?? Enumerable.Empty()) + { + if(Activator.CreateInstance(type) is IBaseWritableImage plugin && + !WritableImages.ContainsKey(plugin.Name.ToLower())) + WritableImages.Add(plugin.Name.ToLower(), type); + } + + foreach(Type type in pluginRegister.GetAllArchivePlugins() ?? Enumerable.Empty()) + { + if(Activator.CreateInstance(type) is IArchive plugin && !Archives.ContainsKey(plugin.Name.ToLower())) + Archives.Add(plugin.Name.ToLower(), type); + } + + foreach(Type type in pluginRegister.GetAllByteAddressablePlugins() ?? Enumerable.Empty()) + { + if(Activator.CreateInstance(type) is IByteAddressableImage plugin && + !ByteAddressableImages.ContainsKey(plugin.Name.ToLower())) + ByteAddressableImages.Add(plugin.Name.ToLower(), type); + } + } +} \ No newline at end of file