using System; using System.Collections.Generic; using System.Reflection; using sharp.tradebot; using sharp.json; using sharp.json.attributes; using System.Threading.Tasks; using System.IO; using System.Text; using sharp.trading.logging; using sharp.trading; using System.Runtime.CompilerServices; using System.Runtime.Remoting; namespace TradeBot { public class BotManager { public TradingBotEnvironment BotEnvironment { get; private set; } public String DataBaseFile { get; private set; } List instances = new List(); public BotManager(string baseDirectory) { DataBaseFile = Path.Combine(baseDirectory, "botmanager.json"); BotEnvironment = new TradingBotEnvironment(TradingEnvironment.DefaultConnection, baseDirectory); if (!Directory.Exists(Path.Combine(BotEnvironment.BaseDataDirectory, "logs"))){ Directory.CreateDirectory(Path.Combine(BotEnvironment.BaseDataDirectory, "logs")); } load(); } private void load() { TradingBotInstance[] _instances = JSON.ReadFrom(DataBaseFile,new TradingBotInstance[0]).To(); if (_instances != null) { instances.AddRange(_instances); } } private void save() { lock (this) { JSON.From(instances.ToArray()).WriteTo(DataBaseFile, true); } } public void Save() { save(); } public Guid RegisterBot(string DllPath, string ClassName) { Guid guid = Guid.NewGuid(); lock (this) { RegisterBot(DllPath, ClassName, guid); } return guid; } public void RegisterBot(string DllPath, string ClassName, Guid uid) { TradingBotInstance i = new TradingBotInstance(); i.DllPath = DllPath; i.ClassName = ClassName; i.UID = uid; lock (this) { this.instances.Add(i); Save(); } } public void UnregisterBot(Guid guid) { lock (this) { foreach (TradingBotInstance inst in instances) { if (inst.UID.Equals(guid)) { UnloadBot(inst); break; } } } } public void LoadBot(String uid){ LoadBot(findBot(Guid.Parse(uid))); } public void UnloadBot(String uid) { UnloadBot(findBot(Guid.Parse(uid))); } public void LoadBot(Guid uid) { LoadBot(findBot(uid)); } public void UnloadBot(Guid uid) { UnloadBot(findBot(uid)); } public void LoadBotAndPrepare(Guid uid) { LoadBotAndPrepare(findBot(uid)); } public void LoadBotAndPrepare(TradingBotInstance bot) { bot.Load(BotEnvironment); bot.Prepare(); } public void LoadBot(TradingBotInstance bot) { bot.Load(BotEnvironment); } public void UnloadBot(TradingBotInstance bot) { bot.Unload(); } public void LoadAllBots(){ foreach (TradingBotInstance bot in instances){ bot.Load(BotEnvironment); } } public TradingBotInstance[] RegisteredBots{ get { return this.instances.ToArray(); } } private TradingBotInstance findBot(Guid uid){ foreach (TradingBotInstance inst in instances){ if (inst.UID.Equals(uid)){ return inst; } } return null; } public override string ToString() { StringBuilder sb = new StringBuilder(); sb.AppendLine("[BotManager Dump]"); foreach (TradingBotInstance i in instances) { sb.AppendLine(i.ToString()); } return sb.ToString(); } } [JSONClassPolicy(Policy = JSONPolicy.ATTRIBUTED)] public class TradingBotInstance : MarshalByRefObject { [JSONField] public String DllPath { get; set; } [JSONField] public String ClassName { get; set; } [JSONField] public Guid UID { get; set; } private AppDomain _appDomain; private Assembly _assembly; private TradeBotLoader loader; private TradingBot _instance; private Logger _logger; /* public void Load(TradingBotEnvironment environment) { AppDomainSetup ads = new AppDomainSetup(); // ads.ApplicationBase = AppDomain.CurrentDomain.BaseDirectory; this._appDomain = AppDomain.CreateDomain(String.Format("TradeBotLoader:{0}:{1}", UID, Guid.NewGuid().ToString()), AppDomain.CurrentDomain.Evidence, ads); this.loader = (TradeBotLoader)this._appDomain.CreateInstanceFromAndUnwrap("sharp.tradebot.dll", "sharp.tradebot.TradeBotLoader"); this.loader.DllPath = DllPath; this.loader.ClassName = ClassName; this.loader.UID = UID; this.loader.Load(environment); } public void Unload() { if (this.loader != null){ this.loader.Unload(); } AppDomain.Unload(this._appDomain); this._appDomain = null; this.loader = null; } public void Prepare() { if (this.loader != null){ this.loader.Prepare(); } } public void Unprepare() { if (this.loader != null){ this.loader.Unprepare(); } } */ public void Load(TradingBotEnvironment environment) { //AppDomainSetup ads = new AppDomainSetup(); // ads.ApplicationBase = AppDomain.CurrentDomain.BaseDirectory; //this._appDomain = AppDomain.CreateDomain(String.Format("{0}:{1}:{2}:{3}", DllPath, ClassName, UID, Guid.NewGuid().ToString()), AppDomain.CurrentDomain.Evidence, ads); //this._instance = (TradingBot)this._appDomain.CreateInstanceFromAndUnwrap(DllPath, ClassName); this._instance = (TradingBot)Activator.CreateInstanceFrom(DllPath, ClassName).Unwrap(); this._logger = new FileLogger(Path.Combine(environment.BaseDataDirectory, "logs", String.Format("{0}.log", UID.ToString()))); this._instance.AfterLoad(environment, UID, this._logger,null); } public void Unload() { if (this._instance != null) { lock (this._instance) { if (this._instance.IsPrepared) { this._instance.Unprepare(); } this._logger.Close(); this._logger = null; } this._instance = null; //AppDomain.Unload(this._appDomain); this._appDomain = null; } } public void Prepare() { if (this._instance != null) { lock (this._instance) { this._instance.Prepare(); } } } public void Unprepare() { if (this._instance != null) { lock (this._instance) { this._instance.Unprepare(); } } } } } /** * [JSONClassPolicy(Policy = JSONPolicy.ATTRIBUTED)] public class BotDll { [JSONField] public string FileName { get; private set;} private AppDomain appDomain; private Assembly assembly; public Type[] BotClasses { get; private set; } public BotDll(string filename){ FileName = filename; } public void Load(){ if (appDomain == null){ AppDomainSetup ads = new AppDomainSetup(); ads.ApplicationBase = AppDomain.CurrentDomain.BaseDirectory; this.appDomain = AppDomain.CreateDomain(FileName,AppDomain.CurrentDomain.Evidence,ads); //this.assembly = this.appDomain.Load(FileName); try { TradingBot bot = (TradingBot)this.appDomain.CreateInstanceFromAndUnwrap(FileName, "BigBot.BigBot"); } catch (Exception e){ Console.WriteLine(e); } Scan(); } else { throw new InvalidOperationException("BotDll already loaded."); } } public void Unload(){ if (appDomain != null){ AppDomain.Unload(appDomain); BotClasses = null; assembly = null; appDomain = null; } else { throw new InvalidOperationException("BotDll is not loaded."); } } private void Scan(){ List botclasses = new List(); Console.WriteLine("Scanning...."); foreach (Type t in this.assembly.ExportedTypes){ if (t.IsSubclassOf(typeof(TradingBot))){ Console.WriteLine("Found BotClass: {0}", t.Name); botclasses.Add(t); } else { Console.WriteLine(" No BotClass: {0}", t.Name); } } BotClasses = botclasses.ToArray(); } } [JSONClassPolicy(Policy = JSONPolicy.ATTRIBUTED)] public class BotInstance { [JSONField] public String ClassName { get; private set; } [JSONField] public String InstanceUID { get; private set; } public BotDll Dll { get; set; } public BotInstance(){ InstanceUID = Guid.NewGuid().ToString(); } } } **/