public Expression Parse(IParser parser) { var segments = new List <ExpressionSegment>(); while (!parser.Is('`')) { if (parser.Is('$')) { parser.Expect('$'); parser.Skip(); parser.Expect('{'); parser.Skip(); parser.SkipWhitespace(); var segment = new ExpressionSegment(ExpressionSegmentType.Interpolated, parser.ReadUntil('}')); segments.Add(segment); parser.SkipWhitespace(); parser.Expect('}'); parser.Skip(); } else { segments.Add(new ExpressionSegment(ExpressionSegmentType.Literal, parser.ReadUntil('$', '`'))); } } return(new Expression(segments)); }
private void AggregateMethodCalls(Func<AssertionComponent, string, int, ExpressionSegment> getSegment, Action<ExpressionSegment> useSegment) { SourceAddress assertionsAddress = calls.First().SourceAddress; string[] sourceLines; if (!Utils.TryReadAllLines(assertionsAddress, out sourceLines)) return; string expressionSource = sourceLines.Skip(assertionsAddress.LineIndex).Join(Environment.NewLine); ExpressionSegment segment = new ExpressionSegment { IndexOfNextSegment = assertionsAddress.ExpressionIndex }; foreach (AssertionComponent method in MethodCalls) { segment = getSegment(method, expressionSource, segment.IndexOfNextSegment); useSegment(segment); } }
IEnumerable <ExpressionSegment> ToParts(string expr) { if (string.IsNullOrEmpty(expr)) { yield break; } int len = expr.Length; char ch; int offset = 0; int count = 0; bool isKw; string keyword = null; bool isWord = false; bool isDigit = false; int index = 0; bool isString = false; ExpressionSegment prev = null; ExpressionSegment current; for (int i = 0; i < len; i++) { ch = expr[i]; isKw = false; if (offset == i) { if (isSpaceChar(ch)) { offset = i + 1; count = 0; continue; } isString = false; isWord = false; isDigit = false; if (ch == '"') { isString = true; count = 0; continue; } else if (IsStartChar(ch)) { isWord = true; } else { if (IsDigit(ch)) { isDigit = true; } } count = 1; if (!isWord && !isDigit) { if (kws.ContainsKey(ch.ToString())) { bool isOper = true; //if (ch == '(' || ch == ')') // isOper = false; if (i < len - 1 && kws.ContainsKey(ch.ToString() + expr[i + 1])) { current = new ExpressionSegment() { Index = index++, Expr = ch.ToString() + expr[i + 1], Offset = offset, Length = 2, IsKeyword = true, IsOper = isOper, Prev = prev }; yield return(current); prev = current; i++; offset = i + 1; } else { current = new ExpressionSegment() { Index = index++, Expr = ch.ToString(), Offset = offset, Length = 1, IsKeyword = true, IsOper = isOper, Prev = prev }; yield return(current); prev = current; offset = i + 1; } } } continue; } else { if (isString) { if (ch != '"') { count++; continue; } current = new ExpressionSegment() { Index = index++, Expr = expr.Substring(offset + 1, count), IsString = true, Offset = offset, Length = count + 2, Prev = prev, }; yield return(current); prev = current; offset = i + 1; isString = false; continue; } else if (isDigit) { if (IsDigit(ch)) { count++; continue; } } else if (isWord) { if (IsMemberChar(ch)) { count++; continue; } } else { if (!IsStartChar(ch) && !IsDigit(ch) && ch != '"') { count++; continue; } } } if (count > 0) { current = new ExpressionSegment() { Index = index++, Expr = expr.Substring(offset, count), Offset = offset, Length = count, Prev = prev, }; if (isDigit) { current.IsDigit = true; } else { current.IsOper = kws.ContainsKey(current.Expr); } yield return(current); prev = current; } i--; offset = i + 1; count = 0; } if (len > offset) { current = new ExpressionSegment() { Index = index++, Expr = expr.Substring(offset, len - offset), Offset = offset, Length = len - offset, Prev = prev }; if (isDigit) { current.IsDigit = true; } else { current.IsOper = kws.ContainsKey(current.Expr); } yield return(current); prev = current; } }