using System; using System.Collections.Generic; using System.Linq; using System.Text; using System.Threading; using System.Drawing; using System.IO; //using System.Windows.Forms; using ChamChat.Models; namespace ChamChat { public abstract class Task { private static string _LogFilePath; private string _EventLogFile; private string _DataTransferLogFile; public static void SetLogPath(String path) { _LogFilePath = path + "\\TaskLogs"; if (!Directory.Exists(_LogFilePath)) Directory.CreateDirectory(_LogFilePath); } public Task(Client Client, Profile Profile) { _Profile = Profile; _Client = Client; ThreadPool.SetMaxThreads(1000, 1000); } private void InitDataTransferLog() { try { _Client.DataTransferLogs = new List(); DateTime dt = DateTime.Now; _DataTransferLogFile = _LogFilePath + "\\" + string.Format("Task_{0:00000}_{1:0000}{2:00}{3:00}.{4:00}{5:00}{6:00}.csv", _Client.MIDS, dt.Year, dt.Month, dt.Day, dt.Hour, dt.Minute, dt.Second); using (StreamWriter sw = File.CreateText(_DataTransferLogFile)) { sw.WriteLine(string.Format("Client : {0}", _Client.ToString())); sw.WriteLine(string.Format("Created : {0:0000}-{1:00}-{2:00} @ {3:00}:{4:00} (system time)", dt.Year, dt.Month, dt.Day, dt.Hour, dt.Minute)); if (_Client.Interface != null) sw.WriteLine(string.Format("Interface : {0}", _Client.Interface.ToString())); else sw.WriteLine("Interface : null"); sw.WriteLine(string.Format("Profile : {0}", _Profile.Title)); sw.WriteLine(""); sw.WriteLine("Timestamp; Command; Returndata"); } _Client.DataTransferLogFile = _DataTransferLogFile; } catch { _Client.DataTransferLogFile = null; } } private void InitEventLog() { try { _EventLogs = new List(); DateTime dt = DateTime.Now; _EventLogFile = _LogFilePath + "\\" + string.Format("Task_{0:00000}_{1:0000}{2:00}{3:00}.{4:00}{5:00}{6:00}_events.csv", _Client.MIDS, dt.Year, dt.Month, dt.Day, dt.Hour, dt.Minute, dt.Second); using (StreamWriter sw = File.CreateText(_EventLogFile)) { sw.WriteLine(string.Format("Client : {0}", _Client.ToString())); sw.WriteLine(string.Format("Created : {0:0000}-{1:00}-{2:00} @ {3:00}:{4:00} (system time)", dt.Year, dt.Month, dt.Day, dt.Hour, dt.Minute)); if (_Client.Interface != null) sw.WriteLine(string.Format("Interface : {0}", _Client.Interface.ToString())); else sw.WriteLine("Interface : null"); sw.WriteLine(string.Format("Profile : {0}", _Profile.Title)); sw.WriteLine(""); } } catch { _EventLogFile = null; } } public String Description { get { string result = string.Format("{0:00000} : Profile '{1}'", _Client.MIDS, _Profile.Title); return result; } } List _EventLogs; public List EventLogs { get { return _EventLogs; } } protected void AddEventLog(String message) { try { DateTime d = DateTime.Now; string sTimestamp = String.Format("{0:0000}-{1:00}-{2:00} @ {3:00}:{4:00}:{5:00}", d.Year, d.Month, d.Day, d.Hour, d.Minute, d.Second); string entry = String.Format("{0} : {1}", sTimestamp, message); //if (_EventLogs.Count > 10000) // Prevent overflowing the list //_EventLogs.RemoveAt(0); _EventLogs.Add(entry); if (_EventLogFile != null) { using (System.IO.StreamWriter sw = System.IO.File.AppendText(_EventLogFile)) { sw.WriteLine(entry); } } } catch { } } public DateTime StartOfTask { get { return _startThread; } } public Boolean IsRunningStandAlone { get { return _IsRunningStandAlone; } } public Profile Profile { get { return _Profile; } } public TaskStatus Status { get { return _Status; } } public virtual Boolean IsStandAloneProgrammable(Profile profile) { return _Client.IsProgrammable(profile); } public abstract Boolean IsControlledProgrammable(Profile profile); public String TaskProgress { get { return _TaskProgress; } } public Boolean Start(Boolean isStandAlone) { if (_Status != TaskStatus.IsRunning) { InitDataTransferLog(); // Only init if also really started InitEventLog(); _Status = TaskStatus.IsRunning; if (isStandAlone) { _thread = new Thread(new ThreadStart(ThreadStandAlone)); } else { _thread = new Thread(new ThreadStart(ThreadControlled)); } _thread.Start(); _startThread = DateTime.Now; _IsRunningStandAlone = isStandAlone; if(isStandAlone) AddEventLog("Stand alone task started"); else AddEventLog("Controlled task started"); return true; } return false; } public Boolean Stop() { _Status = TaskStatus.AbortRequested; DateTime OnStop = DateTime.Now; while ((_isKicking) && (OnStop.AddSeconds(20) > DateTime.Now)) Thread.Sleep(100); if (_isKicking) { _thread.Abort(); Thread.Sleep(100); if (_thread.Join(2000)) _isKicking = false; } if (!_isKicking) _Status = TaskStatus.Finished; // Set to finished because user invoked return !_isKicking; } public Boolean NextStep() { _Status = TaskStatus.NextStepRequested; DateTime OnStop = DateTime.Now; while (_Status == TaskStatus.NextStepRequested && (OnStop.AddSeconds(30) > DateTime.Now)) Thread.Sleep(200); return (_Status == TaskStatus.IsRunning); } protected String _TaskProgress; protected Thread _thread; protected Client _Client; public Client Client { get { return _Client; } } protected DateTime _startThread; protected Profile _Profile; protected Boolean _isKicking; protected TaskStatus _Status = TaskStatus.Starting; protected abstract void ThreadControlled(); protected abstract void ThreadStandAlone(); protected Boolean _IsRunningStandAlone; public Color StatusColor { get { Color color = Color.Black; switch (_Status) { case TaskStatus.ExceptionOccured: color = Color.Red; break; case TaskStatus.IsRunning: color = Color.Green; break; case TaskStatus.Stopped: color = Color.Orange; break; case TaskStatus.Finished: color = Color.DarkGray; break; default: color = Color.Black; break; } return color; } } } public enum TaskStatus { Starting, IsRunning, AbortRequested, Aborted, Stopped, Interrupted, Finished, ExceptionOccured, NextStepRequested, } public static class TaskStatusExtensionMethods { public static string ToText(this TaskStatus s) { string result = s.ToString(); switch (s) { case TaskStatus.AbortRequested: result = "Abort requested"; break; case TaskStatus.ExceptionOccured: result = "Exception occured"; break; case TaskStatus.IsRunning: result = "Running"; break; case TaskStatus.NextStepRequested: result = "Proceeding with next step"; break; default: result = s.ToString(); break; } return result; } } }