How would a static variable work in a web farm? - c#

I have a static class with a static dictionary to keep track of some stats. Is this approach viable in a single and multi server environment?

Not in a multi-server environment. Unless the dictionary isn't the .Net dictionary, but one that works against a database or some other outside storage. Also in a single server environment you should remember the Dictionary will be emptied with every IIS refresh.

No, a static variable in memory in one server won't be visible or synchronized with other servers.
Since you mention "keeping track of stats", what many multi-instance server farms end up doing is post-processing locally gathered data into an aggregate view of activity across all the servers. Each server accumulates stats in memory for a short while (a few minutes), then writes the data from memory to a log file on the local file system. Every few hours or daily a batch process copies the log files from each server in the farm to a central location and merges all the log records together to form one collection of data. One useful byproduct of this might be consolidating user activity across multiple servers if a user's web requests were served by different servers in the same farm (load balancing).
Depending on the volume of data, this batch processing of log data may itself require quite a bit of computational power, with multiple machines crunching different subsets of the server logs, and then those intermediates getting reduced again.
Google Sawzall is an example of a very large scale distributed data processing system. I believe Sawzall is (or was) used at Google to process server access logs to detect fraudulent ad click patterns.

No, it's not viable in a web farm multi-server environment.
Storing Session State in an ASP.Net Web Farm
Allowing Session in a Web Farm? Is StateServer Good Enough?
Fast, Scalable, and Secure Session State Management for Your Web Applications
ASP.NET Session State
Session-State Modes
The State Mode options are:
InProc mode, which stores session state in memory on the Web server. This is the default.
StateServer mode, which stores session state in a separate process called the ASP.NET state service. This ensures that session state is preserved if the Web application is restarted and also makes session state available to multiple Web servers in a Web farm.
SQLServer mode stores session state in a SQL Server database. This ensures that session state is preserved if the Web application is restarted and also makes session state available to multiple Web servers in a Web farm.
Custom mode, which enables you to specify a custom storage provider.
Off (disables session state)

Normally, this is what you would use Application state for.

Related

How to use Azure App Service Local Cache?

I am having a MVC API project which is using a server side cache. It is deployed to Azure App Service. I was wondering to make use of App Service Local Cache to overcome challenge of keeping the cache in sync across nodes.Is this the right approach ? If yes, how do i modify the cache from my code.
PS: I am not much interested in using the Redis Cache.
I was wondering to make use of App Service Local Cache to overcome challenge of keeping the cache in sync across nodes.
What does sync across nodes mean? Do multiple webapp applications share cache data?
HttpRuntime.Cache can only be used in a single webapp application and cannot be accessed by other webapps. Once each cache is created, it takes up server resources. So from this point we can say: it is not that the more cache, the better. The cache has a time limit. After the expiration time set by the server, it will be recycled by the server. The cache can store any object.
So if you want to share cache data across sites, it is impossible to achieve, which is why the redis cache appears.
If you really don't want to use redis cache, then you can store the required data in sql server. This can only be an alternative, not the best.

Out of proc SessionState memory management

We're using an out-of-proc session state service/ASP.Net Session state. We know were having problems with this as it's been abused in the past, too much stored in session state too often, so were in the process of moving onto a more scalable system.
In the meantime, though, we're trying to get our heads around how a session state service manages it's memory and what limits do we have. But none of the Microsoft docs seem to go into any details.
Specifically I want to know:
What are the limits to how much "the standard" out of proc session state service (installed along with IIS in the windows management console) can store?
(x64)
Is there a per user limit?
by standard service, I mean this one:
There is no limit beyond that of the machine hosting the service. If it has 16 gigs of RAM, assuming a few gigs are used for other processes / the OS / etc., there would be something like 13 GB of memory available for the session data. The data is not persisted to disk so the data only ever exists in RAM / memory; this is why when you restart the service all sessions are gone. The memory is volatile and works like a RAM disk.
If you're reaching the memory limits of the machine hosting your session state service, you are either storing too much data per user, or have too many users storing a little data. You're already on the right track as the next step is moving to a distributed session state provider to scale correctly. This is often achieved via a distributed caching system which comes with a session state provider, or by writing your own provider against said system.
There is no per-user limit on data, but note that out of process communication always happens via serialization. Therefore, there is a practical limit as serializing/deserializing a gig of user data per request is going to be very slow no matter how you approach it.

InProc vs StateServer

We recently changed from using InProc to StateServer for storing Session information.
I was wondering, if it's possible to update configuration files on the website now without losing session information. As when we used InProc and updated resource files (like language files), web config files, global.asax or files in the App_Code, we found that sessions appeared to reset and received errors like
'Object reference not set to an instance of an object'
Does this change with going to StateServer? Is it safe to update these types of files without losing the session data? I have run a couple of tests on our test system, and it appears that it works OK, but I'm not 100% confident...
A simple answer to your query is YES
Further more saying...
- Using State Server, session is serialized and stored in memory in a separate process (aspnet_state.exe).
- State Server can run on another machine.
- Session is persistent, you don't need to be afraid that your session data is lost during application restarts
- When storing data of basic types (e.g. string, integer, etc), in one test environment it's 15% slower than InProc.
- The cost of serialization/deserialization can affect performance if you're storing lots of objects.
- Solve the session state loss problem in InProc mode. Allows a webfarm to store ASP.NET session on a central server. Single point of failure at the State Server.
For more refer:
- Steps for session inproc mode to state server
Yes it does. Once your session data are out-of-process it's safe to restart worker processes. You can test it by logging in to your site, making some actions that involve session update and killing the corresponding w3wp.exe process (assuming it's IIS 7+) from the task manager (or just touching web.config).

Paradox - know whether there is change in the database without opening a connection

I am writing a application in C# that needs to do the following:
without connecting to the database I need to check if there are some new logs in database. If there are then I am allowed to open the connection and retrieve them.
So I just need to know if there are new logs (elements) in the database WITHOUT opening the connection to it.
Server can send mail to administrator and I could monitor mailbox for changes but that solution is unacceptable.
Can server on inserting new rows create *.txt file on disk with text indication new rows which I can check and delete/edit after downloading change?
(database is in SQL Server 2008 R2)
Is it even possible? Any/And/Or other options to do this are welcome.
Thank you all very much in advance.
Based on the following clarifying comments from the OP under the question:
There is Web application which checks for change every 30 sec and shows latest authorizations. Database is tracking employee authorization and has frequent updates. Now I'm building desktop application, which has local connection to the server and can update more frequently, but client does-not want application to open connection every sec, aldo connection is opened for several ms.
I think that the appropriate solution is a business layer.
If you build a business layer hosted in IIS that performs the database access on behalf of the users using a single database user for access (the application pool user or an impersonated user within the web application), then connection pooling will reduce the number of connections made to the database significantly.
Here is an MSDN article that describes the mechanics and benefits of connection pooling in great detail.
All of the clients, including the web layer, would connect to the business layer using WCF or .Net Remoting (depending on your .Net version), and the business layer would be the only application performing database access.
The added benefit of this approach is that you can move all database access (including from the web client) inside the DMZ so that there is no direct database access from the DMZ outward. This could be a good selling point for your customer.
We use this mechanism extensively for very large, very security and performance conscious customers.
Update
As an alternative, you could have the business layer query the database every 30 seconds, extract the necessary information, and store it locally to the business layer in a database of some sort (Access, Sql Server Express, etc). When requests from clients are received, they will be served from the local data store instead of the database.
You could do this by kicking off a background thread in global.asax's Application_Start event or by adding a cache entry that expires every 30 seconds and performing the work in the cache timeout event.
This will reduce the number of connections to 1 (or 2 if the web isn't modified) every 30 seconds (or whatever the time is).
Try to monitor files change date inside DB folder.
If the client desktop application is not going to be deployed massively you could use SqlDependency. Then you wouldn't have to poll the database on a frequent basis, instead the database will notify you if something changes.
You could also deploy a service on the server which uses SqlDependency and then connect to this service from your desktop applications.
If that's not an option this document mentions some other options.
These two could be applied to your situation:
Create an AFTER UPDATE trigger on the table being monitored, whose action uses SQL Server Service Broker to send a message to the entity needing the notification.
Use Windows Server App Fabric Cache, which supports a change notifications mechanism, based on an in-memory object cache and callback functions you register with the objects.

ASP.NET Session Abandoning Unexpectantly

For some reason, the session is abandoning unexpectantly, and wreaking havoc in our application. We've had the app setup to use Session and have been using it for several months with no problems. Now, as we add additional content and store additional info in it, the Session is dumping well before the 20 minute timeout than its supposed to. I'm at a loss for the reason why... could it be because we may be adding a lot of data in the Session (not sure of exact size)? This is my local machine after all (Win 7, using IIS, ASP.NET 4.0, 4 GB RAM).
Or could there be other reasons for this occurrence? Any thoughts?
Thanks.
ASP.Net sessions are stored in the cache. If you are running out of memory then it will be dumped. You need to store the session in a database or other storage to keep it. I'll try to find a relevant link. Sessions are not meant to store tons of data!
Here is a link explaining how to use out-of-process sessions. Basically the idea is that, by default, ASP.Net/IIS will use in-process sessions (which are fastest) but are also limited by the power/storage on the server running IIS. The alternatives are to use a session state farm or a SQL server to store sessions. These are a bit slower but offer more flexibility. You will need to take into account the ability to serialize sessions into your decision.
Here is an excerpt from a book I've been reading (Programming Microsoft ASP.NET 3.5 by Dino Esposito):
Why Does My Session State Sometimes Get Lost?
When the working mode is InProc, the session state is mapped in the memory space of the AppDomain in which the page request is being served. In light of this, the session state is subject to process recycling and AppDomain restarts. As we discussed in Chapter 2, the ASP.NET worker process is periodically restarted to maintain an average good performance; when this happens, the session state is lost. Process recycling depends on the percentage of memory consumption and maybe the number of requests served. Although the process is cyclic, no general consideration can be made regarding the interval of the cycle. Be aware of this when designing your session-based, in-process application. As a general rule, bear in mind that the session state might not be there when you try to access it. Use exception handling or recovery techniques as appropriate for your application.
In Knowledge Base article Q316148, Microsoft suggests that some antivirus software might be marking the web.config or global.asax file as modified, thus causing a new application to be started and subsequently causing the loss of the session state. This holds true also if you or your code modify the timestamp of those files. Also, any addition to or removal from the Bin directory causes the application to restart.
Note: What happens to the session state when a running page hits an error? Will the current dictionary be saved or is it just lost? The state of the session is not saved if, at the end of the request, the page results in an error—that is, the GetLastError method of the Server object returns an exception. However, if in your exception handler you reset the error state by calling Server.ClearError, the values of the session are saved regularly as if no error ever occurred.
I'm assuming you are using Session state in-proc. If this is the case then the most common reason of losing your Session is that the corresponding Application Pool recycles. Go check IIS settings on Application pool and set up Event log entries for such events. You'll find the settings in: "Advanced settings" of your app pool -> "Recycling" -> "Generate Recycle Event Log Entry". Set them all to true and see if it will give you the reason of your Session State loss.
Also if you change data on given sites a lot then it will eventually trigger app pool recycling.
More ideas on app pool recycling:
http://blogs.msdn.com/b/johan/archive/2007/05/16/common-reasons-why-your-application-pool-may-unexpectedly-recycle.aspx

Categories