Mike Maggy
Mike Maggy

Reputation: 103

Add log to my application that can write from different EXE files at same time

i have Command Line application that received file from user (DOC, PDF), this file is locate on the same machine and my application copy this file to specific folder and return 0 is this operation passed and 1 otherwise. This command line exe file can open several times concurrency and there is no problem with it. Now i want to add to my application a Log that will locate in the application folder and this Log will write each file name and if the operation passed or failed. Now i wonder how to achieve that in case i have several open processes and how to avoid situation that 2 exe files try to write to my log at the same time. can i using lock in such case although i am using several exe files in the same time ?

Upvotes: 0

Views: 793

Answers (4)

akapoo11
akapoo11

Reputation: 1

One of the cleanest and SOA based approach would be to a use a separate logging service which your process ( or processes) will call to log information. Log4Net provides a mechanism for both client and server to post and consume messages respectively. Look at https://log4netremotelogging.codeplex.com/ for further details.

Upvotes: 0

ikh
ikh

Reputation: 2436

If you don't care too much about the log's cleanliness, you can open the log file in a way that allows multiple processes to write to it:

private static Stream CreateFile(string path, bool checkHost)
{
    var mode = FileMode.Append;
    return new FileStream(path, mode, FileAccess.Write, FileShare.ReadWrite, 4096, FileOptions.SequentialScan, Path.GetFileName(path), false, false, checkHost);
}

The drawback is that if two processes write to the file concurrently then you'll get a mess that will look like this:

2014-11-26 11:32:93 Suc2014-11-26 11:32:93 Failed: file "Some.doc" seeded: file "Other.doc"

I.e. the processes race each other and you end up with intermingled log entries. If you don't have too many processes writing to the same log file, and if each process writes infrequently, you should have very few collisions like this.

There are several ways around it. One is to open the file in read-only mode in each process, and wait on other processes until the file is available; the crudest way to do this is to try-catch a File.AppendAllText() in a while-loop until you succeed. There are other options listed in questions like this one.

Another alternative is to write log to multiple files, or to something other than file, e.g. to a DB.

Upvotes: 0

xakpc
xakpc

Reputation: 1809

You can create named system mutex to control access to log file

// Set this variable to false if you do not want to request  
// initial ownership of the named mutex. 
bool requestInitialOwnership = true;
bool mutexWasCreated;

// Request initial ownership of the named mutex by passing 
// true for the first parameter. Only one system object named  
// "MyMutex" can exist; the local Mutex object represents 
// this system object. If "MyMutex" is created by this call,
// then mutexWasCreated contains true; otherwise, it contains 
// false.
Mutex m = new Mutex(requestInitialOwnership, "MyMutex", out mutexWasCreated);

To ensure there are named mutex you can use Mutex.TryOpenExisting("MyMutex", resultMutex) and if it exists you can Wait, Log and Release it

    resultMutex.WaitOne();
    Log("success");
    resultMutex.ReleaseMutex();

More info availible in MSDN: http://msdn.microsoft.com/en-us/library/System.Threading.Mutex(v=vs.110).aspx

Upvotes: 2

TomTom
TomTom

Reputation: 62093

Do not make a log file. Use ETW and log to the windows mechanisms. It is not like the event log is new (it is there for a long time) and ETW is now fully supported via nuget packages.

ETW also is kernel based.

Upvotes: 1

Related Questions