I'm making a simple winforms application in C#, with VS2010. My winforms design contains a FileSystemWatcher, which fires a pile of code when a file is created.
My problem is that the path for FileSystemWatcher needs to be defined prior to the program running, as it won't always be the same.
I have a string called startPath which I'd like to use, but it would appear that I can't just add this to the "path" field in the FileSystemWatcher properties in my design.
I was able to get it to work if I edited my form1.designer.cs, but as I swiftly learned this code is regenerated even if a different component of the form is edited!
As you might have guessed, I'm still very much learning C#.net (about a week in), and am by no means experienced! If I'm missing something stupid, please point it out!
The FileSystemWatcher has a path property that can be used to change the path after the FileSystemWatcher object is initialized. Otherwise, you'll have to re-setup your watcher if you use the constructor to set the path to watch.
FileSystemWatcher.Path Property
Storing the path itself can be easily done through the Application Settings as mentioned by #leppie
Reference for settings:
Application Settings Overview
Using Settings in C#
Saving User Settings in Winform Application
I assigned my user defined string as the path at run time like so:
In my form1.cs:
protected override void OnActivated(EventArgs e)
{
base.OnActivated(e);
fileSystemWatcher1.Path = inputPath;
}
I think this is an ok way of doing it (it seems to be working!), the string "inputPath" is defined earlier by getting the corresponding setting from my configuration file. It just didn't seem to want to play nice if I placed it settings.cs.
Add the required path to the appSettings part of your app.config file:
<?xml version="1.0" encoding="utf-8"?>
<configuration>
<appSettings>
<add key="watcherPath" value="\\myPC\myShare\myFolder\" />
</appSettings>
</configuration>
Then you can access this value from with your code, and assign it to the FileWatcher path:
string myPath = System.Configuration.ConfigurationManager.AppSettings["watcherPath"];
FileSystemWatcher fsw = new FileSystemWatcher(myPath);
Related
I currently am writing to a statically named log file as defined in my serilog config:
<add key="serilog:write-to:File.path" value="%LOCALAPPDATA%\App_Data\Logs\StaticallyNamedLog.log" />
I'd like to be able to change the logfile name at runtime i.e.
<add key="serilog:write-to:File.path" value="%LOCALAPPDATA%\App_Data\Logs\{appname}-Log.log" />
In log4net for example I'd set a log4net global property value for "appname" in code before the settings were read in.
log4net.globalContext.properties["appname"] = "App1"
log4net.config.xmlConfigurator.configure("log4net.config")
Then in the logfile I'd reference it like so
%property{appname}
This would then get substituted into this path.
How can I do the equivalent in Serilog? I've done a lot of searching but can't find anything on this specific problem.
Thanks
Let's say I have a command line application that needs to reference some form of a user configuration file. Furthermore, the values contained within this file are to only be updated by the user manually -- there won't be any ways of updating the configuration file within the application, nor will the application seek out any inputs once started. If a configuration listing is missing from the configuration file, a default value should be used instead.
I understand that Visual Studio / .NET Framework offer tools for creating such constructs (i.e. Settings and App.configs), but I'm not sure I'm using them correctly -- or if I should be using them at all.
I created a Settings file and threw in a couple of default settings (e.g. SomeBooleanFlag is a bool with a default value of 'False'). This addition of course was reflected within my App.config. However, here is where the dilemma lies: how should I read from the App.config?
Currently, I've created a class to abstract away the configuration manager / settings stuff:
class AppSettings
{
public static bool SomeBooleanFlag
{
get
{
try
{
string rawValue = ConfigurationManager.AppSettings["SomeBooleanFlag"];
bool userSetSomeBooleanFlag;
bool userValueParsed = bool.TryParse(rawValue, out userSetSomeBooleanFlag);
return (userValueParsed) ? userSetSomeBooleanFlag : Settings.Default.SomeBooleanFlag;
}
catch
{
return Settings.Default.SomeBooleanFlag;
}
}
}
}
Which then gives me the ability to write:
if (AppSettings.SomeBooleanFlag)
{
/* Do Something... */
}
However, this does not seem like a clean way to approach the problem I stated above. Any help would be greatly appreciated!
Instead of coding your own Application Settings wrapper, you can reuse the functionality built into Visual Studio to generate this wrapper for you. See How to: Add or Remove Application Settings and How To: Read Settings at Run Time With C#. In addition to specifying the type of the setting you can also indicate the scope (User or Application).
Following the steps in the aforementioned articles, it will add the settings to your App.config file, below is an example:
<configuration>
...
<applicationSettings>
<ConsoleApplication1.Properties.Settings>
<setting name="TestKey" serializeAs="String">
<value>TestValue</value>
</setting>
</ConsoleApplication1.Properties.Settings>
</applicationSettings>
...
</configuration>
And you can access these settings as follows:
string s = Properties.Settings.Default.TestKey;
I do apologise if i didn't asked correctly in the title.. i don't know how to ask or what to call for what i need.
-
Let's say that i have a simple Application called "TestApp" written in C#.
Inside that application, i have the next variables:
int clientid = 123;
string apiurl = "http://somesite/TestApp/api.php";
When i have a new client, i need to create a new special TestApp.exe just for him, changing the 'clientid' variable inside the code.
It's possible to automate this process? To change that variable automatically and export an exe without for me to interfere with the process?
-
I asked this because i think/or i'm sure that it's possible because of the next popular examples:
http://download.cnet.com/2701-20_4-1446.html?tag=sideBar;downloadLinks
[ It creates a special .exe with a predefinied link from where to download the real file ]
http://torrent2exe.com/
[ It's embedding the .torrent file to a special .exe just with some custom variables changed, like torrent name or download size ]
Again, i do apologise if i didn't asked my question correctly and for my bad english, trying my best.
So you have two parts to your question:
You want to have variables inside the program based on client for your app
You want to automate the process of making the settings changes.
To make custom settings:
Use AppSettings.
First, add a reference to System.Configuration assembly.
In your app.config file:
<configuration>
<appSettings>
<add key="ClientID" value="123" />
<add key="ApiUrl" value="http://somesite/TestApp/api.php" />
</appSettings>
</configuration>
In your code, to read the settings:
using System;
using System.Configuration;
class Program
{
private static int clientID;
private static string apiUrl;
static void Main(string[] args)
{
// Try to get clientID - example that this is a required field
if (!int.TryParse( ConfigurationManager.AppSettings["ClientID"], out clientID))
throw new Exception("ClientID in appSettings missing or not an number");
// Get apiUrl - example that this isn't a required field; you can
// add string.IsNullOrEmpty() checking as needed
apiUrl = ConfigurationManager.AppSettings["apiUrl"];
Console.WriteLine(clientID);
Console.WriteLine(apiUrl);
Console.ReadKey();
}
}
More about AppSettings on MSDN
To automate the creation of settings:
This all depends on how complex you want to get.
When you build your project, your app.config file becomes TestApp.exe.config
You can use ConfigurationManager class to write Config files.
Further, you can write a little Exe that writes the config file with custom settings and execute it as part of a build action. Lots of ways to accomplish automation which depend on how you intend to deploy your application.
A quick example of writing an app.config file appSettings section programmatically:
public static void CreateOtherAppSettings()
{
Configuration config =
ConfigurationManager.OpenExeConfiguration("OtherApp.config");
config.AppSettings.Settings.Add("ClientID", "456");
config.AppSettings.Settings.Add("ApiUrl", "http://some.other.api/url");
config.Save(ConfigurationSaveMode.Modified);
}
i have a class library, with domain objects (linq based objects, in .net
4.0).
i want to have this library use connection strings for its own app.config.
there are some problems:
following the model used by Settings : ApplicationSettingsBase, i created a
wrapper that should read the settings from app.config.
however, unlike the model, i provide default values.
the problem is that the properties which should load the data from app.config
internal sealed class ApplicationSettings : ApplicationSettingsBase
{
// other properties
[SpecialSetting( SpecialSetting.ConnectionString )]
[global::System.Configuration.DefaultSettingValueAttribute("Server=.;Database=RFPLUSSTD;User Id=SYSADM;Password=SYSADM;")]
public string MainConnectionString
{
get { return (string)this["MainConnectionString"]; }
}
// other properties
}
in app.config:
<connectionStrings>
<add name="MainConnectionString"
connectionString="..."
providerName="System.Data.SqlClient" />
</connectionStrings>
now, this doesn't work...
i tried to set the name of the conn string to the fully qualified name like
namespace.class.property, but to avail.
i don't want to use the default Settings class, used by the dbml because
it compiles the settings :D and i can't change them without recompiling...
i'm already using a different model of app settings class in a project in
1.1, but i thought 3.5 has grown enough and have its own objects, that
work..
So, why is not working and how can i make it work?
Thank you
You need to make sure that you have permissions in the file system to make the change. I hope you have considered that. If you are sure that you changed the config file and if it only brings the default settings, it might be loading the config file from output bin folder not in the project root. If you are sure that the modification fails, please post the error message.
Updated:
Hi Jack, I think the main issue with your code is that it is creating new instance of the ApplicationSettings class every time and if the setting is in user scope, you will be having null value and then it results to default value every time.
You could easily do it with the built in Settings class. By default the Settings can only be accessed within the Assembly, internal sealed partial class Settings (in Settings.Designer.cs). If you change this to public sealed you will be able to access the Settings from any assembly and the next thing is you have to keep the setting to Application Scope not User scope. Once you have done these two, you can retrieve and save without any problem.
This is very frustrating... I can set the Configuration File for a Windows Forms Application just fine. Consider this:
public static void Main(){
AppDomain.CurrentDomain.SetData("APP_CONFIG_FILE", #"SharedAppConfig.config");
//do other things
}
However, in a WPF application, this doesn't seem to work! If I set this value, the value of the AppDomain.CurrentDomain.SetupInformation.ConfigurationFile property is correct, but any calls to that configuration file while debugging yield no results. There are WCF configuration settings in an App.config that I need to share between application, so this is my proposed solution. Is it possible to dynamically set the location of my config file in WPF?
Help! Thanks!
You should be able to do something along the lines of:
using System.Configuration;
public class TryThis
{
Configuration config = ConfigurationManager.OpenExeConfiguration("C:\PathTo\app.exe");
public static void Main()
{
// Get something from the config to test.
string test = config.AppSettings.Settings["TestSetting"].Value;
// Set a value in the config file.
config.AppSettings.Settings["TestSetting"].Value = test;
// Save the changes to disk.
config.Save(ConfigurationSaveMode.Modified);
}
}
NOTE: This will attempt to open a file named app.exe.config at C:\PathTo. This also REQUIRES that a file exists at the same path with the name "app.exe". The "app.exe" file can just be an empty file though. For your case I'd almost make a shared "Config.dll" library that would handle the config file.
~md5sum~
Is this on the service side or the client side? If on the service side, it is often the case that the service is running in its own AppDomain, so that if you set AppDomain.CurrentDomain.SetData(...) it won't apply to the service configuration.
I'm not entirely sure how to get around this, but you should be able to control the service's configuration by implementing your own ServiceHost.