Ejemplo n.º 1
0
        private WSelectElement ParseSelectElement(SelectElement sel)
        {
            if (sel == null)
            {
                return null;
            }

            switch (sel.GetType().Name)
            {
                case "SelectScalarExpression":
                    {
                        var sse = sel as SelectScalarExpression;
                        var pScalarExpr = new WSelectScalarExpression
                        {
                            SelectExpr = ParseScalarExpression(sse.Expression),
                            FirstTokenIndex = sse.FirstTokenIndex,
                            LastTokenIndex = sse.LastTokenIndex
                        };
                        if (sse.ColumnName != null)
                        {
                            pScalarExpr.ColumnName = sse.ColumnName.Value;
                        }

                        return pScalarExpr;
                    }
                case "SelectStarExpression":
                    {
                        var sse = sel as SelectStarExpression;
                        return new WSelectStarExpression()
                        {
                            FirstTokenIndex = sse.FirstTokenIndex,
                            LastTokenIndex = sse.LastTokenIndex,
                            Qulifier = ParseMultiPartIdentifier(sse.Qualifier)
                        };
                    }
                case "SelectSetVariable":
                    {
                        var ssv = sel as SelectSetVariable;
                        return new WSelectSetVariable
                        {
                            VariableName = ssv.Variable.Name,
                            Expression = ParseScalarExpression(ssv.Expression),
                            AssignmentType = ssv.AssignmentKind,
                            FirstTokenIndex = ssv.FirstTokenIndex,
                            LastTokenIndex = ssv.LastTokenIndex
                        };
                    }
                default:
                    {
                        return null;
                    }
            }
        }
Ejemplo n.º 2
0
 public virtual void Visit(WSelectScalarExpression node)
 {
     node.AcceptChildren(this);
 }
        public override void Visit(WSelectQueryBlock node)
        {
            if (node.SelectElements == null || node.SelectElements.Count < 2)
            {
                throw new GraphViewException("Numbers of select elements mismatch.");
            }
            var sourceTableScalar = node.SelectElements[0] as WSelectScalarExpression;
            if (sourceTableScalar == null)
                throw new GraphViewException("Source node id should be a scalar expression.");
            var sourceTableColumn = sourceTableScalar.SelectExpr as WColumnReferenceExpression;
            if (sourceTableColumn == null)
                throw new GraphViewException("Source node id column should be a column reference expression.");
            var sourceTableName = sourceTableColumn.MultiPartIdentifier.Identifiers.Last().Value;

            var sourceNodeIdExpr = new WColumnReferenceExpression();
            foreach (var identifier in sourceTableColumn.MultiPartIdentifier.Identifiers)
                sourceNodeIdExpr.Add(identifier);
            sourceNodeIdExpr.AddIdentifier("GlobalNodeId");

            if (node.SelectElements.Count < 2)
                throw new GraphViewException("Source and Sink tables should be specified in select elements.");

            if (node.GroupByClause != null)
            {
                throw new GraphViewException("GROUP BY clause is not allowed in INSERT EDGE statement.");
            }
            var collectVarVisitor = new CollectVariableVisitor();
            var context = collectVarVisitor.Invoke(node);
            WColumnReferenceExpression sinkNodeIdExpr = null;

            for (var index = 1; index < node.SelectElements.Count; ++index)
            {
                var element = node.SelectElements[index] as WSelectScalarExpression;
                if (element == null)
                    throw new GraphViewException("Edge property should be a scalar expression.");
                //sink table
                if (index == 1)
                {
                    var sinkTableColumn = element.SelectExpr as WColumnReferenceExpression;
                    if (sinkTableColumn == null)
                        throw new GraphViewException("Sink node id column should be a column reference expression.");

                    var sinkTableName = sinkTableColumn.MultiPartIdentifier.Identifiers.Last().Value;
                    _sinkTable = context[sinkTableName];

                    sinkNodeIdExpr = new WColumnReferenceExpression();
                    foreach (var identifier in sinkTableColumn.MultiPartIdentifier.Identifiers)
                        sinkNodeIdExpr.Add(identifier);
                    sinkNodeIdExpr.AddIdentifier("GlobalNodeId");
                }
                else
                {
                    _edgeProperties.Add(element.SelectExpr);
                }

            }

            var sourceTable = context[sourceTableName] as WNamedTableReference;

            if (sourceTable == null)
            {
                throw new GraphViewException("Source table of INSERT EDGE statement should be a named table reference.");
            }


            var sourceNodeId = new WSelectScalarExpression
            {
                SelectExpr = sourceNodeIdExpr,
                ColumnName = "src",
            };
            var sinkNodeId = new WSelectScalarExpression
            {
                SelectExpr = sinkNodeIdExpr,
                ColumnName = "sink"
            };


            var elements = new List<WSelectElement>
            {
                sourceNodeId,
                sinkNodeId
            };

            var result = new WCommonTableExpression
            {
                ExpressionName = new Identifier {Value = _tempTableName},
                QueryExpression = new WSelectQueryBlock
                {
                    FromClause = node.FromClause,
                    WhereClause = new WWhereClause
                    {
                        SearchCondition = node.WhereClause.SearchCondition
                    },
                    HavingClause = node.HavingClause,
                    OrderByClause = node.OrderByClause,
                    TopRowFilter = node.TopRowFilter,
                    UniqueRowFilter = node.UniqueRowFilter,
                    SelectElements = elements,
                    MatchClause = node.MatchClause
                }
            };
            

            _result = result;
        }
        private WCommonTableExpression ConstructDeleteEdgeSelect(WSelectQueryBlock node, string edgeAlias, string tempTableName
            ,out WTableReference sinkTable, out WTableReference sourceTable)
        {
            sourceTable = null;
            sinkTable = null;
            var sourceTableScalar = node.SelectElements[0] as WSelectScalarExpression;
            if (sourceTableScalar == null)
                return null;
            var sourceTableColumn = sourceTableScalar.SelectExpr as WColumnReferenceExpression;
            if (sourceTableColumn == null)
                return null;
            var sourceTableName = sourceTableColumn.MultiPartIdentifier.Identifiers.Last().Value;

            var sourceNodeIdExpr = new WColumnReferenceExpression();
            foreach (var identifier in sourceTableColumn.MultiPartIdentifier.Identifiers)
                sourceNodeIdExpr.Add(identifier);
            sourceNodeIdExpr.AddIdentifier("GlobalNodeId");

            var collectVarVisitor = new CollectVariableVisitor();
            var context = collectVarVisitor.Invoke(node);
            if (!context.NodeTableDictionary.Any())
            {
                throw new GraphViewException("Missing From Clause in Delete Edge statement");
            }
            WColumnReferenceExpression sinkNodeIdExpr = null;
            sourceTable = context[sourceTableName];

            var groupByParams = new List<WScalarExpression>();
            for (var index = 1; index < node.SelectElements.Count; ++index)
            {
                var element = node.SelectElements[index] as WSelectScalarExpression;
                if (element == null)
                    return null;
                //sink table
                if (index == 1)
                {
                    var sinkTableColumn = element.SelectExpr as WColumnReferenceExpression;
                    if (sinkTableColumn == null)
                        return null;

                    var sinkTableName = sinkTableColumn.MultiPartIdentifier.Identifiers.Last().Value;
                    sinkTable = context[sinkTableName];

                    sinkNodeIdExpr = new WColumnReferenceExpression();
                    foreach (var identifier in sinkTableColumn.MultiPartIdentifier.Identifiers)
                        sinkNodeIdExpr.Add(identifier);
                    sinkNodeIdExpr.AddIdentifier("GlobalNodeId");
                }
            }

            var sourceNodeId = new WSelectScalarExpression
            {
                SelectExpr = sourceNodeIdExpr,
                ColumnName = "src",
            };
            var sinkNodeId = new WSelectScalarExpression
            {
                SelectExpr = sinkNodeIdExpr,
                ColumnName = "sink"
            };
            var edgeId = new WSelectScalarExpression
            {
                SelectExpr = new WColumnReferenceExpression
                {
                    MultiPartIdentifier = new WMultiPartIdentifier(
                        new Identifier[]
                        {
                            new Identifier {Value = edgeAlias},
                            new Identifier {Value = "Edgeid"}
                        }
                        )
                },
                ColumnName = "edgeid"
            };

            var elements = new List<WSelectElement>
            {
                sourceNodeId,
                sinkNodeId,
                edgeId
            };

            return new WCommonTableExpression
            {
                ExpressionName = new Identifier { Value = tempTableName },
                QueryExpression = new WSelectQueryBlock
                {
                    FromClause = node.FromClause,
                    WhereClause = new WWhereClause
                    {
                        SearchCondition = node.WhereClause.SearchCondition
                    },
                    HavingClause = node.HavingClause,
                    OrderByClause = node.OrderByClause,
                    TopRowFilter = node.TopRowFilter,
                    UniqueRowFilter = node.UniqueRowFilter,
                    SelectElements = elements,
                    MatchClause = node.MatchClause,
                }

            };
        }
Ejemplo n.º 5
0
 public virtual void Visit(WSelectScalarExpression node)
 {
     node.AcceptChildren(this);
 }
        private WMultiCommonTableExpression ConstructDeleteEdgeSelect(WSelectQueryBlock node, WEdgeColumnReferenceExpression edgeCol, string tempTableName
            ,out WTableReference sinkTable, out WTableReference sourceTable, ref bool hasReversedEdge)
        {
            sourceTable = null;
            sinkTable = null;
            string sourceTableName = null;
            string sinkTableName = null;
            var sourceTableScalar = node.SelectElements[0] as WSelectScalarExpression;
            if (sourceTableScalar == null)
                return null;
            var sourceTableColumn = sourceTableScalar.SelectExpr as WColumnReferenceExpression;
            if (sourceTableColumn == null)
                return null;
            sourceTableName = sourceTableColumn.MultiPartIdentifier.Identifiers.Last().Value;

            var sourceNodeIdExpr = new WColumnReferenceExpression();
            foreach (var identifier in sourceTableColumn.MultiPartIdentifier.Identifiers)
                sourceNodeIdExpr.Add(identifier);
            sourceNodeIdExpr.AddIdentifier("GlobalNodeId");

            var collectVarVisitor = new CollectVariableVisitor();
            var context = collectVarVisitor.Invoke(node);
            if (!context.NodeTableDictionary.Any())
            {
                throw new GraphViewException("Missing From Clause in Delete Edge statement");
            }
            WColumnReferenceExpression sinkNodeIdExpr = null;
            sourceTable = context[sourceTableName];

            var groupByParams = new List<WScalarExpression>();
            for (var index = 1; index < node.SelectElements.Count; ++index)
            {
                var element = node.SelectElements[index] as WSelectScalarExpression;
                if (element == null)
                    return null;
                //sink table
                if (index == 1)
                {
                    var sinkTableColumn = element.SelectExpr as WColumnReferenceExpression;
                    if (sinkTableColumn == null)
                        return null;

                    sinkTableName = sinkTableColumn.MultiPartIdentifier.Identifiers.Last().Value;
                    sinkTable = context[sinkTableName];

                    sinkNodeIdExpr = new WColumnReferenceExpression();
                    foreach (var identifier in sinkTableColumn.MultiPartIdentifier.Identifiers)
                        sinkNodeIdExpr.Add(identifier);
                    sinkNodeIdExpr.AddIdentifier("GlobalNodeId");
                }
            }

            var sourceNodeId = new WSelectScalarExpression
            {
                SelectExpr = sourceNodeIdExpr,
                ColumnName = "src",
            };
            var sinkNodeId = new WSelectScalarExpression
            {
                SelectExpr = sinkNodeIdExpr,
                ColumnName = "sink"
            };
            var edgeId = new WSelectScalarExpression
            {
                SelectExpr = new WColumnReferenceExpression
                {
                    MultiPartIdentifier = new WMultiPartIdentifier(
                        new Identifier[]
                        {
                            new Identifier {Value = edgeCol.Alias??string.Format("{0}_{1}_{2}",sourceTableName,edgeCol.MultiPartIdentifier.Identifiers.Last().Value,sinkTableName)},
                            new Identifier {Value = "Edgeid"}
                        })
                },
                ColumnName = "edgeid"
            };

            var sourceTableNameRef = sourceTable as WNamedTableReference;
            if (sourceTableNameRef == null)
                throw new GraphViewException("Source table of DELETE EDGE statement should be a named table reference.");
            var sinkTableNameRef = sinkTable as WNamedTableReference;
            if (sinkTableNameRef == null)
                throw new GraphViewException("Sink table of DELETE EDGE statement should be a named table reference.");
            int compare = string.CompareOrdinal(sourceTableNameRef.TableObjectName.ToString(), sinkTableNameRef.TableObjectName.ToString());

            using (var command = Tx.Connection.CreateCommand())
            {
                command.Transaction = Tx;
                command.Parameters.AddWithValue("@schema", WNamedTableReference.SchemaNameToTuple(sourceTableNameRef.TableObjectName).Item1);
                command.Parameters.AddWithValue("@tableName", sourceTableNameRef.TableObjectName.Identifiers.Last().Value);
                command.Parameters.AddWithValue("@colName", edgeCol.MultiPartIdentifier.Identifiers.Last().Value);
                command.Parameters.AddWithValue("@role", WNodeTableColumnRole.Edge);
                command.CommandText = string.Format(@"
                    SELECT NodeColumn.HasReversedEdge
                    FROM [{0}] AS NodeColumn
                    WHERE NodeColumn.TableSchema = @schema and
                          NodeColumn.TableName = @tableName and
                          NodeColumn.ColumnName = @colName and
                          NodeColumn.ColumnRole = @role",
                    GraphViewConnection.MetadataTables[1]);
                using (var reader = command.ExecuteReader())
                {
                    if (reader.Read())
                    {
                        hasReversedEdge = bool.Parse(reader[0].ToString());
                    }
                }
            }

            var reversedEdgeName = sourceTableNameRef.TableObjectName.Identifiers.Last().Value +
                                    "_" + edgeCol.MultiPartIdentifier.Identifiers.Last().Value + "Reversed";
            var reversedEdgeId = new WSelectScalarExpression
            {
                SelectExpr = new WColumnReferenceExpression
                {
                    MultiPartIdentifier = new WMultiPartIdentifier(
                        new Identifier[]
                        {
                            new Identifier {Value = edgeCol.Alias??string.Format("{0}_{1}_{2}",sourceTableName,edgeCol.MultiPartIdentifier.Identifiers.Last().Value,sinkTableName)},
                            new Identifier {Value = "Edgeid"}
                        })
                },
                ColumnName = "edgeid"
            };

            var elements = new List<WSelectElement>
            {
                sourceNodeId,
                sinkNodeId,
                edgeId
            };

            var reversedElements = new List<WSelectElement>
            {
                sourceNodeId,
                sinkNodeId,
                reversedEdgeId,
            };

            return new WMultiCommonTableExpression
            {
                WCommonTableExpressions = new List<WCommonTableExpression>()
                {
                    new WCommonTableExpression
                    {
                        ExpressionName = new Identifier
                        {
                            Value = hasReversedEdge && compare == 0 ? tempTableName + "_1" : tempTableName
                        },
                        QueryExpression = new WSelectQueryBlock
                        {
                            FromClause = node.FromClause,
                            WhereClause = new WWhereClause
                            {
                                SearchCondition = node.WhereClause.SearchCondition
                            },
                            HavingClause = node.HavingClause,
                            OrderByClause = node.OrderByClause,
                            TopRowFilter = node.TopRowFilter,
                            UniqueRowFilter = node.UniqueRowFilter,
                            SelectElements = elements,
                            MatchClause = node.MatchClause,
                        }
                    },
                    new WCommonTableExpression
                    {
                        ExpressionName = new Identifier
                        {
                            Value = hasReversedEdge && compare == 0 ? tempTableName + "_2" : tempTableName
                        },
                        QueryExpression = new WSelectQueryBlock
                        {
                            FromClause = node.FromClause,
                            WhereClause = hasReversedEdge ?
                                new WWhereClause { SearchCondition = ObjectExtensions.Copy(node.WhereClause.SearchCondition), }
                                : node.WhereClause,
                            HavingClause = node.HavingClause,
                            OrderByClause = node.OrderByClause,
                            TopRowFilter = node.TopRowFilter,
                            UniqueRowFilter = node.UniqueRowFilter,
                            SelectElements = hasReversedEdge ? reversedElements : elements,
                            MatchClause = hasReversedEdge? ConstructReversedMatchClause(node, context) : node.MatchClause,
                        }
                    },
                }
            };
        }