Пример #1
0
        private static void DispatchInsertReplace(RouteResultsetNode[] rn,
                                                  DmlInsertReplaceStatement stmt,
                                                  IList <string> ruleColumns,
                                                  IDictionary <int, IList <object[]> > dataNodeMap,
                                                  TableConfig matchedTable,
                                                  string originalSql,
                                                  PartitionKeyVisitor visitor)
        {
            if (stmt.Select != null)
            {
                DispatchWhereBasedStmt(rn, stmt, ruleColumns, dataNodeMap, matchedTable, originalSql, visitor);
                return;
            }

            var colsIndex = visitor.GetColumnIndex(stmt.Table.IdTextUpUnescape);

            if (colsIndex == null || colsIndex.IsEmpty())
            {
                throw new ArgumentException("columns index is empty: " + originalSql);
            }

            var colsIndexList = new List <ColumnValueType>(ruleColumns.Count);

            for (int i = 0, len = ruleColumns.Count; i < len; ++i)
            {
                colsIndexList.Add(colsIndex[ruleColumns[i]]);
            }

            var dataNodeId = -1;

            foreach (var en in dataNodeMap)
            {
                var tuples         = en.Value;
                var replaceRowList = new HashSet <RowExpression>();
                foreach (var tuple in tuples)
                {
                    ICollection <Pair <IExpression, IAstNode> > tupleExprs = null;
                    for (var i1 = 0; i1 < tuple.Length; ++i1)
                    {
                        var valueMap = colsIndexList[i1];
                        var value    = tuple[i1];
                        var set      = GetExpressionSet(valueMap, value);
                        tupleExprs = CollectionUtil.IntersectSet(tupleExprs, set);
                    }

                    if (tupleExprs == null || tupleExprs.IsEmpty())
                    {
                        throw new ArgumentException(
                                  string.Format("route: empty expression list for insertReplace stmt: {0}", originalSql));
                    }

                    foreach (var p in tupleExprs)
                    {
                        if (p.Value == stmt && p.Key is RowExpression)
                        {
                            replaceRowList.Add((RowExpression)p.Key);
                        }
                    }
                }

                stmt.ReplaceRowList = new List <RowExpression>(replaceRowList);
                var sql = GenSql(stmt, originalSql);
                stmt.ClearReplaceRowList();

                var dataNodeName = matchedTable.DataNodes[en.Key];
                rn[++dataNodeId] = new RouteResultsetNode(dataNodeName, sql);
            }
        }
Пример #2
0
        private static void DispatchWhereBasedStmt(RouteResultsetNode[] rn,
                                                   ISqlStatement stmtAST,
                                                   IList <string> ruleColumns,
                                                   IDictionary <int, IList <object[]> > dataNodeMap,
                                                   TableConfig matchedTable,
                                                   string originalSQL,
                                                   PartitionKeyVisitor visitor)
        {
            // [perf tag] 11.617 us: sharding multivalue
            if (ruleColumns.Count > 1)
            {
                string sql;
                if (visitor.IsSchemaTrimmed())
                {
                    sql = GenSql(stmtAST, originalSQL);
                }
                else
                {
                    sql = originalSQL;
                }

                var i = -1;
                foreach (var dataNodeId in dataNodeMap.Keys)
                {
                    var dataNode = matchedTable.DataNodes[dataNodeId];
                    rn[++i] = new RouteResultsetNode(dataNode, sql);
                }
                return;
            }

            var table       = matchedTable.Name;
            var columnIndex = visitor.GetColumnIndex(table);
            var valueMap    = columnIndex.GetValue(ruleColumns[0]);

            ReplacePartitionKeyOperand(columnIndex, ruleColumns);
            var unreplacedInExpr      = new Dictionary <InExpression, ICollection <IExpression> >(1);
            var unreplacedSingleExprs = new HashSet <IReplacableExpression>();
            // [perf tag] 12.2755 us: sharding multivalue
            var nodeId = -1;

            foreach (var en in dataNodeMap)
            {
                var tuples = en.Value;
                unreplacedSingleExprs.Clear();
                unreplacedInExpr.Clear();

                foreach (var tuple in tuples)
                {
                    var value = tuple[0];
                    var indexedExpressionPair = GetExpressionSet(valueMap, value);
                    foreach (var pair in indexedExpressionPair)
                    {
                        var expr   = pair.Key;
                        var parent = (InExpression)pair.Value;
                        if (PartitionKeyVisitor.IsPartitionKeyOperandSingle(expr, parent))
                        {
                            unreplacedSingleExprs.Add((IReplacableExpression)expr);
                        }
                        else if (PartitionKeyVisitor.IsPartitionKeyOperandIn(expr, parent))
                        {
                            var newInSet = unreplacedInExpr.GetValue(parent);
                            if (newInSet == null)
                            {
                                newInSet = new HashSet <IExpression>();
                                unreplacedInExpr[parent] = newInSet;
                            }
                            newInSet.Add(expr);
                        }
                    }
                }
                // [perf tag] 15.3745 us: sharding multivalue
                foreach (var expr1 in unreplacedSingleExprs)
                {
                    expr1.ClearReplaceExpr();
                }

                foreach (var entemp in unreplacedInExpr)
                {
                    var @in = entemp.Key;
                    var set = entemp.Value;
                    if (set == null || set.IsEmpty())
                    {
                        @in.ReplaceExpr = ReplacableExpressionConstants.BoolFalse;
                    }
                    else
                    {
                        @in.ClearReplaceExpr();
                        var inlist = @in.GetInExpressionList();
                        if (inlist != null)
                        {
                            inlist.ReplaceExpr = new List <IExpression>(set);
                        }
                    }
                }

                // [perf tag] 16.506 us: sharding multivalue
                var sql = GenSql(stmtAST, originalSQL);
                // [perf tag] 21.3425 us: sharding multivalue
                var dataNodeName = matchedTable.DataNodes[en.Key];
                rn[++nodeId] = new RouteResultsetNode(dataNodeName, sql);
                foreach (var expr2 in unreplacedSingleExprs)
                {
                    expr2.ReplaceExpr = ReplacableExpressionConstants.BoolFalse;
                }

                foreach (var in1 in unreplacedInExpr.Keys)
                {
                    in1.ReplaceExpr = ReplacableExpressionConstants.BoolFalse;
                    var list = in1.GetInExpressionList();
                    if (list != null)
                    {
                        list.ClearReplaceExpr();
                    }
                }
            }
        }