Single application instance per network - c#

We have developed some long running C# console applications which will be run by Windows Scheduled tasks.
These applications might be run on many different server machines on intranet/extranet.
We cannot ensure that they run on one machine because each application might need access to some resources, which are available only on a certain machine.
Still, all these applications are using a common WCF service to access the database.
We need to ensure, that there is only instance of one of our applications running at any moment.
As the apps might be on different extranet computers, we cannot use per-machine mutexes or MSMQ.
I have thought about the following solution - WCF Mutex service with a timeout. When one app runs, it checks to see if it is already launched (maybe on another machine) and then (in a dedicated thread) periodically pings the WCF Mutex service to update the timestamp (if ping fails, the app exits immediately). If the timestamp gets expired, this means, that the application has crashed, so it can be run again.
I would like to know, if this "WCF mutex" is optimal solution for my problem. Maybe there are already some third party libraries which have implemented such functionality?

You mutex solution has a race condition.
If an app on a different server checks the timestamp in the window after the timestamp expired, but before the current service had updated the timestamp you will have two instances running.
I'd probably go the opposite route. I'd have a central monitoring service. This service would continually monitor the health of the system. If it detects a service went down, it would restart it on either that machine or a different one.
You may want to bite the bullet and go with a full Enterprise Service Bus. Check the Wikipedia article for ESBs. It lists over a dozen commercial and open source systems.

How about a file lock on a network location?
If you can create/open the file with exclusive read write then it is the only app running. If this running app then subsequently crashes, the lock is released automaticaly by the OS.
Tim
Oops, just re-read the question and saw "extranet", ignore me!

Related

Run an application from the IIS application pool

I have a console application which basically sends emails once per day.
The Windows server administrator disallows this technique and doesn't want to allow extra software on the computer (launched by a scheduled task or a service).
I've been asked to evaluate the possibility of redeveloping a part of the application and integrate it into the IIS application pool but I don't think IIS can do this. Is it possible ? If so, how ?
The only approach I've looked at so far is to redevelop it as a web application and launch a web page everyday with a scheduled task, but I'd like to avoid that.
Let's analyze your options:
Use task scheduler in your server to launch console app
Use task schedule**r in your server to **web service hosted in IIS
Have an IIS application running 100% of time in an infinite loop that that checks time every minute and if it happens to be the correct time send the emails
Have a windows service.
Use task scheduler in a different server to invoke
Analyzing each one of them:
KO: Your administrator does not want console apps and process is not isolated.
KO: You have process isolated but still you are installing a console app.
OK: Not very good for performance but your fulfills your admin conditions.
KO: Your admin does not want windows services.
??: Probably your admin will not want to use an extra server
Proposed solution: As you can see only options 3 and 5 might pass the filter. Ask him
Correct solution I did similar things in the past and went for option 2. You have to convince your admin that solution 3 is a bad idea and probably 5 is already out of the question. When he had to choose the lesser of the evils option 2 is the best :-)
NOTE: You don't mention it but in case you have a SQL Server or similar you can store there an scheduled task too...
I had similar questions when I was moving from Apache servers (where it's dead easy to send a nightly email) to Windows (where you have options).
Clients have sometimes pushed me towards SQL Mail. It's not terrible. If your web app has a SQL backend, and it's okay to schedule things there, it's capable of sending emails when properly configured.
I don't think this is possible. With an IIS application you'd need something to trigger loading the application (call the web page). This itself would require a scheduled task.
You need to pound some sense into your administrator. Sorry.

Process Management Library

I am working on an OLAP application, WCF + Silverlight clients (up to 100 concurrent users). Unfortunately from time to time, a specific service call goes crazy (although it is perfectly valid, just too complex) and occasionally (once a month) brings the whole server down (by consuming all CPU).
A solution would involve killing user request or even the whole user session which is not a big deal for us from the business perspective - recovering/restarting the whole application is.
The idea of isolating user sessions into separate processes is very tempting: CPU/memory throttling and clean resource disposal (not like Thread.Abort) - if modern browsers can do this just for web pages, maybe it's time to do this on servers. We just want to evaluate this concept and see pros and cons in our particular scenario.
Hence the questions:
Is there already an existing library/framework which will be useful for managing processes (like pre-spawning/reusing processes, throttling, kill after timeout)?
Are there any "best practices" or guidelines how to create such architecture?
I was having same problem with my WCF services they too serve more than 100 clients..
and problem which i discovered using IIS logs (C:\Windows\System32\LogFiles\HTTPERR)
I found my problem in Application Pool Recycle timeout on IIS setting.
Application pool was getting restarted every 48 hours and which was causing issues with already subscribed clients.
So i would suggest
1. Analyze the http error logs and IIS logs which will give more information about all the application pools status if any gets shutdown or recycled.
2. If application pool crashes then Setup for Windbg and attach the process set the correct source file path. It will tell you the location if any exceptions are occurring.

C#, ASP.net application which calls executable to create output file

We are developing a web application in ASP.Net and C#. The requirement here is to interact with a third party exe which is developed in Fortran77. This third party exe produces an output file after being provided with some inputs and shuts down.In windows desktop single user application this is easily possible by using System.Diagnostics.Process and the events provided therein. But in web there will be multi-user environment, and many calls will be made to this exe. What are the best possible ways to handle such an exe in web application?
Is it fine if we invoke exe on each user request as the exe shuts down after generating output file? Or
Is it possible to use windows service? Or
Any other approach?
Thanks in advance.
-Prasad
Typically, invoking a different process to do some job (for a request) does not scale well when your number of requests start growing. Said that, if the process invocation is not going to happen frequently then you should be OK. The number of concurrent requests and through-put etc will really depend on your server hardware and the best bet would be to load test the server. As such you should use Process class to launch the process to get the work done.
Yet another issue that is possible that your legacy executable does not support multiple instance. It's unlikely but there are quite a few desktop windows application that check for existing instance. So in such, you cannot launch process concurrently and only way would be to create a queuing logic - you can create a in-process queue (in your web application) or create a external application (such as windows service) that will do queuing.
There can be alternate approach for this solution that is useful when the time taken for process to complete is large (so that you cannot block your web requests till the job is complete) and/or you need to scale your app to support more load. Essentially idea is use producer-consumer pattern where your web server will add requests to a persisted (e.g. table in database) queue and then you have multiple machines/servers running a job/windows service that would read from this queue and run the process to generate file.

Running a process as the current user from a SYSTEM process

This is the scenario:
I have a service (#1) running as LOCAL SYSTEM, and it will eventually run a process (#2) that updates an application (#3). This process (#2), the updater, must run as LOCAL SYSTEM also, no problem here, since it needs to rewrite some files (#3).
When the updater starts as LOCAL SYSTEM, it will kill any running instance of my application (#3). After the files being update, I need to start the updated application (#3) again as the current logged account.
How could I manage this? Is there anything conceptually wrong in my idea?
UPDATED
The updater kills the app just to replace the files.
I don't think there's a way for the service to get its hands on the WindowsIdentity.Token handle it would need to call the CreateProcessAsUser() API function. Unless the app itself provides it.
There's a better way, you don't have to terminate the app to replace its executable files. All you have to do is rename them. You can then put the updates in place and signal the app to restart itself. Another nice advantage of this approach is that the app voluntarily shuts down (including notifying the user) instead of getting rudely aborted. Clean up the renamed files when you see the process terminated.
If you have access to the user's credentials, you can use Process.Start with a ProcessStartInfo specifying the username and password of the user.
If you don't know the credentials, then I am not sure it can be done.
A work around could be to have the service communicate with your program, asking it to shutdown itself, but before doing so, it should start a seperate tiny program. This should be running in the background, but it will be running with the current user's credentials. When you are finished, ask the background program to start your main program again, then exit.
One problem is knowing the "logged in user". XP and up support fast user switching, where more than 1 user may be logged on at the same time (vista and up support this feature even if the machine is a domain member).
Here is a link to a Raymond Chen blog article discussing the issue: http://blogs.msdn.com/oldnewthing/archive/2006/08/22/712677.aspx

Suggestions for developing Windows Service with C#

I am developing a distributed application where each distributed site will run a 2-tier winform based client-server application (there are specific reasons for not going into web architecture). The local application server will be responsible for communicating with a central server and the local workstations will in turn communicate with the local server.
I am about to develop one or more windows services to achieve the following objectives. I presume some of them will run on the local server while some on the local workstations. The central server is just a SQL Server database so no services to be developed on that end, just DML statements will be fired from local server.
Windows Service Objectives
Synchronise local data with data from central server (both end SQL Server) based on a schedule
Take automatic database backup based on a schedule
Automatically download software updates from vendor site based on a schedule
Enforce software license management by monitoring connected workstations
Intranet messaging between workstations and/or local server (like a little richer NET SEND utility)
Manage deployment of updates from local server to workstations
Though I have something on my mind, I am a little confused in deciding and I need to cross-check my thoughts with experts like you. Following are my queries -
How many services should run on the local server?
Please specify individual service roles.
How many services should run on the workstations?
Please specify individual service roles.
Since some services will need to query the local SQL database, where should the services read the connection string from? registry? Config file? Any other location?
If one service is alotted to do multiple tasks, e.g. like a scheduler service, what should be the best/optimal way with respect to performance for managing the scheduled tasks
a. Build .NET class Library assemblies for the scheduled tasks and spin them up on separate threads
b. Build .NET executable assemblies for the scheduled tasks and fire the executables
Though it may seem as too many questions in a single post, they are all related. I will share my views with the forum later as I do not want to bias the forum's views/suggestions in any way.
Thanking all of you in advance.
How many services should run on the local server?
It depends on many factors, but I would generally go for as less services as possible, because maintaining and surveilling one service is less work for the admin than having many services.
How many services should run on the workstations?
I would use just one, because this will make it a single point of failure. The user will notice if the service on the workstation is down. If this is the case only one service needs to be started.
Since some services will need to query the local SQL database, where should the services read the connection string from? registry? Config file? Any other location?
I would generally put the connection string in the app.config. The .NET framework also offers facilities to encrypt the connection string.
If one service is alotted to do multiple tasks, e.g. like a scheduler service, what should be the best/optimal way with respect to performance for managing the scheduled tasks a. Build .NET class Library assemblies for the scheduled tasks and spin them up on separate threads b. Build .NET executable assemblies for the scheduled tasks and fire the executables
b. is easier to design and implement. It gives you the possibility to use the windows scheduler. In this case you will need to think of the problem, when the windows scheduler starts the executable, when the previous start has not finished yet. This results to two processes, which may do the same. If this is not a problem then stay at that design. If it is a problem, consider solution a.
For solution a. have a look on Quartz.NET which offers you a lot of advanced scheduling capabilities. Also considering using application domains instead of threads to make the service more robust.
If you don't get admin rights on the local server, think about means to restart the service without the service control manager. Give some priviledged user the possibility to re-initialize the service from a client machine.
Also think about ways to restart just one part of a serivce, if one service is doing mulitple tasks. For instance the service is behaving strangely, because the update task is running wrong. If you need to restart the whole service to repair this, all users may become aware of it. Provide some means to re-intialize only the update task.
Most important: Don't follow any of my advices if you find an easier way to achieve your goals. Start with a simple design. Don't overengineer! Solutions with (multiple) services and scheduling tend to explode in their complexity with each added feature. Especially when you need to let the services talk to each other.
I dont think there is one answer to this, some would probably use just one service and other would modularize every domain into a service and add enterprise transaction services etc. The question is more of a SOA one than C# and you might consider read up on some SOA books to find your pattern.
This does not answer your questions specifically, but one thing to consider is that you can run multiple services in the same process. The ServiceBase.Run method accepts an array of ServerBase instances to start. They are technically different services and appear as such in the service control manager, but they are executed inside the same process. Again, just something to consider in the broader context of your questions.

Categories