5

I want a configuration file in my .net core 3.1 winforms project. I have the following working to read the file

using Microsoft.Extensions.Configuration;
using System;
using System.Text;
using System.Windows.Forms;
using System.Xml;
namespace FeedRead
{

    public partial class Form1 : Form
    {

        private ConfigurationBuilder configuration;
        public Form1()
        {
            configuration = new ConfigurationBuilder();
            configuration.SetBasePath(System.IO.Directory.GetCurrentDirectory());
            configuration.AddJsonFile(path: "appsettings.json", optional: false, reloadOnChange: true);
            configuration.Build();
        }

but how do I save the configuration when I have made changes?

I tried the following but don't know how to complete it.

    private void Form1_FormClosing(object sender, System.Windows.Forms.FormClosingEventArgs e)
    {

        configuration.Properties.Add("col1Width", listView1.Columns[0].Width);
        var extn = configuration as Microsoft.Extensions.Configuration.IConfigurationBuilder; // not sure about
        var provider = extn.GetFileProvider();
        var info = provider.GetFileInfo(subpath: "appsettings.json"); // not sure about
        // how do i save?

    }
Kirsten
  • 15,730
  • 41
  • 179
  • 318
  • You need to write the configuration back to disk as JSON. Which (if I remember correctly) is as easy as calling `Save()` on the configuration object – MindSwipe Dec 20 '19 at 10:15
  • configuration no longer has this property. – Kirsten Dec 20 '19 at 21:03
  • 2
    These articles may be helpful. [How to update values into appsetting.json?](https://stackoverflow.com/q/40970944/9014308), [Save Changes of IConfigurationRoot sections to its *.json file in .net Core 2.2](https://stackoverflow.com/q/57978535/9014308) – kunif Dec 21 '19 at 04:48
  • 2
    I feel like it should be easier! – Kirsten Dec 21 '19 at 08:11

2 Answers2

3

There is a discussion about why it has not been added . On GitHub

I asked a related question on binding to a configuration.

Then I used the following to implement a save

  public static void SaveConfiguration(FeedReadConfiguration configuration)
    {
        var props = DictionaryFromType(configuration); 
        foreach (var prop in props)
        {
            SetAppSettingValue(prop.Key,prop.Value.ToString());
        }

    }

    private static Dictionary<string, object> DictionaryFromType(object atype)
    {
        if (atype == null) return new Dictionary<string, object>();
        Type t = atype.GetType();
        PropertyInfo[] props = t.GetProperties();
        Dictionary<string, object> dict = new Dictionary<string, object>(); // reflection
        foreach (PropertyInfo prp in props)
        {
            object value = prp.GetValue(atype, new object[] { });
            dict.Add(prp.Name, value);
        }
        return dict;
    }

Where SetAppSettingsValue comes from this question

   public static void SetAppSettingValue(string key, string value, string appSettingsJsonFilePath = null)
    {
        if (appSettingsJsonFilePath == null)
        {
            appSettingsJsonFilePath = System.IO.Path.Combine(System.AppContext.BaseDirectory, "appsettings.json");
        }

        var json = System.IO.File.ReadAllText(appSettingsJsonFilePath);
        dynamic jsonObj = Newtonsoft.Json.JsonConvert.DeserializeObject<Newtonsoft.Json.Linq.JObject>(json);

        jsonObj[key] = value;

        string output = Newtonsoft.Json.JsonConvert.SerializeObject(jsonObj, Newtonsoft.Json.Formatting.Indented);

        System.IO.File.WriteAllText(appSettingsJsonFilePath, output);
    }
Kirsten
  • 15,730
  • 41
  • 179
  • 318
1

In your Startup.cs file, add the following:

    private IConfiguration Configuration { get; }

    public Startup(IWebHostEnvironment env)
    {
        var builder = new ConfigurationBuilder()
            .SetBasePath(env.ContentRootPath)
            .AddJsonFile("appsettings.json", optional: false, reloadOnChange: true)
            .AddEnvironmentVariables();
        Configuration = builder.Build();
    }

    public void ConfigureServices(IServiceCollection services)
    {
        _appSettings = Configuration.GetSection("AppSettings").Get<AppSettings>();
        services.AddSingleton(_appSettings);

        ...
    }
James LoForti
  • 1,456
  • 1
  • 8
  • 8