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

HicServices / RDMP / 6245535001

20 Sep 2023 07:44AM UTC coverage: 57.013%. First build
6245535001

push

github

web-flow
8.1.0 Release (#1628)

* Bump Newtonsoft.Json from 13.0.1 to 13.0.2

Bumps [Newtonsoft.Json](https://github.com/JamesNK/Newtonsoft.Json) from 13.0.1 to 13.0.2.
- [Release notes](https://github.com/JamesNK/Newtonsoft.Json/releases)
- [Commits](https://github.com/JamesNK/Newtonsoft.Json/compare/13.0.1...13.0.2)

---
updated-dependencies:
- dependency-name: Newtonsoft.Json
  dependency-type: direct:production
  update-type: version-update:semver-patch
...

Signed-off-by: dependabot[bot] <support@github.com>

* Bump NLog from 5.0.5 to 5.1.0

Bumps [NLog](https://github.com/NLog/NLog) from 5.0.5 to 5.1.0.
- [Release notes](https://github.com/NLog/NLog/releases)
- [Changelog](https://github.com/NLog/NLog/blob/dev/CHANGELOG.md)
- [Commits](https://github.com/NLog/NLog/compare/v5.0.5...v5.1.0)

---
updated-dependencies:
- dependency-name: NLog
  dependency-type: direct:production
  update-type: version-update:semver-minor
...

Signed-off-by: dependabot[bot] <support@github.com>

* Bump NLog from 5.0.5 to 5.1.0

* Fix -r flag - should have been --results-directory all along

* Bump Newtonsoft.Json from 13.0.1 to 13.0.2

* Bump YamlDotNet from 12.0.2 to 12.1.0

Bumps [YamlDotNet](https://github.com/aaubry/YamlDotNet) from 12.0.2 to 12.1.0.
- [Release notes](https://github.com/aaubry/YamlDotNet/releases)
- [Commits](https://github.com/aaubry/YamlDotNet/compare/v12.0.2...v12.1.0)

---
updated-dependencies:
- dependency-name: YamlDotNet
  dependency-type: direct:production
  update-type: version-update:semver-minor
...

Signed-off-by: dependabot[bot] <support@github.com>

* Bump Moq from 4.18.2 to 4.18.3

Bumps [Moq](https://github.com/moq/moq4) from 4.18.2 to 4.18.3.
- [Release notes](https://github.com/moq/moq4/releases)
- [Changelog](https://github.com/moq/moq4/blob/main/CHANGELOG.md)
- [Commits](https://github.com/moq/moq4/compare/v4.18.2...v4.18.3)

---
updated-dependencies:
- dependency-name: Moq
... (continued)

10732 of 20257 branches covered (0.0%)

Branch coverage included in aggregate %.

48141 of 48141 new or added lines in 1086 files covered. (100.0%)

30685 of 52388 relevant lines covered (58.57%)

7387.88 hits per line

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

92.54
/Rdmp.Core/Curation/SimpleStringValueEncryption.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.Linq;
9
using System.Security.Cryptography;
10
using System.Text;
11

12
namespace Rdmp.Core.Curation;
13

14
/// <summary>
15
/// Core RDMP implementation of RSA public/private key encryption.  In order to be secure you should create a private key (See PasswordEncryptionKeyLocationUI).  If
16
/// no private key is configured then the default Key will be used (this is not secure and anyone with access to the RDMP source code could decrypt your strings - which
17
///  is open source!). Strings are encrypted based on the key file.  Note that because RSA is a good encryption technique you will get a different output (encrypted) string
18
/// value for repeated calls to Encrypt even with the same input string.
19
/// </summary>
20
public class SimpleStringValueEncryption : IEncryptStrings
21
{
22
    private readonly RSACryptoServiceProvider _turing = new();
8,409✔
23

24
    private const string Key =
25
        @"<?xml version=""1.0"" encoding=""utf-16""?>
26
<RSAParameters xmlns:xsd=""http://www.w3.org/2001/XMLSchema"" xmlns:xsi=""http://www.w3.org/2001/XMLSchema-instance"">
27
   <Exponent>AQAB</Exponent>
28
    <Modulus>sMDeszVErUmbqOxQavw5OsWpL3frccEGtTJYM8G54Fw7NK6xFVUrq79nWB6px4/B</Modulus>
29
    <P>6kcXnTVJrVuD9j6qUm+F71jIL2H92lgN</P>
30
    <Q>wSRbrdj1qGBPBnYMO5dx11gvfNCKKdWF</Q>
31
    <DP>aKdxaQzQ6Nwkyu+bbk/baNwkMOZ5W/xR</DP>
32
    <DQ>B/B8rErM3l0HIpbbrd9t2JJRcWoJI+sZ</DQ>
33
    <InverseQ>NFv4Z26nbMpOkOcAnO3rktoMffza+3Ul</InverseQ>
34
    <D>Y8zC8dUF7gI9zeeAkKfReInauV6wpg4iVh7jaTDN5DAmKFURTAyv6Il6LEyr07JB</D>
35
</RSAParameters>";
36

37
    public SimpleStringValueEncryption(string parameters)
8,409✔
38
    {
39
        _turing.FromXmlString(parameters ?? Key);
8,409✔
40
    }
8,409✔
41

42
    /// <summary>
43
    /// Encrypt the payload using a new AES key and IV.  The AES key is then encrypted using the RSA public key and the IV is prepended to the encrypted payload.
44
    /// A prefix '$js1$' is added to the encrypted string to indicate that it is encrypted using the new (2023) RDMP default encryption algorithm.
45
    /// </summary>
46
    /// <returns></returns>
47
    public string Encrypt(string toEncrypt)
48
    {
49
        // Fall back on bad encryption if no private key is configured
50
        if (_turing.KeySize < 1024)
110✔
51
            return string.Join('-',
108✔
52
                _turing.Encrypt(Encoding.UTF8.GetBytes(toEncrypt), false).Select(octet => octet.ToString("X2")));
5,196✔
53
        using var aes = Aes.Create();
2✔
54
        aes.KeySize = 256;
2✔
55
        aes.GenerateIV();
2✔
56
        aes.GenerateKey();
2✔
57
        var cipherText = Convert.ToBase64String(aes.EncryptCfb(Encoding.UTF8.GetBytes(toEncrypt), aes.IV));
2✔
58
        var keyBlock = new byte[1 + aes.IV.Length + aes.Key.Length];
2✔
59
        keyBlock[0] = (byte)aes.IV.Length; // Note: this encoding assumes IV cannot exceed 255 bytes!
2✔
60
        Array.Copy(aes.IV, 0, keyBlock, 1, aes.IV.Length);
2✔
61
        Array.Copy(aes.Key, 0, keyBlock, 1 + aes.IV.Length, aes.Key.Length);
2✔
62
        var key = Convert.ToBase64String(_turing.Encrypt(keyBlock, true));
2✔
63
        return $"$js1${key}${cipherText}$";
2✔
64
    }
2✔
65

66
    /// <summary>
67
    /// Takes an encrypted byte[] (in string format as produced by BitConverter.ToString()
68
    /// </summary>
69
    /// <param name="toDecrypt"></param>
70
    /// <returns></returns>
71
    public string Decrypt(string toDecrypt)
72
    {
73
        if (toDecrypt.StartsWith($"$js1$") && toDecrypt.EndsWith("$"))
1,284✔
74
        {
75
            // Good, it's a new-style AES+RSA encrypted string
76
            var parts = toDecrypt.Split('$');
2✔
77
            if (parts.Length != 5)
2!
78
                throw new CryptographicException(
×
79
                    "Could not decrypt an encrypted string, it was not in the expected format of $js1$<base64key>$<base64ciphertext>$");
×
80
            var keyBlock = _turing.Decrypt(Convert.FromBase64String(parts[2]), true);
2✔
81
            var ivLength = keyBlock[0];
2✔
82
            var iv = new byte[ivLength];
2✔
83
            var key = new byte[keyBlock.Length - 1 - ivLength];
2✔
84
            Array.Copy(keyBlock, 1, iv, 0, ivLength);
2✔
85
            Array.Copy(keyBlock, 1 + ivLength, key, 0, key.Length);
2✔
86
            var cipherText = Convert.FromBase64String(parts[3]);
2✔
87
            using var aes = Aes.Create();
2✔
88
            aes.KeySize = 256;
2✔
89
            aes.IV = iv;
2✔
90
            aes.Key = key;
2✔
91
            return Encoding.UTF8.GetString(aes.DecryptCfb(cipherText, aes.IV));
2✔
92
        }
93

94
        try
95
        {
96
            return Encoding.UTF8.GetString(_turing.Decrypt(ByteConverterGetBytes(toDecrypt), false));
1,282✔
97
        }
98
        catch (CryptographicException e)
2✔
99
        {
100
            throw new CryptographicException(
2✔
101
                "Could not decrypt an encrypted string, possibly you are trying to decrypt it after having changed the PrivateKey to a different one than at the time it was encrypted?",
2✔
102
                e);
2✔
103
        }
104
    }
1,282✔
105

106
    private static byte[] ByteConverterGetBytes(string encodedstring)
107
    {
108
        var arr = encodedstring.Split('-');
1,282✔
109
        var array = new byte[arr.Length];
1,282✔
110

111
        for (var i = 0; i < arr.Length; i++)
125,636✔
112
            array[i] = Convert.ToByte(arr[i], 16);
61,536✔
113

114
        return array;
1,282✔
115
    }
116

117
    public bool IsStringEncrypted(string value)
118
    {
119
        return value != null && !string.IsNullOrWhiteSpace(value) &&
1,865!
120
               (value.StartsWith("$js1$") || value.Count(c => c == '-') >= 47);
254,846✔
121
    }
122
}
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