internal void RestoreSession() { Log.Main.Inform("Restoring session: " + This.TimeMark); restoring = true; Dictionary <int, InputItem> input_item_id2input_items = new Dictionary <int, InputItem>(); Dictionary <int, TagItem> tag_item_id2tag_items = new Dictionary <int, TagItem>(); try { startReading(); string tag; Dictionary <string, object> names2value; while (readNextElement(out tag, out names2value)) { if (tag == QueueTag) { string name = (string)names2value["name"]; int position = (int)names2value["position"]; Session.SetInputItemQueuePosition(name, position); continue; } if (tag.StartsWith("__")) { continue; } string type_name = tag; int id = (int)names2value["id"]; if (id > This.item_count) { This.item_count = id; } if (input_item_type_names2input_item_type.ContainsKey(type_name)) { InputItem parent_item = null; object o; if (names2value.TryGetValue("parent_id", out o)) { parent_item = input_item_id2input_items[(int)o]; } string queue; if (names2value.TryGetValue("queue", out o)) { queue = (string)o; } else { queue = type_name; } InputItemState state = (InputItemState)names2value["state"]; if (state == InputItemState.ERROR_RESTORE_AS_NEW && !Settings.Engine.RestoreErrorItemsAsNew) { state = InputItemState.ERROR; } switch (state) { case InputItemState.NEW: Type type = input_item_type_names2input_item_type[type_name]; Dictionary <string, TagItem> fields2tag_item = new Dictionary <string, TagItem>(); Dictionary <string, string> attr_names2tag_item_id = new Dictionary <string, string>(); foreach (string name in names2value.Keys) { Match m = Regex.Match(name, "^id_of_(?'ItemTypeName'.+)"); if (!m.Success) { continue; } fields2tag_item[m.Groups["ItemTypeName"].Value] = tag_item_id2tag_items[int.Parse(attr_names2tag_item_id[name])]; } ArrayList seed = (ArrayList)names2value["seed"]; InputItem item = InputItem.Restore(GetInputItemQueue(queue), type, seed, id, parent_item, fields2tag_item); input_item_id2input_items[id] = item; break; case InputItemState.COMPLETED: case InputItemState.ERROR: input_item_id2input_items[id].__State = state; break; default: throw new Exception("Unknown item state: " + state); } } else if (work_item_type_names2work_item_type.ContainsKey(type_name)) { string key = (string)names2value["key"]; ArrayList seed = (ArrayList)names2value["seed"]; This.GetRestoredWorkItemDictionary(work_item_type_names2work_item_type[type_name]).Restore(key, seed, id); } else if (tag_item_type_names2tag_item_type.ContainsKey(type_name)) { ArrayList seed = (ArrayList)names2value["seed"]; TagItem item = Cliver.Bot.TagItem.Restore(tag_item_type_names2tag_item_type[type_name], seed, id); tag_item_id2tag_items[item.__Id] = item; } else { throw new Exception("Unknown item type in the sesson log: " + type_name); } } } catch (Exception e) { __ErrorClose(e, true); } foreach (InputItemQueue iiq in This.input_item_queue_name2input_item_queues.Values) { iiq.OmitRestoredProcessedItems(); } restoring = false; }
void bot_cycle() { try { typeof(BotCycle).GetField("Id", BindingFlags.NonPublic | BindingFlags.Instance).SetValue(this, Log.Id); lock (id2bot_cycles) { id2bot_cycles[Id] = this; } if (Created != null) { Created.Invoke(Id); } bot = CustomizationApi.CreateBot(); if (bot == null) { throw (new Exception("Could not create Bot instance.")); } typeof(Bot).GetField("BotCycle", BindingFlags.Instance | BindingFlags.NonPublic).SetValue(bot, this); Counter processor_errors = new Counter("processor_errors", Properties.General.Default.MaxProcessorErrorNumber); bot.CycleBeginning(); while (run) { current_item = Session.This.GetNext(); if (current_item == null) { return; } InputItemState state = InputItemState.COMPLETED; try { current_item.PROCESSOR(this); } catch (ThreadAbortException) { return; } catch (Exception e) { if (e is TargetInvocationException) { e = e.InnerException; } if (e is ProcessorException) { switch (((ProcessorException)e).Type) { case ProcessorExceptionType.ERROR: state = InputItemState.ERROR; break; case ProcessorExceptionType.RESTORE_AS_NEW: state = InputItemState.ERROR_RESTORE_AS_NEW; Session.This.IsItem2Restore = true; break; case ProcessorExceptionType.COMPLETED: break; default: throw new Exception("No case for " + ((ProcessorException)e).Type.ToString()); } } else { state = InputItemState.ERROR; } Log.Error(e); } current_item.__State = state; if (state == InputItemState.ERROR || state == InputItemState.ERROR_RESTORE_AS_NEW) { processor_errors.Increment(); } else { processor_errors.Reset(); } Start(); } bot.CycleFinishing(); } catch (ThreadAbortException) { } catch (Exception e) { LogMessage.Exit(e); } finally { close_thread(Id); } }
/// <summary> /// Restore session from the specified session file. /// </summary> /// <param name="items_xml_file">previous session file where data is to be restored from</param> void restore_session_from_xml_file(string items_xml_file) { Dictionary <int, InputItem> input_item_id2input_items = new Dictionary <int, InputItem>(); Dictionary <int, TagItem> tag_item_id2tag_items = new Dictionary <int, TagItem>(); Regex tag_item_field_filter = new Regex("^id_of_(?'ItemTypeName'.+)"); try { XmlTextReader xtr = new XmlTextReader(items_xml_file); while (xtr.Read()) { if (xtr.Name == "Items") { break; } } while (xtr.Read()) { if (xtr.NodeType != XmlNodeType.Element) { continue; } //if (xtr.Name == "__QueueOrder") //{ // string[] iiqns = xtr.ReadInnerXml().Split('\n'); // Session.SetInputItemQueuesOrder(iiqns); // continue; //} if (xtr.Name == "__Queue") { string name = xtr.GetAttribute("name"); int position = int.Parse(xtr.GetAttribute("position")); Session.SetInputItemQueuePosition(name, position); continue; } string type_name = xtr.Name; int id = int.Parse(xtr.GetAttribute("id")); string seed = xtr.GetAttribute("seed"); if (id > item_count) { item_count = id; } if (input_item_type_name2input_item_types.ContainsKey(type_name)) { InputItem parent_item = null; string parent_id = xtr.GetAttribute("parent_id"); if (parent_id != null) { parent_item = input_item_id2input_items[int.Parse(parent_id)]; } string queue = xtr.GetAttribute("queue"); if (queue == null) { queue = type_name; } InputItemState state = (InputItemState)Enum.Parse(typeof(InputItemState), xtr.GetAttribute("state"), true); if (state == InputItemState.ERROR_RESTORE_AS_NEW && !Properties.General.Default.RestoreErrorItemsAsNew) { state = InputItemState.ERROR; } switch (state) { case InputItemState.NEW: Type type = input_item_type_name2input_item_types[type_name]; Dictionary <string, string> attr_name2tag_item_id_s = xtr.GetAttributeName2AttributeValues(tag_item_field_filter); Dictionary <string, TagItem> field2tag_items = new Dictionary <string, TagItem>(); foreach (string name in attr_name2tag_item_id_s.Keys) { field2tag_items[tag_item_field_filter.Match(name).Groups["ItemTypeName"].Value] = tag_item_id2tag_items[int.Parse(attr_name2tag_item_id_s[name])]; } InputItem item = InputItem.Restore(GetInputItemQueue(queue), type, seed, id, parent_item, field2tag_items); input_item_id2input_items[id] = item; break; case InputItemState.COMPLETED: case InputItemState.ERROR: //case InputItemState.ERROR_RESTORE_AS_NEW: input_item_id2input_items[id].__State = state; break; } } else if (work_item_type_name2work_item_types.ContainsKey(type_name)) { string key = xtr.GetAttribute("key"); GetRestoredWorkItemDictionary(work_item_type_name2work_item_types[type_name]).Restore(key, seed, id); } else if (tag_item_type_name2tag_item_types.ContainsKey(type_name)) { TagItem item = Cliver.Bot.TagItem.Restore(tag_item_type_name2tag_item_types[type_name], seed, id); tag_item_id2tag_items[item.__Id] = item; } } } catch (XmlException e) { Log.Main.Warning("Session restoring: " + Log.GetExceptionMessage(e)); } catch (Exception e) { LogMessage.Error("Session restoring: " + Log.GetExceptionMessage(e)); } foreach (InputItemQueue iiq in input_item_queue_name2input_item_queues.Values) { iiq.OmitRestoredProcessedItems(); } Log.Main.Write("Items were restored from " + items_xml_file.ToString()); }
void bot_cycle() { try { try { Created?.Invoke(Id); __Starting(); while (run) { current_item = Session.This.GetNext(); if (current_item == null) { return; } InputItemState state = InputItemState.COMPLETED; try { current_item.__Processor(this); } catch (ThreadAbortException) { Thread.ResetAbort(); return; } catch (Session.FatalException) { throw; } catch (Exception e) { if (e is TargetInvocationException) { e = e.InnerException; //throw; } if (e is ProcessorException) { switch (((ProcessorException)e).Type) { case ProcessorExceptionType.ERROR: state = InputItemState.ERROR; break; //case ProcessorExceptionType.FatalError: case ProcessorExceptionType.RESTORE_AS_NEW: state = InputItemState.ERROR_RESTORE_AS_NEW; Session.This.IsItem2Restore = true; break; case ProcessorExceptionType.COMPLETED: break; default: throw new Exception("No case for " + ((ProcessorException)e).Type.ToString()); } } else { if (TreatExceptionAsFatal) { throw new Session.FatalException(e); } state = InputItemState.ERROR; } Log.Error(e); } current_item.__State = state; if (state == InputItemState.ERROR || state == InputItemState.ERROR_RESTORE_AS_NEW) { Session.This.ProcessorErrors.Increment(); } else { Session.This.ProcessorErrors.Reset(); } Start(); } } catch (ThreadAbortException) { Thread.ResetAbort(); } //catch (Exception e) //{ // throw new Session.FatalException(e); //} finally { __Exiting(); if (Finishing != null) { Finishing.Invoke(Id); } } } catch (Exception e) { Session.__ErrorClose(e, true); } finally { close_thread(Thread.CurrentThread); } }