Two things to finally close the series about the server dashboard.
First: In Part 3 / 5 I described my problems with the “unexpected dispose”.
This dispose is a (weakly documented) feature of WCF.
I started a thread in the MS forums about it and finally go the answer.
And here is the solution for this project.
First you can remove all “dispose avoid code” from the class PerfInfos
This is:
The private member on top of the class (remove it):
//avoid dispose for cached object!
private bool m_bIamInCache;
Next compile and follow the errors (also a way to fix code
):
Revome the following functions:
//create object for cache
public PerfInfos(bool bInit, bool bImInCache) {
m_bIamInCache = bImInCache;
m_dtLastRead = DateTime.MinValue;
ErrMess = "OK";
if (bInit) {
if (InitCountersAndTotalRAM()) {
ReadCurValues();
}
}
}
//cleanup for no longer cached item
public void CleanUp() {
m_bIamInCache = false;
Dispose();
}
And the first three lines from Dispose:
public void Dispose() {
if (m_bIamInCache) { //do not dispose cached objects!!
return;
}
Here is the code for the service:
[OperationContract]
[OperationBehavior(AutoDisposeParameters = false)]
public string GetPerfString() {
return (GetCachedPerfInfo().ToString());
}
[OperationContract]
[OperationBehavior(AutoDisposeParameters = false)]
public PerfInfos GetPerfInfo() {
return (GetCachedPerfInfo());
}
private static PerfInfos GetCachedPerfInfo() {
Cache cH = HttpRuntime.Cache;
if (cH == null) {
return (new PerfInfos() { ErrMess = "No Cache" });
}
PerfInfos pI = cH["PerfInf"] as PerfInfos;
if (pI == null) {
//pI = new PerfInfos(true, true); //be sure to creat "cache stable instance" NO LONGER NEEDED
pI = new PerfInfos(true); //use the normal (with init) constructor
cH.Insert("PerfInf", pI, null, DateTime.Now.AddMinutes(20), Cache.NoSlidingExpiration,
CacheItemPriority.Default, RemovedCallback);
}
pI.LockedReadCurValues();
return pI;
}
public static void RemovedCallback(String strKey, Object oValue, CacheItemRemovedReason rEason) {
PerfInfos pI = oValue as PerfInfos;
if (pI != null) {
//pI.CleanUp(); //calls dispose for a "cache stable object" NO LONGER NEEDED
pI.Dispose(); //simply use a dispose
}
}
The second reason for this follow-up is that I want to inform you that the code is finally available at the telerik website:
You can find it a the code library.
And you should also read the optimization suggestions Andrey Murzov made there.