Add CoreConfigLine
MODIFY
WalletWasabi.Tests/UnitTests/BitcoinCore/ConfigTests.cs
WalletWasabi.Tests/UnitTests/BitcoinCore/ConfigTests.cs
@@ -22,6 +22,35 @@ too =1
foo
bar
#qoo=boo";
+ var coreConfig = new CoreConfig();
+ coreConfig.TryAdd(testConfig);
+
+ var configDic = coreConfig.ToDictionary();
+
+ Assert.True(configDic.TryGetValue("foo", out string v1));
+ Assert.True(configDic.TryGetValue("too", out string v2));
+ Assert.False(configDic.TryGetValue("qoo", out _));
+ Assert.False(configDic.TryGetValue("bar", out _));
+ Assert.True(configDic.TryGetValue("foo bar", out string v3));
+
+ Assert.Equal("buz", v1);
+ Assert.Equal("1", v2);
+ Assert.Equal("buz quxx", v3);
+
+ var coreConfig2 = new CoreConfig();
+ coreConfig2.AddOrUpdate(testConfig);
+
+ var configDic2 = coreConfig2.ToDictionary();
+
+ Assert.True(configDic2.TryGetValue("foo", out string v1_2));
+ Assert.True(configDic2.TryGetValue("too", out string v2_2));
+ Assert.False(configDic2.TryGetValue("qoo", out _));
+ Assert.False(configDic2.TryGetValue("bar", out _));
+ Assert.True(configDic2.TryGetValue("foo bar", out string v3_3));
+
+ Assert.Equal("bar", v1_2);
+ Assert.Equal("1", v2_2);
+ Assert.Equal("buz quxx", v3_3);
var add1 = "moo=1";
var add2 = "foo=bar";
@@ -37,21 +66,6 @@ foo
#qoo=boo
moo = 1
too = 0";
-
- var coreConfig = new CoreConfiguration();
- coreConfig.AddOrUpdate(testConfig);
-
- var configDic = coreConfig.ToDictionary();
-
- Assert.True(configDic.TryGetValue("foo", out string v1));
- Assert.True(configDic.TryGetValue("too", out string v2));
- Assert.False(configDic.TryGetValue("qoo", out _));
- Assert.False(configDic.TryGetValue("bar", out _));
- Assert.True(configDic.TryGetValue("foo bar", out string v3));
-
- Assert.Equal("bar", v1);
- Assert.Equal("1", v2);
- Assert.Equal("buz quxx", v3);
}
}
}

ADD
WalletWasabi/BitcoinCore/CoreConfig.cs
+using System;
+using System.Collections.Generic;
+using System.Linq;
+using System.Text;
+using WalletWasabi.Helpers;
+
+namespace WalletWasabi.BitcoinCore
+{
+ public class CoreConfig
+ {
+ private List<CoreConfigLine> Lines { get; } = new List<CoreConfigLine>();
+
+ public IDictionary<string, string> ToDictionary()
+ {
+ var myDic = new Dictionary<string, string>();
+ foreach (var line in Lines)
+ {
+ if (line.HasKeyValuePair)
+ {
+ myDic.Add(line.Key, line.Value);
+ }
+ }
+
+ return myDic;
+ }
+
+ public override string ToString() => $"{string.Join(Environment.NewLine, Lines)}{Environment.NewLine}"; // Good practice to end with a newline.
+
+ /// <summary>
+ /// TryAdd and AddOrUpdate are sisters. TryAdd always considers the first occurrence of a key as valid, while AddOrUpdate considers the last occurrence of it.
+ /// </summary>
+ public void TryAdd(string configString)
+ {
+ configString = Guard.Correct(configString);
+ foreach (var line in configString.Split(new char[] { '\r', '\n' }, StringSplitOptions.None))
+ {
+ var currentLine = new CoreConfigLine(line);
+ if (currentLine.HasKeyValuePair)
+ {
+ var foundLine = Lines.FirstOrDefault(x => x.Key == currentLine.Key);
+ if (foundLine is null)
+ {
+ Lines.Add(currentLine);
+ }
+ }
+ else
+ {
+ Lines.Add(currentLine);
+ }
+ }
+ }
+
+ /// <summary>
+ /// TryAdd and AddOrUpdate are sisters. TryAdd always considers the first occurrence of a key as valid, while AddOrUpdate considers the last occurrence of it.
+ /// </summary>
+ public void AddOrUpdate(string configString)
+ {
+ configString = Guard.Correct(configString);
+ foreach (var line in configString.Split(new char[] { '\r', '\n' }, StringSplitOptions.None))
+ {
+ var currentLine = new CoreConfigLine(line);
+ if (currentLine.HasKeyValuePair)
+ {
+ var foundLine = Lines.FirstOrDefault(x => x.Key == currentLine.Key);
+ if (foundLine is null)
+ {
+ Lines.Add(currentLine);
+ }
+ else
+ {
+ Lines.Remove(foundLine);
+ Lines.Add(currentLine);
+ }
+ }
+ else
+ {
+ Lines.Add(currentLine);
+ }
+ }
+ }
+ }
+}

ADD
WalletWasabi/BitcoinCore/CoreConfigLine.cs
+using System;
+using System.Collections.Generic;
+using System.Linq;
+using System.Text;
+using WalletWasabi.Helpers;
+
+namespace WalletWasabi.BitcoinCore
+{
+ public class CoreConfigLine
+ {
+ public string Line { get; }
+ public string Key { get; } = string.Empty;
+ public string Value { get; } = string.Empty;
+ public bool HasKeyValuePair => !string.IsNullOrWhiteSpace(Key) && !string.IsNullOrWhiteSpace(Value);
+
+ public CoreConfigLine(string key, string value)
+ : this($"{Guard.NotNullOrEmptyOrWhitespace(key, value, true)} = {Guard.NotNullOrEmptyOrWhitespace(key, value, true)}")
+ {
+ }
+
+ public CoreConfigLine(string line)
+ {
+ // The point of having the line would be to not modify the original config file, but oh well, nobody would be against by removing whitespaces.
+ Line = Guard.Correct(line);
+ if (Line.Length == 0 || Line.StartsWith('#'))
+ {
+ return;
+ }
+
+ var parts = Line.Split('=', StringSplitOptions.RemoveEmptyEntries).Select(x => Guard.Correct(x)).ToArray();
+
+ if (parts.Length != 2 || parts.Any(x => x.Length == 0))
+ {
+ return;
+ }
+
+ Key = parts[0];
+ Value = parts[1];
+ }
+
+ public override string ToString() => Line;
+ }
+}

DELETE
WalletWasabi/BitcoinCore/CoreConfiguration.cs
-using System;
-using System.Collections.Generic;
-using System.Linq;
-using System.Text;
-using WalletWasabi.Helpers;
-
-namespace WalletWasabi.BitcoinCore
-{
- public class CoreConfiguration
- {
- private StringBuilder ConfigStringBuilder { get; } = new StringBuilder();
-
- public IDictionary<string, string> ToDictionary()
- {
- var myDic = new Dictionary<string, string>();
- foreach (var line in ConfigStringBuilder.ToString().Split(new char[] { '\r', '\n' }, StringSplitOptions.RemoveEmptyEntries).Select(x => Guard.Correct(x)))
- {
- if (line.Length == 0 || line.StartsWith('#'))
- {
- continue;
- }
-
- var parts = line.Split('=', StringSplitOptions.RemoveEmptyEntries).Select(x => Guard.Correct(x)).ToArray();
-
- if (parts.Length != 2 || parts.Any(x => x.Length == 0))
- {
- continue;
- }
-
- if (!myDic.TryAdd(parts[0], parts[1]))
- {
- myDic.Remove(parts[0]);
- myDic.Add(parts[0], parts[1]);
- }
- }
-
- return myDic;
- }
-
- public void AddOrUpdate(string configString)
- {
- if (ConfigStringBuilder.Length != 0)
- {
- ConfigStringBuilder.Append(Environment.NewLine);
- }
-
- ConfigStringBuilder.Append(configString);
- }
- }
-}

Add CoreConfigLine