public bool ContainsKey(string name) { var res = vars.ContainsKey(name); if (!res && bvars != null) { res = bvars.ContainsKey(name); } return(res); }
public OssParseResult ParseOssString(string str, string rootPath) { int errors = 0; var insertedList = new List <string>(); var lres = new List <Rule>(); var namedRules = new Dictionary <string, Rule>(); var rheader = string.Empty; // named rule, used for inheritance string ruleName = null; var vars = new VarStorg(); //var vars = new SortedDictionary<string, OssVar>(new ReverseComparer<string>(StringComparer.InvariantCulture)); void ClearEmpty() { if (rheader.Trim(StrConst.EmptyChars).Length == 0) { rheader = string.Empty; } } void AddHeaderToBase(IEnumerable <string> inherits) { if (inherits == null) { return; } foreach (var name in inherits) { if (!namedRules.ContainsKey(name)) { logger.Error($"could not find name {name} to inherit"); errors++; continue; } //if (namedRules[name].IsEmpty) //{ // logger.Info($"inheriting empty rule {name}, statement can be removed"); //} var baseRule = namedRules[name]; if (baseRule.Header != null) { baseRule.Header = StrUtil.InsertStrBeforeEmptys(baseRule.Header, ",\r\n" + StrUtil.GetLastIndentation(baseRule.Header) + StrUtil.TrimEmptys(rheader)); } else { baseRule.Header = rheader; } AddHeaderToBase(baseRule.Inherits); } } for (var i = 0; i < str.Length; i++) { if (str.IsNextStr(i, OssConst.VarDeclKey)) { // var = x / {x:y} / { header { x: y } .. }; i += OssConst.VarDeclKey.Length; var varname = str.GetVarName(i, out i); var varval = str.GetVarVal(i, out i); var keepraw = false; if (varname[0] == ':') { keepraw = true; varname = varname.Substring(1); } var osv = new OssVar(); osv.Name = varname; osv.IsRules = varval.IsRules; osv.Val = osv.IsRules || keepraw ? new ParseContentRes { Content = varval.Val, IsRaw = true } : ParseContent(varval.Val, vars); osv.Val.RawContent = varval.Val; vars.Add(varname, osv); if (i < str.Length - 1 && str[i + 1] == ';') { i++; } rheader = rheader.TrimEnd(StrConst.EmptyChars); } else if (str.IsNextStr(i, "{")) { // rule block var endi = str.GetBlockEnd(i); var block = str.FromTo(i, endi); i = endi; var vpr = ParseContent(block, vars); var val = vpr.Content; var lrule = new Rule(); if (rheader.Trim(StrConst.EmptyChars) == string.Empty) { rheader = null; lrule.EmptyHeader = true; } lrule.Header = rheader; lrule.Body = val; lrule.Name = ruleName; lrule.Inherits = vpr.Inherits; lrule.IsEmpty = val.Trim(StrConst.RuleTrimChars).Length == 0; lres.Add(lrule); if (ruleName != null) { if (namedRules.ContainsKey(ruleName)) { logger.Error($"name {ruleName} already defined"); } namedRules.Add(ruleName, lrule); } if (vpr.Inherits.Any()) { AddHeaderToBase(vpr.Inherits); } rheader = string.Empty; ruleName = null; } else if (str.IsNextStr(i, OssConst.InsertKey)) { // insert file.txt content i += OssConst.InsertKey.Length; var url = str.GetNextWordToSemicol(i, out i); var insPath = rootPath + "\\" + url; // add inserted file to watchlist insertedList.Add(insPath); // read inserted file var instr = fileOp.ReadText(insPath); str = str.Insert(i + 1, instr); } else if (str.IsNextStr(i, OssConst.NameKey)) { // define rule name (for inheritance) i += OssConst.NameKey.Length; ruleName = str.GetNextWordToSemicol(i, out i); } else if (str.IsNextStr(i, OssConst.Atvar)) { // insert var content i += OssConst.Atvar.Length; var name = str.GetNextWordToSemicol(i, out i); if (vars.ContainsKey(name)) { var osv = vars[name]; if (string.IsNullOrWhiteSpace(osv.Val.RawContent)) { ClearEmpty(); } else { str = str.Insert(i + 1, osv.Val.RawContent); } } else { ClearEmpty(); logger.Info($"could not find var {name}"); } } else { var c = str[i]; rheader += c; } } lres.Add(new Rule { IsComment = true, Body = rheader }); var slres = string.Empty; foreach (var rule in lres.Where(o => !o.IsEmpty && o.Header != null)) { slres += rule.Header + rule.Body; } slres = slres.Trim(StrConst.EmptyChars); var unusedVars = vars.GetUnusedNames().ToArray(); if (unusedVars.Any()) { logger.Warn("unused variables: " + string.Join(", ", unusedVars)); } return(new OssParseResult { ParseRes = slres, InsertedFiles = insertedList, Errors = errors, UnusedVars = unusedVars }); }