8

I have an application that needs to store data. Currently, I am using the built-in Application Settings to do it, but it only gives me two choices: application and user scopes. Ideally, I want a "local" scope that allows the application to run under another user and still find its data rather than recreate it for that user. The application scope can do this, but it's read only. The application data will be changed by the user. It's OK if only the administrator is allowed to make changes to the data.

As you probably can guess, I have an administration tool that allows the user to change the data and windows service runner that reads the data and does something with it. It would be great if the windows service runner access the data created by the administration tool.

ATL_DEV
  • 9,256
  • 11
  • 60
  • 102
  • What kind of data are you storing? User preferences, etc or data used by the application? – gooch May 04 '10 at 18:51
  • I'm storing incredibly simple data. There will almost never be a situation where there are more than 10 objects stored. The data are task settings (i.e. name, directory, plugin to use, etc.) that will be run in a service that will exist outside my admin tool. It is imperative that the service can find this information. Settings would be ideal, but accessing it from the service seems like it will be difficult. How would I do this? – ATL_DEV May 05 '10 at 02:32

2 Answers2

8

If the data is very, very simple, and you need it to be readable by other applications or users (with appropriate permissions), I would probably choose to store it in an XML file or even a plain-text file inside the user's Application Data folder, which would be obtained via Environment.GetFolderPath. An example for saving might look like:

using System.IO;
using System.Xml.Linq;

string settingsDirectory = Environment.GetFolderPath(Environment.SpecialFolder.ApplicationData);
if (!Directory.Exists(settingsDirectory))
    Directory.CreateDirectory(settingsDirectory);
string fileName = "tasks.xml";
string settingsPath = Path.Combine(settingsDirectory, fileName);
XDocument settingsDoc = new XDocument(
    new XElement("Tasks",
        new XElement("Task",
            new XElement("Name", "Make Breakfast"),
            new XElement("Location", @"C:\Program Files\MyApp\Plugins"),
            new XElement("FileName", "breakfast.dll"))));
// ... etc.
settingsDoc.Save(settingsPath);

That's it - settings saved! You can load them again with XDocument.Load.

Orwellophile
  • 13,235
  • 3
  • 69
  • 45
Aaronaught
  • 120,909
  • 25
  • 266
  • 342
  • Thanks! This is great. Is there anyway to make this work like settings.settings where its strongly typed? I would love to be able to do something like this: Settings.Default.Tasks= TaskList; Settings.Default.Save(); – ATL_DEV May 05 '10 at 15:38
  • @joe: If that's what you want, you should look into the `XmlSerializer` class and `System.Xml.Serialization` namespace. You can use these to take a class structure and "automatically" serialize to/from XML. You definitely *can't* make this part of the actual `Settings` object; if you want to use the `Settings` then use the `Settings`. If you just want it to be a singleton object like `Properties.Settings.Default`, then that's possible but you'd have to implement the pattern yourself. – Aaronaught May 05 '10 at 16:19
  • Oh btw. Should I use the CommonApplicationData folder instead of ApplicationData? The documentation says "The directory that serves as a common repository for application-specific data that is used by all users." – ATL_DEV May 05 '10 at 16:22
  • 1
    @joe: You *can*, but you'll need to run your app with admin privileges for it to work, so I wouldn't really recommend it unless you *actually* need the *same* settings to be shared by *all* users. If the data is supposed to be unique per user, that's the wrong place. – Aaronaught May 05 '10 at 18:08
0

Sounds like you want to store it in a database, the question is local or on a network or not. The answer also depends on what kind of data you are storing, how your app is distributed, and other factors.

Oh, and BTW we could help you way better if you specify your platform (preferably with a tag)--silverlight, wpf, winforms, asp.net, console, etc.

Muad'Dib
  • 28,542
  • 5
  • 55
  • 68
  • Sorry, I thought the .NET tag was sufficient for specifying the platform. Anyway, I think a database may be overkill for my data persistence needs. This is going to be a WPF application. – ATL_DEV May 05 '10 at 02:28
  • its OK, .NET can cover all of the platforms I listed, and ones I haven't. – Muad'Dib May 05 '10 at 04:26