/// <summary> /// add runnable to method and return double conditions side, parent and self /// </summary> /// <param name="runnable"></param> /// <returns></returns> public Tuple <IAddConditionSides, IAddConditionSides> AddDouble(IAddConditionSides runnable) { MethodBaseInfo instance = (MethodBaseInfo)Activator.CreateInstance(GetType()); instance.Parent = runnable; instance.PublicVariables = runnable.PublicVariables; return(new Tuple <IAddConditionSides, IAddConditionSides>(runnable.Add((IRunnable)instance), instance)); }
/// <summary> /// after finished to read a side need to calculate /// sides are left and right of an operator like '=' '>' '>=' etc /// </summary> /// <param name="data"></param> /// <param name="parent"></param> /// <param name="isString"></param> private IAddConditionSides CalculateSide(string data, IAddConditionSides parent, bool isString = false) { IRunnable sideValue = null; if (isString || double.TryParse(data, out double newData)) { sideValue = new ValueInfo() { Value = data, PublicVariables = parent.PublicVariables } } ; else { sideValue = new PropertyInfo() { PropertyPath = data, PublicVariables = parent.PublicVariables }; } return(parent.Add(sideValue)); }
/// <summary> /// extract full 'where' /// </summary> /// <param name="selectQuery"></param> /// <param name="index"></param> /// <param name="parent"></param> private void ExtractInside(string selectQuery, string breakString, char startChar, char breakChar, ref int index, IAddConditionSides parent) { //find variable with 'var' word byte foundVariableStep = 0; if (string.IsNullOrEmpty(breakString)) { foundVariableStep = 1; } bool canSkip = true; //variable name that found after 'var' string variableName = ""; string concat = ""; //calculate all of char after select query for (int i = index; i < selectQuery.Length; i++) { //current char char currentChar = selectQuery[i]; bool isWhiteSpaceChar = StringHelper.IsWhiteSpaceCharacter(currentChar); if (canSkip) { //skip white space chars if (isWhiteSpaceChar || (foundVariableStep == 0 && currentChar == startChar)) { continue; } else { canSkip = false; } } concat += currentChar; if (currentChar == breakChar) { concat = concat.Trim('}'); CheckVariable(currentChar, ref i, ref index); index = i; break; } if (isWhiteSpaceChar && foundVariableStep == 0 && concat.Trim().Equals("in", StringComparison.OrdinalIgnoreCase)) { foundVariableStep = 3; concat = ""; canSkip = true; } else if (foundVariableStep == 3 && isWhiteSpaceChar) { parent.Add(new PropertyInfo() { PropertyPath = concat.Trim(), PublicVariables = parent.PublicVariables }); foundVariableStep = 0; concat = ""; canSkip = true; } //find a side else if (foundVariableStep == 1) { if (currentChar == '"') { index = i; parent = ExtractString(selectQuery, ref index, parent); i = index; foundVariableStep = 2; concat = ""; variableName = ""; canSkip = true; } else { CheckVariable(currentChar, ref i, ref index); } } //find operator and parameter else if (foundVariableStep == 2) { //find next parameter of method if (currentChar == ',') { foundVariableStep = 1; concat = concat.Trim().Trim(',').Trim(); canSkip = true; continue; } //find operator else { string trim = concat.Trim().ToLower(); //now this is a method if (OperatorInfo.SupportedOperators.TryGetValue(trim, out OperatorType currentOperator)) { if (OperatorInfo.OperatorStartChars.Contains(selectQuery[i + 1])) { continue; } parent.ChangeOperatorType(currentOperator); //OperatorKey findEmpty = parent.WhereInfo.Operators.FirstOrDefault(x => x.OperatorType == OperatorType.None); foundVariableStep = 1; concat = ""; canSkip = true; } else if (concat.Equals("var", StringComparison.OrdinalIgnoreCase)) { index = i; do { index--; }while (selectQuery[index].ToString().ToLower() != "v"); VariableInfo newVariableInfo = new VariableInfo() { WhereInfo = new WhereInfo() }; newVariableInfo.Parent = parent.Parent; newVariableInfo.WhereInfo.Parent = newVariableInfo; newVariableInfo.WhereInfo.PublicVariables = newVariableInfo.PublicVariables; parent.Parent.Add(newVariableInfo); ExtractVariables(selectQuery, ref index, newVariableInfo.WhereInfo); i = index; concat = ""; canSkip = true; } else if (concat.Length > 3) { throw new Exception($"I cannot found operator,I try but found '{concat}' are you sure you don't missed?"); } } } else if (concat.Equals(breakString, StringComparison.OrdinalIgnoreCase)) { concat = ""; canSkip = true; foundVariableStep = 1; } } void CheckVariable(char currentChar, ref int i, ref int index2) { string trim = concat.Trim(); //step 1 of left side complete if (trim.Length > 0) { bool isFindingOperator = OperatorInfo.OperatorStartChars.Contains(currentChar); int findNextP = CheckFirstCharacterNoWitheSpace(selectQuery, i + 1, '('); if (currentChar == '(' || findNextP >= 0) { if (string.IsNullOrEmpty(variableName)) { IAddConditionSides addParent = null; //check if variable name is nuot null so its a method //else its just Parentheses if (!string.IsNullOrEmpty(trim.Trim('('))) { //method name variableName = trim.Trim('(').ToLower(); if (!SupportedMethods.TryGetValue(variableName, out IAddConditionSides addConditionSides)) { throw new Exception($"I cannot find method '{variableName}' are you sure you wrote true?"); } else { Tuple <IAddConditionSides, IAddConditionSides> value = addConditionSides.AddDouble(parent); parent = value.Item1; addParent = value.Item2; } variableName = ""; } else { addParent = parent.Add(); } concat = ""; if (findNextP >= 0) { index2 = findNextP + 1; } else { index2 = i + 1; } ExtractInside(selectQuery, null, '(', ')', ref index2, addParent); i = index2; foundVariableStep = 2; canSkip = true; } } else if (StringHelper.IsWhiteSpaceCharacter(currentChar) || isFindingOperator || currentChar == breakChar) { variableName = trim.Trim().Trim(breakChar).Trim(')').Trim(',').Trim(); concat = ""; canSkip = true; //if there was no space this will fix that //example user.name="ali" there is no space like user.name = "ali" if (isFindingOperator) { variableName = variableName.Trim(OperatorInfo.OperatorStartChars); i--; } if (foundVariableStep == 1) { //calculate left side parent = CalculateSide(variableName, parent); foundVariableStep++; canSkip = true; variableName = ""; } } else if (currentChar == ',') { variableName = trim.Trim().Trim(',').Trim(); if (!string.IsNullOrEmpty(variableName)) { if (foundVariableStep == 1) { //calculate left side parent = CalculateSide(variableName, parent); foundVariableStep++; canSkip = true; variableName = ""; concat = ""; } index2 = i; ExtractInside(selectQuery, null, ',', ')', ref index2, parent); i = index2 - 1; } } //variable is method //that is method so find method name and data //or is just inside of Parentheses } } }