public void Visit(CaseStatement statement)
        {
            object value = null;

            foreach (var when in statement.WhenExpression)
            {
                var arg = new QueryPhaseArgs();
                VisitChild(when.BooleanExpression, arg);
                if (arg.RowResult) //we matched
                {
                    arg = new QueryPhaseArgs();
                    arg.BoolQueryArg = new Http.QueryArgs();
                    VisitChild(when.Variable, arg); //want to get it's value
                    value = arg.BoolQueryArg.PropertyValue.Value;
                    break;
                }
            }

            if (value == null && statement.ElseVariable != null)
            {
                var arg = new QueryPhaseArgs();
                arg.BoolQueryArg = new Http.QueryArgs();
                VisitChild(statement.ElseVariable, arg); //want to get it's value
                value = arg.BoolQueryArg.PropertyValue.Value;
            }

            _visitStack.Peek().BoolQueryArg.PropertyValue = new PropertyValue(value);
        }
Esempio n. 2
0
        private QueryPhaseArgs VisitChild(Element node, QueryPhaseArgs arg)
        {
            if (node != null)
            {
                _visitStack.Push(arg);
                node.Accept(this);
                return(_visitStack.Pop());
            }

            return(null);
        }
        public void Visit(NestedFromStatement statement)
        {
            var args = new QueryPhaseArgs();

            VisitChild(statement.Query, args);

            if (args.QueryTable != null && statement.Alias != null)
            {
                _scope.AddTable(statement.Alias, args.QueryTable);
            }

            VisitChild(statement.InnerJoin);
        }
        public void Visit(OrExpression expression)
        {
            var parentArgs = _visitStack.Peek() as QueryPhaseArgs;

            var leftArts = new QueryPhaseArgs();

            VisitChild(expression.Left, leftArts);
            var rightArgs = new QueryPhaseArgs();

            VisitChild(expression.Right, rightArgs);

            parentArgs.RowResult = leftArts.RowResult || rightArgs.RowResult;
        }
        public void Visit(SubtractExpression expression)
        {
            var leftArg = new QueryPhaseArgs()
            {
                BoolQueryArg = new QueryArgs()
            };

            VisitChild(expression.Left, leftArg);

            var rightArg = new QueryPhaseArgs()
            {
                BoolQueryArg = new QueryArgs()
            };

            VisitChild(expression.Right, rightArg);

            _visitStack.Peek().BoolQueryArg.PropertyValue = ValidateTypes(leftArg.BoolQueryArg, rightArg.BoolQueryArg, (l, r) => l - r);
        }
        public void Visit(GreaterThanExpression expression)
        {
            var leftArg = new QueryPhaseArgs()
            {
                BoolQueryArg = new QueryGreaterThan()
            };

            VisitChild(expression.Left, leftArg);

            var rightArg = new QueryPhaseArgs()
            {
                BoolQueryArg = new QueryGreaterThan()
            };

            VisitChild(expression.Right, rightArg);

            var parentArgs = _visitStack.Peek();

            parentArgs.RowResult = ValidateTypes(leftArg.BoolQueryArg, rightArg.BoolQueryArg, (l, r) => l > r);
        }
        public void Visit(SelectStatement statement)
        {
            var executedTables = _scope.FetchAllExecutedTablesSameLevel();

            if (executedTables.Length == 0) //no executed tables. nothing to do
            {
                return;
            }

            var dynamicColumns = new List <DynamicColumn>();
            var descriptors    = new List <IResult>();

            if (statement.All) //get all columns
            {
                var selectedIndex = 0;
                foreach (var executeTable in executedTables)
                {
                    foreach (var p in executeTable.Descriptor.Properties)
                    {
                        int propIndex = executeTable.Descriptor.GetDataRowIndex(p.Name);
                        descriptors.Add(new SelectColumn()
                        {
                            Table = executeTable, PropDescriptor = p, PropIndex = propIndex
                        });

                        if (selectedIndex >= statement.Args.Length)
                        {
                            var selectArg = new SelectArgExpression(statement.Bounds);
                            selectArg.Children.Add(new SingleVariableExpression(statement.Bounds)
                            {
                                Id = p.Name
                            });
                            statement.Children.Add(selectArg);
                        }
                        selectedIndex++;
                    }
                }
            }
            else
            {
                for (int selectIndex = 0; selectIndex < statement.Args.Length; selectIndex++)
                {
                    Array.ForEach(executedTables, (x) => x.SelectIndex = selectIndex);
                    var arg = new QueryPhaseArgs();
                    VisitChild(statement.Args[selectIndex], arg);

                    if (arg.BoolQueryArg.Table == null) //can't find selected PropertyDescriptor. Must be a statement
                    {
                        var prop = new PropertyDescriptor()
                        {
                            Name = arg.BoolQueryArg.Variable ?? "(No column name)"
                        };
                        var dynamicColumn = new DynamicColumn {
                            SelectArgExpression = statement.Args[selectIndex], PropDescriptor = prop
                        };
                        descriptors.Add(dynamicColumn);
                        dynamicColumns.Add(dynamicColumn);
                    }
                    else
                    {
                        int propIndex = arg.BoolQueryArg.Table.Descriptor.GetDataRowIndex(arg.BoolQueryArg.Property.Name);
                        arg.BoolQueryArg.Property.Name = arg.BoolQueryArg.Variable;
                        descriptors.Add(new SelectColumn()
                        {
                            Table = arg.BoolQueryArg.Table, PropDescriptor = arg.BoolQueryArg.Property, PropIndex = propIndex
                        });
                    }
                }
            }

            //need to go through every row here of select dynamic statement then add it Properties
            if (executedTables.Length > 0)
            {
                var rowCount = executedTables.First().Rows.Length;
                for (int row = 0; row < rowCount; row++)
                {
                    Array.ForEach(executedTables, (x) => x.RowIndex = row);
                    foreach (var d in dynamicColumns) //run each column. Value goes in data at selected index
                    {
                        var arg = new QueryPhaseArgs();
                        VisitChild(d.SelectArgExpression, arg);
                        d.Values.Add(arg.BoolQueryArg.PropertyValue);
                    }
                }
            }

            var rows = new List <Row>();

            if (executedTables.Length > 0)
            {
                var rowCount = executedTables.First().Rows.Length;
                for (int rowIndex = 0; rowIndex < rowCount; rowIndex++) //select data for only those columns selected
                {
                    var values = new List <PropertyValue>();
                    for (int selectIndex = 0; selectIndex < statement.Args.Length; selectIndex++)
                    {
                        var selectedColumn = descriptors[selectIndex];
                        values.Add(selectedColumn.Fetch(rowIndex));
                    }

                    rows.Add(new Row()
                    {
                        Values = values.ToArray()
                    });
                }
            }

            var             finalDescriptors = descriptors.Select(x => x.Descriptor()).ToArray();
            TableDescriptor tableDescriptor;

            //if nested
            if (statement.IsNestedQuery)
            {
                var dups = finalDescriptors.GroupBy(x => x.Name).Where(g => g.Count() > 1).Select(x => x.Key).ToList();
                if (dups.Count > 1) //error
                {
                }

                tableDescriptor = finalDescriptors;
            }
            else
            {
                FinalSelectTableDescriptor ftableDescriptor = descriptors.Select(x => x.Descriptor()).ToArray();
                tableDescriptor = ftableDescriptor;
            }

            var selectTable = new ExecutedTable(tableDescriptor)
            {
                Rows = rows.ToArray()
            };

            _visitStack.Peek().QueryTable = selectTable;

            if (!statement.IsNestedQuery)
            {
                _selectResult.Add(ToSelectTable(selectTable));
            }
        }
        public void Visit(QueryStatement statement)
        {
            using (var s = _scope.Push())
            {
                //Visit from to get tables in scope
                if (statement.From != null)
                {
                    VisitChild(statement.From);
                }

                var executedTables = _scope.FetchAllExecutedTablesSameLevel();
                if (executedTables.Length > 0 && statement.Where != null)
                {
                    var rowCount = executedTables.First().Rows.Length;
                    if (rowCount == 0) //even if no rows we still want to validate where variables
                    {
                        Array.ForEach(executedTables, (x) => x.RowIndex = 0);
                        var arg = new QueryPhaseArgs();
                        VisitChild(statement.Where, arg);
                    }
                    else
                    {
                        for (int row = 0; row < rowCount; row++)
                        {
                            Array.ForEach(executedTables, (x) => x.RowIndex = row);
                            var arg = new QueryPhaseArgs();
                            VisitChild(statement.Where, arg);
                            if (!arg.RowResult)
                            {
                                Array.ForEach(executedTables, (x) => x.Rows[x.RowIndex].Match = false);
                            }
                        }
                    }

                    //remove rows that didn't match through all executed tables
                    executedTables = _scope.FetchAllExecutedTablesSameLevel();
                    Array.ForEach(executedTables, (e) =>
                    {
                        var joinedRows = new List <Row>();
                        Array.ForEach(e.Rows, r =>
                        {
                            if (r.Match)
                            {
                                joinedRows.Add(r);
                            }
                        });

                        e.Rows = joinedRows.ToArray();
                    });
                }

                if (statement.Limit != null)
                {
                    VisitChild(statement.Limit);
                }

                var args = new QueryPhaseArgs();
                if (statement.Select != null)
                {
                    VisitChild(statement.Select, args);
                }

                _visitStack.Peek().QueryTable = args.QueryTable;

                if (statement.Bounds.Contains(_editorCursor) && ScopeModel == null)
                {
                    ScopeModel = _scope.BuildScopeModel();
                }
            }
        }
Esempio n. 9
0
        public void Visit(InnerJoinStatement statement)
        {
            string tableName = statement.Name;

            string tableVariable;

            if (statement.Alias != null)
            {
                tableVariable = statement.Alias;
            }
            else
            {
                tableVariable = statement.Name;
            }

            if (_scope.IsTableDefineSameLevel(tableName)) //table exists already
            {
                Errors.Add(new TableConflict(tableName, statement.Bounds.Start));
            }

            if (!_scope.IsTableDefinedAnyLevel(tableName)) //we don't know this table at any level
            {
                Errors.Add(new TableNotDefined(tableName, statement.Bounds.Start));
                return;
            }

            if (_scope.IsTableDefineSameLevel(tableVariable)) //if alias variable exists we have conflict
            {
                throw new InvalidOperationException("");
            }

            var executedTables = _scope.FetchAllExecutedTablesSameLevel();
            int rowCount       = 0;

            if (executedTables.Length > 0)
            {
                rowCount = executedTables.First().Rows.Length;
            }

            var rightTableRows = new List <Row>();

            if (rowCount == 0) //need to visit for semantic errors
            {
                var table = _scope.TableLookupAnyLevel(tableName);
                table = table.Create();
                _scope.AddTable(tableVariable, table);
                VisitChild(statement.BooleanExpression);
                VisitWhereIgnoreErrors(statement.ParentQueryStatement.Where);

                var executeTable = table.Execute(statement.ParentQueryStatement.Limit);
                foreach (var e in table.Errors)
                {
                    Errors.Add(e);
                }

                _scope.RemoveTable(tableVariable);
            }
            else
            {
                for (int row = 0; row < rowCount; row++)
                {
                    var table = _scope.TableLookupAnyLevel(tableName);
                    table = table.Create();
                    _scope.AddTable(tableVariable, table);

                    Array.ForEach(executedTables, (x) => x.RowIndex = row);
                    VisitChild(statement.BooleanExpression);
                    VisitWhereIgnoreErrors(statement.ParentQueryStatement.Where);
                    var executeTable = table.Execute(statement.ParentQueryStatement.Limit);

                    foreach (var e in table.Errors)
                    {
                        Errors.Add(e);
                    }

                    _scope.RemoveTable(tableVariable);            //remove query table
                    _scope.AddTable(tableVariable, executeTable); // add execute table
                    var arg = new QueryPhaseArgs();
                    VisitChild(statement.BooleanExpression, arg);
                    if (arg.RowResult) //row passed join. If didn't row needs to be removed from the left joining result
                    {
                        Array.ForEach(executedTables, (x) => x.Rows[x.RowIndex].Expand = executeTable.Rows.Length);
                        rightTableRows.AddRange(executeTable.Rows);
                    }
                    else //flag row as unmatching for all executed tables
                    {
                        Array.ForEach(executedTables, (x) => x.Rows[x.RowIndex].Match = false);
                    }

                    _scope.RemoveTable(tableVariable);
                }
            }

            var returnTable        = _scope.TableLookupAnyLevel(tableName);
            var returnExecuteTable = new ExecutedTable(returnTable.Create().Descriptor)
            {
                Rows = rightTableRows.ToArray()
            };

            _scope.AddTable(tableVariable, returnExecuteTable);

            executedTables = _scope.FetchAllExecutedTablesSameLevel();
            Array.ForEach(executedTables, (e) =>
            {
                var joinedRows = new List <Row>();

                //Add matched rows
                Array.ForEach(e.Rows, r => {
                    if (r.Match)
                    {
                        for (int x = 0; x < r.Expand; x++)
                        {
                            joinedRows.Add(r);
                        }
                    }
                });

                e.Rows = joinedRows.ToArray();
            });

            VisitChild(statement.InnerJoin);
        }