• Home
  • Features
  • Pricing
  • Docs
  • Announcements
  • Sign In

HicServices / RDMP / 7528620232

15 Jan 2024 12:09PM UTC coverage: 56.76% (-0.02%) from 56.776%
7528620232

push

github

JFriel
fix bad merge

10725 of 20361 branches covered (0.0%)

Branch coverage included in aggregate %.

30655 of 52543 relevant lines covered (58.34%)

7292.26 hits per line

Source File
Press 'n' to go to next uncovered line, 'b' for previous

12.16
/Rdmp.Core/Curation/Data/LoadModuleAssembly.cs
1
// Copyright (c) The University of Dundee 2018-2019
2
// This file is part of the Research Data Management Platform (RDMP).
3
// RDMP 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.
4
// RDMP 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.
5
// You should have received a copy of the GNU General Public License along with RDMP. If not, see <https://www.gnu.org/licenses/>.
6

7
using System;
8
using System.Collections.Generic;
9
using System.IO;
10
using System.Linq;
11
using ICSharpCode.SharpZipLib.Zip;
12
using Rdmp.Core.ReusableLibraryCode.Checks;
13

14
namespace Rdmp.Core.Curation.Data;
15

16
/// <summary>
17
/// This entity wraps references to plugin .nupkg files on disk.
18
/// </summary>
19
public sealed class LoadModuleAssembly
20
{
21
    private static readonly bool IsWin = AppDomain.CurrentDomain.GetAssemblies()
4✔
22
        .Any(static a => a.FullName?.StartsWith("Rdmp.UI", StringComparison.Ordinal) == true);
356!
23

24
    private static readonly string PluginsList = Path.Combine(AppDomain.CurrentDomain.BaseDirectory, "rdmpplugins.txt");
4✔
25

26
    internal static readonly List<LoadModuleAssembly> Assemblies = [];
4✔
27
    private readonly FileInfo _file;
28

29
    private LoadModuleAssembly(FileInfo file)
×
30
    {
31
        _file = file;
×
32
    }
×
33

34
    /// <summary>
35
    /// List the plugin files to load
36
    /// </summary>
37
    /// <returns></returns>
38
    internal static IEnumerable<string> PluginFiles()
39
    {
40
        return File.Exists(PluginsList)
16!
41
            ? File.ReadAllLines(PluginsList)
16✔
42
                .Select(static name => Path.Combine(AppDomain.CurrentDomain.BaseDirectory, name))
×
43
            : Directory.EnumerateFiles(AppDomain.CurrentDomain.BaseDirectory, "*.nupkg");
16✔
44
    }
45

46
    /// <summary>
47
    /// Unpack the plugin DLL files, excluding any Windows UI specific dlls when not running a Windows GUI
48
    /// </summary>
49
    internal static IEnumerable<(string, MemoryStream)> GetContents(string path)
50
    {
51
        var info = new FileInfo(path);
×
52
        if (!info.Exists || info.Length < 100) yield break; // Ignore missing or empty files
×
53

54
        var pluginStream = info.OpenRead();
×
55
        if (!pluginStream.CanSeek)
×
56
            throw new ArgumentException("Seek needed", nameof(path));
×
57

58
        Assemblies.Add(new LoadModuleAssembly(info));
×
59

60
        using var zip = new ZipFile(pluginStream);
×
61
        foreach (var e in zip.Cast<ZipEntry>()
×
62
                     .Where(static e => e.IsFile && e.Name.EndsWith(".dll", StringComparison.OrdinalIgnoreCase) &&
63
                                        (IsWin || !e.Name.Contains("/windows/"))))
64
        {
65
            using var s = zip.GetInputStream(e);
×
66
            using var ms2 = new MemoryStream();
×
67
            s.CopyTo(ms2);
×
68
            ms2.Position = 0;
×
69
            yield return (e.Name, ms2);
×
70
        }
×
71
    }
×
72

73
    /// <summary>
74
    /// Copy the plugin nupkg to the given directory
75
    /// </summary>
76
    /// <param name="downloadDirectory"></param>
77
    public void DownloadAssembly(DirectoryInfo downloadDirectory)
78
    {
79
        if (!downloadDirectory.Exists)
×
80
            downloadDirectory.Create();
×
81
        var targetFile = Path.Combine(downloadDirectory.FullName, _file.Name);
×
82
        _file.CopyTo(targetFile, true);
×
83
    }
×
84

85
    /// <summary>
86
    /// Delete the plugin file from disk, and remove it from rdmpplugins.txt if in use
87
    /// </summary>
88
    public void Delete()
89
    {
90
        _file.Delete();
×
91
        if (!File.Exists(PluginsList)) return;
×
92

93
        var tmp = $"{PluginsList}.tmp";
×
94
        File.WriteAllLines(tmp, File.ReadAllLines(PluginsList).Where(l => !l.Contains(_file.Name)));
×
95
        File.Move(tmp, PluginsList, true);
×
96
    }
×
97

98
    public override string ToString() => _file.Name;
×
99

100
    public static void UploadFile(ICheckNotifier checkNotifier, FileInfo toCommit)
101
    {
102
        try
103
        {
104
            toCommit.CopyTo(Path.Combine(AppDomain.CurrentDomain.BaseDirectory, toCommit.Name), true);
×
105
            if (!File.Exists(PluginsList)) return;
×
106

107
            // Now the tricky bit: add this new file, and remove any other versions of the same
108
            // e.g. adding DummyPlugin-1.2.3 should delete DummyPlugin-2.0 and DummyPlugin-1.0 if present
109
            var list = File.ReadAllLines(PluginsList);
×
110
            var tmp = $"{PluginsList}.tmp";
×
111

112
            var versionPos = toCommit.Name.IndexOf('-');
×
113
            if (versionPos != -1)
×
114
            {
115
                var stub = toCommit.Name[..(versionPos + 1)];
×
116
                list = list.Where(l => !l.StartsWith(stub, StringComparison.OrdinalIgnoreCase)).ToArray();
×
117
            }
118

119
            File.WriteAllLines(tmp, list.Union([toCommit.Name]));
×
120
            File.Move(tmp, PluginsList, true);
×
121
        }
×
122
        catch (Exception e)
×
123
        {
124
            checkNotifier.OnCheckPerformed(new CheckEventArgs($"Failed copying plugin {toCommit.Name}",
×
125
                CheckResult.Fail, e));
×
126
            throw;
×
127
        }
128
    }
×
129
}
STATUS · Troubleshooting · Open an Issue · Sales · Support · CAREERS · ENTERPRISE · START FREE · SCHEDULE DEMO
ANNOUNCEMENTS · TWITTER · TOS & SLA · Supported CI Services · What's a CI service? · Automated Testing

© 2025 Coveralls, Inc