public void Load() { Log.Info("Loading rules"); using (var progress = Display.StartProgress("Loading rules")) { long total = context.Plugins.Count; long current = 0; foreach (var pluginFileName in context.Plugins.Select(p => p.FileName)) { bool retry; do { retry = false; try { var compiler = new RuleCompiler(this, pluginFileName); string path = Path.Combine(Program.ProgramFolder, Program.ProgramRulesFolder, RulesFolder, pluginFileName); var files = Context.DataFileProvider.FindDataFiles(path, "*.rules").ToArray(); total += files.Length; foreach (var file in files) { using (var stream = file.Open()) { bool isDebugModeEnabled = DebugAll || pluginFileName.Equals(DebugPluginFileName, StringComparison.OrdinalIgnoreCase) && (DebugRuleFileName == null || Path.GetFileName(file.Name).Equals(DebugRuleFileName, StringComparison.OrdinalIgnoreCase)); int count = 0; using (RuleReader reader = new RuleReader(stream)) { foreach (var entry in reader.ReadRules()) { if (entry.Select == null && entry.Update == null && entry.Inserts.Count() == 0) { Log.Warning("Rule {0} in file {1} ignored because it lacks any operation", entry.Name, pluginFileName); continue; } var metadata = new RuleMetadata() { PluginFileName = pluginFileName, RuleFileName = Path.GetFileName(file.Name), Name = entry.Name, Description = entry.Description, }; Log.Fine("Loading rule {0}\\{1}@{2}", metadata.PluginFileName, metadata.RuleFileName, metadata.Name); try { compiler.Add(entry, metadata, isDebugModeEnabled); } catch (IllegalTokenException ex) { Display.ShowProblems("Illegal Token", ex.ToString(), new Problem() { Message = ex.Message, File = file.GetRelativePath(), Solution = string.Format("Please avoid using the following tokens in rule code: {0}", string.Join(", ", RuleCompiler.GetIllegalCodeTokens())) }); throw; } count++; } } Log.Fine("Loaded {0} rule(s) from file {1}", count, stream.Name); } progress.Update(current, total, string.Format("{0}\\{1}", pluginFileName, Path.GetFileName(file.Name))); } if (compiler.HasRules) { try { compiler.CompileAll(); } catch (CompilerException ex) { StringBuilder text = new StringBuilder(); List <Problem> problems = new List <Problem>(); foreach (System.CodeDom.Compiler.CompilerError error in ex.Errors) { if (!error.IsWarning) { text.AppendLine(error.ToString()); problems.Add(new Problem() { Message = string.Format("{0}: {1}", error.ErrorNumber, error.ErrorText), File = DataFile.GetRelativePath(error.FileName), Line = error.Line, Column = error.Column, Solution = RuleCompiler.GetCompilerErrorHint(error) }); } } text.Append(ex.ToString()); Display.ShowProblems("Compiler Error(s)", text.ToString(), problems.ToArray()); throw ex; } rules.Add(pluginFileName, new List <IRule>(compiler.CompiledRules)); } } catch (Exception ex) { Log.Error("Error occured while loading rules for plugin {0} with message: {1}", pluginFileName, ex.Message); Log.Fine(ex.ToString()); // Depending on the kind of error, offer a choice to reload rules for this plugin // Rules can be reloaded only if illegal tokens have been detected or when compilation has failed ChoiceOption result = ChoiceOption.Cancel; if (ex.GetType() == typeof(IllegalTokenException) || ex.GetType() == typeof(CompilerException)) { result = Display.Choice(string.Format("Try loading rules for plugin {0} again?", pluginFileName), ChoiceOption.Yes, ChoiceOption.Continue, ChoiceOption.Cancel); } else { result = Display.Choice("Continue loading rules?", ChoiceOption.Continue, ChoiceOption.Cancel); } if (result == ChoiceOption.Yes) { Log.Info("Rules for plugin {0} will be reloaded.", pluginFileName); retry = true; } else if (result == ChoiceOption.Continue) { Log.Warning("Rules for plugin {0} skipped because an error occured: {1} ", pluginFileName, ex.Message); } else { Log.Warning("Rule loading has been aborted."); throw new UserAbortException("Rule loading has been aborted by the user."); } } finally { Display.ClearProblems(); } } while (retry); } current++; } }
public void Load() { Log.Info("Loading rules"); using (var progress = Display.StartProgress("Loading rules")) { long total = context.Plugins.Count; long current = 0; foreach (var pluginFileName in context.Plugins.Select(p => p.FileName)) { bool retry; do { retry = false; try { var compiler = new RuleCompiler(this, pluginFileName); string path = Path.Combine(Program.ProgramFolder, Program.ProgramRulesFolder, RulesFolder, pluginFileName); var files = Context.DataFileProvider.FindDataFiles(path, "*.rules").ToArray(); total += files.Length; foreach (var file in files) { using (var stream = file.Open()) { bool isDebugModeEnabled = DebugAll || pluginFileName.Equals(DebugPluginFileName, StringComparison.OrdinalIgnoreCase) && (DebugRuleFileName == null || Path.GetFileName(file.Name).Equals(DebugRuleFileName, StringComparison.OrdinalIgnoreCase)); int count = 0; using (RuleReader reader = new RuleReader(stream)) { foreach (var entry in reader.ReadRules()) { if (entry.Select == null && entry.Update == null && entry.Inserts.Count() == 0) { Log.Warning("Rule {0} in file {1} ignored because it lacks any operation", entry.Name, pluginFileName); continue; } var metadata = new RuleMetadata() { PluginFileName = pluginFileName, RuleFileName = Path.GetFileName(file.Name), Name = entry.Name, Description = entry.Description, }; Log.Fine("Loading rule {0}\\{1}@{2}", metadata.PluginFileName, metadata.RuleFileName, metadata.Name); try { compiler.Add(entry, metadata, isDebugModeEnabled); } catch (IllegalTokenException ex) { Display.ShowProblems("Illegal Token", ex.ToString(), new Problem() { Message = ex.Message, File = file.GetRelativePath(), Solution = string.Format("Please avoid using the following tokens in rule code: {0}", string.Join(", ", RuleCompiler.GetIllegalCodeTokens())) }); throw; } count++; } } Log.Fine("Loaded {0} rule(s) from file {1}", count, stream.Name); } progress.Update(current, total, string.Format("{0}\\{1}", pluginFileName, Path.GetFileName(file.Name))); } if (compiler.HasRules) { try { compiler.CompileAll(); } catch (CompilerException ex) { StringBuilder text = new StringBuilder(); List<Problem> problems = new List<Problem>(); foreach (System.CodeDom.Compiler.CompilerError error in ex.Errors) { if (!error.IsWarning) { text.AppendLine(error.ToString()); problems.Add(new Problem() { Message = string.Format("{0}: {1}", error.ErrorNumber, error.ErrorText), File = DataFile.GetRelativePath(error.FileName), Line = error.Line, Column = error.Column, Solution = RuleCompiler.GetCompilerErrorHint(error) }); } } text.Append(ex.ToString()); Display.ShowProblems("Compiler Error(s)", text.ToString(), problems.ToArray()); throw ex; } rules.Add(pluginFileName, new List<IRule>(compiler.CompiledRules)); } } catch (Exception ex) { Log.Error("Error occured while loading rules for plugin {0} with message: {1}", pluginFileName, ex.Message); Log.Fine(ex.ToString()); // Depending on the kind of error, offer a choice to reload rules for this plugin // Rules can be reloaded only if illegal tokens have been detected or when compilation has failed ChoiceOption result = ChoiceOption.Cancel; if (ex.GetType() == typeof(IllegalTokenException) || ex.GetType() == typeof(CompilerException)) { result = Display.Choice(string.Format("Try loading rules for plugin {0} again?", pluginFileName), ChoiceOption.Yes, ChoiceOption.Continue, ChoiceOption.Cancel); } else { result = Display.Choice("Continue loading rules?", ChoiceOption.Continue, ChoiceOption.Cancel); } if (result == ChoiceOption.Yes) { Log.Info("Rules for plugin {0} will be reloaded.", pluginFileName); retry = true; } else if (result == ChoiceOption.Continue) { Log.Warning("Rules for plugin {0} skipped because an error occured: {1} ", pluginFileName, ex.Message); } else { Log.Warning("Rule loading has been aborted."); throw new UserAbortException("Rule loading has been aborted by the user."); } } finally { Display.ClearProblems(); } } while (retry); } current++; } }