Timekeeper2
Represents a class object that tracks operational metrics. This class cannot be inherited.
using Relativity.DataExchange.Io;
using System;
using System.Collections.Concurrent;
using System.Text;
namespace Relativity.DataExchange
{
public sealed class Timekeeper2
{
private const int DefaultThread = 0;
private readonly ConcurrentDictionary<string, ConcurrentDictionary<int, TimekeeperEntry2>> dictionary;
private readonly IFileSystem fileSystem;
private readonly IAppSettings settings;
private bool? logAllEvents;
public int Count => dictionary.Count;
public Timekeeper2()
: this(FileSystem.Instance.DeepCopy(), AppSettings.Instance)
{
}
public Timekeeper2(IFileSystem fileSystem, IAppSettings settings)
{
if (fileSystem == null)
throw new ArgumentNullException("fileSystem");
if (settings == null)
throw new ArgumentNullException("settings");
this.fileSystem = fileSystem;
this.settings = settings;
dictionary = new ConcurrentDictionary<string, ConcurrentDictionary<int, TimekeeperEntry2>>();
}
public TimekeeperEntry2 GetEntry(string key)
{
return GetEntry(key, 0);
}
public TimekeeperEntry2 GetEntry(string key, int thread)
{
if (!dictionary.ContainsKey(key))
return null;
ConcurrentDictionary<int, TimekeeperEntry2> concurrentDictionary = dictionary[key];
if (!concurrentDictionary.ContainsKey(thread))
return null;
return concurrentDictionary[thread];
}
public void MarkEnd(string key)
{
MarkEnd(key, 0);
}
public void MarkEnd(string key, int thread)
{
if (LogAllEvents()) {
ConcurrentDictionary<int, TimekeeperEntry2> concurrentDictionary = dictionary[key];
TimekeeperEntry2 timekeeperEntry = (concurrentDictionary != null) ? concurrentDictionary[thread] : null;
if (timekeeperEntry != null) {
timekeeperEntry.Count++;
TimekeeperEntry2 timekeeperEntry2 = timekeeperEntry;
long length = timekeeperEntry2.Length;
DateTime now = DateTime.Now;
timekeeperEntry2.Length = length + (now.Ticks - timekeeperEntry.StartTime) / 10000;
TimekeeperEntry2 timekeeperEntry3 = timekeeperEntry;
now = DateTime.Now;
timekeeperEntry3.StartTime = now.Ticks;
}
}
}
public void MarkStart(string key)
{
MarkStart(key, 0);
}
public void MarkStart(string key, int thread)
{
if (LogAllEvents()) {
if (dictionary.ContainsKey(key)) {
ConcurrentDictionary<int, TimekeeperEntry2> concurrentDictionary = dictionary[key];
if (concurrentDictionary.ContainsKey(thread))
concurrentDictionary[thread].StartTime = DateTime.Now.Ticks;
else
concurrentDictionary[thread] = new TimekeeperEntry2();
} else
dictionary[key] = new ConcurrentDictionary<int, TimekeeperEntry2> {
[thread] = new TimekeeperEntry2()
};
}
}
public void GenerateCsvReportItemsAsRows()
{
GenerateCsvReportItemsAsRows(string.Empty, string.Empty);
}
public void GenerateCsvReportItemsAsRows(string filenameSuffix, string directory)
{
if (LogAllEvents()) {
string fileName = GetFileName(filenameSuffix);
string path = directory + fileName;
if (!string.IsNullOrEmpty(directory))
path = fileSystem.Path.Combine(directory, fileName);
using (IStreamWriter streamWriter = fileSystem.CreateStreamWriter(path, false, Encoding.Default)) {
streamWriter.WriteLine("\"Function Name\",\"Number of calls\",\"Total Length (ms)\"");
string[] array = new string[checked(dictionary.Keys.Count - 1 + 1)];
dictionary.Keys.CopyTo(array, 0);
Array.Sort(array);
string[] array2 = array;
foreach (string text in array2) {
ConcurrentDictionary<int, TimekeeperEntry2> concurrentDictionary = dictionary[text];
int num = 0;
long num2 = 0;
foreach (TimekeeperEntry2 value in concurrentDictionary.Values) {
num += value.Count;
num2 += value.Length;
}
streamWriter.WriteLine($"""{text}""{num}""{num2}""");
}
}
}
}
private string GetFileName(string filenameSuffix)
{
if (!LogAllEvents())
return null;
StringBuilder stringBuilder = new StringBuilder();
DateTime now = DateTime.Now;
stringBuilder.Append(now.Year);
now = DateTime.Now;
int num = now.Month;
stringBuilder.Append(num.ToString().PadLeft(2, '0'));
now = DateTime.Now;
num = now.Day;
stringBuilder.Append(num.ToString().PadLeft(2, '0'));
now = DateTime.Now;
num = now.Hour;
stringBuilder.Append(num.ToString().PadLeft(2, '0'));
now = DateTime.Now;
num = now.Minute;
stringBuilder.Append(num.ToString().PadLeft(2, '0'));
now = DateTime.Now;
num = now.Second;
stringBuilder.Append(num.ToString().PadLeft(2, '0'));
stringBuilder.Append(filenameSuffix);
stringBuilder.Append(".csv");
return stringBuilder.ToString();
}
private bool LogAllEvents()
{
if (!logAllEvents.HasValue)
logAllEvents = settings.LogAllEvents;
bool? nullable = logAllEvents;
bool flag = true;
return (nullable.GetValueOrDefault() == flag) & nullable.HasValue;
}
}
}