Skip to content

Commit eb5e356

Browse files
authored
Merge pull request #32 from servicetitan/sqlxxx-improvements
Set of improvements of Sql translation subsystem
2 parents cf9b153 + 9cba5d1 commit eb5e356

File tree

14 files changed

+341
-197
lines changed

14 files changed

+341
-197
lines changed

Orm/Xtensive.Orm/Orm/Providers/Expressions/ExpressionProcessor.cs

Lines changed: 4 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -28,13 +28,13 @@ internal sealed partial class ExpressionProcessor : ExpressionVisitor<SqlExpress
2828
private readonly StorageDriver driver;
2929
private readonly BooleanExpressionConverter booleanExpressionConverter;
3030
private readonly IMemberCompilerProvider<SqlExpression> memberCompilerProvider;
31-
private readonly List<SqlExpression>[] sourceColumns;
31+
private readonly IReadOnlyList<SqlExpression>[] sourceColumns;
3232
private readonly ExpressionEvaluator evaluator;
3333
private readonly ParameterExtractor parameterExtractor;
3434
private readonly LambdaExpression lambda;
3535
private readonly HashSet<QueryParameterBinding> bindings;
3636
private readonly List<ParameterExpression> activeParameters;
37-
private readonly Dictionary<ParameterExpression, List<SqlExpression>> sourceMapping;
37+
private readonly Dictionary<ParameterExpression, IReadOnlyList<SqlExpression>> sourceMapping;
3838
private readonly SqlCompiler compiler;
3939

4040
private readonly Dictionary<QueryParameterIdentity, QueryParameterBinding> bindingsWithIdentity
@@ -448,7 +448,7 @@ private SqlExpression TryUnwrapEnum(SqlContainer container)
448448
// Constructors
449449

450450
public ExpressionProcessor(
451-
LambdaExpression lambda, HandlerAccessor handlers, SqlCompiler compiler, params List<SqlExpression>[] sourceColumns)
451+
LambdaExpression lambda, HandlerAccessor handlers, SqlCompiler compiler, params IReadOnlyList<SqlExpression>[] sourceColumns)
452452
{
453453
ArgumentValidator.EnsureArgumentNotNull(lambda, "lambda");
454454
ArgumentValidator.EnsureArgumentNotNull(handlers, "handlers");
@@ -478,7 +478,7 @@ public ExpressionProcessor(
478478
throw Exceptions.InternalError(Strings.ExParametersCountIsNotSameAsSourceColumnListsCount, OrmLog.Instance);
479479
if (sourceColumns.Any(list => list.Any(c => c.IsNullReference())))
480480
throw Exceptions.InternalError(Strings.ExSourceColumnListContainsNullValues, OrmLog.Instance);
481-
sourceMapping = new Dictionary<ParameterExpression, List<SqlExpression>>();
481+
sourceMapping = new Dictionary<ParameterExpression, IReadOnlyList<SqlExpression>>();
482482
}
483483
}
484484
}

Orm/Xtensive.Orm/Orm/Providers/SqlCompiler.Apply.cs

Lines changed: 7 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -92,10 +92,11 @@ private SqlSelect ProcessApplyViaSubqueries(ApplyProvider provider, SqlProvider
9292
if (shouldUseQueryReference) {
9393
var leftTable = left.PermanentReference;
9494
query = SqlDml.Select(leftTable);
95-
query.Columns.AddRange(leftTable.Columns.Cast<SqlColumn>());
95+
query.Columns.AddRange(leftTable.Columns);
9696
}
97-
else
97+
else {
9898
query = left.Request.Statement.ShallowClone();
99+
}
99100

100101
var isApplyExistence =
101102
provider.Right.Type==ProviderType.Existence ||
@@ -166,15 +167,15 @@ private SqlSelect ProcessApplyViaCrossApply(ApplyProvider provider, SqlProvider
166167
? left.PermanentReference
167168
: left.Request.Statement.From;
168169
var leftColumns = leftShouldUseReference
169-
? leftTable.Columns.Cast<SqlColumn>()
170+
? (IReadOnlyList<SqlColumn>) leftTable.Columns
170171
: left.Request.Statement.Columns;
171172

172173
var rightShouldUseReference = ShouldUseQueryReference(provider, right);
173174
var rightTable = rightShouldUseReference
174175
? right.PermanentReference
175176
: right.Request.Statement.From;
176177
var rightColumns = rightShouldUseReference
177-
? rightTable.Columns.Cast<SqlColumn>()
178+
? (IReadOnlyList<SqlColumn>) rightTable.Columns
178179
: right.Request.Statement.Columns;
179180

180181
var joinType = provider.ApplyType==JoinType.LeftOuter
@@ -185,8 +186,8 @@ private SqlSelect ProcessApplyViaCrossApply(ApplyProvider provider, SqlProvider
185186
joinType,
186187
leftTable,
187188
rightTable,
188-
leftColumns.ToList(),
189-
rightColumns.ToList());
189+
leftColumns,
190+
rightColumns);
190191

191192
var query = SqlDml.Select(joinedTable);
192193
if (!leftShouldUseReference)

Orm/Xtensive.Orm/Orm/Providers/SqlCompiler.Helpers.cs

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -67,7 +67,7 @@ protected virtual string ProcessAliasedName(string name)
6767
}
6868

6969
protected Pair<SqlExpression, IEnumerable<QueryParameterBinding>> ProcessExpression(LambdaExpression le,
70-
params List<SqlExpression>[] sourceColumns)
70+
params IReadOnlyList<SqlExpression>[] sourceColumns)
7171
{
7272
var processor = new ExpressionProcessor(le, Handlers, this, sourceColumns);
7373
var result = new Pair<SqlExpression, IEnumerable<QueryParameterBinding>>(
@@ -81,7 +81,7 @@ protected static SqlSelect ExtractSqlSelect(CompilableProvider origin, SqlProvid
8181
if (ShouldUseQueryReference(origin, compiledSource)) {
8282
var queryRef = compiledSource.PermanentReference;
8383
var query = SqlDml.Select(queryRef);
84-
query.Columns.AddRange(queryRef.Columns.Cast<SqlColumn>());
84+
query.Columns.AddRange(queryRef.Columns);
8585
return query;
8686
}
8787
return sourceSelect.ShallowClone();

Orm/Xtensive.Orm/Orm/Providers/SqlCompiler.Index.cs

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -94,7 +94,7 @@ private SqlSelect BuildUnionQuery(IndexInfo index)
9494

9595
var unionRef = SqlDml.QueryRef(result);
9696
var query = SqlDml.Select(unionRef);
97-
query.Columns.AddRange(unionRef.Columns.Cast<SqlColumn>());
97+
query.Columns.AddRange(unionRef.Columns);
9898
return query;
9999
}
100100

Orm/Xtensive.Orm/Orm/Providers/SqlCompiler.Paging.cs

Lines changed: 3 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -88,7 +88,7 @@ private SqlProvider VisitSkipRowNumber(SkipProvider provider)
8888
var source = compiledSource.Request.Statement;
8989
var queryRef = SqlDml.QueryRef(source);
9090
var query = SqlDml.Select(queryRef);
91-
query.Columns.AddRange(queryRef.Columns.Cast<SqlColumn>());
91+
query.Columns.AddRange(queryRef.Columns);
9292
query.Where = queryRef.Columns.Last() > skipParameterBinding.ParameterReference;
9393
return CreateProvider(query, bindings, provider, compiledSource);
9494
}
@@ -101,7 +101,7 @@ private SqlProvider VisitTakeRowNumber(TakeProvider provider)
101101
var source = compiledSource.Request.Statement;
102102
var queryRef = SqlDml.QueryRef(source);
103103
var query = SqlDml.Select(queryRef);
104-
query.Columns.AddRange(queryRef.Columns.Cast<SqlColumn>());
104+
query.Columns.AddRange(queryRef.Columns);
105105
query.Where = queryRef.Columns.Last() <= takeParameterBinding.ParameterReference;
106106
return CreateProvider(query, bindings, provider, compiledSource);
107107
}
@@ -116,7 +116,7 @@ private SqlProvider VisitPagingRowNumber(PagingProvider provider)
116116
var queryRef = SqlDml.QueryRef(source);
117117
var query = SqlDml.Select(queryRef);
118118
var rowNumberColumn = queryRef.Columns.Last();
119-
query.Columns.AddRange(queryRef.Columns.Cast<SqlColumn>());
119+
query.Columns.AddRange(queryRef.Columns);
120120
query.Where = SqlDml.Between(rowNumberColumn,
121121
fromParameterBinding.ParameterReference,
122122
toParameterBinding.ParameterReference);

Orm/Xtensive.Orm/Orm/Providers/SqlCompiler.cs

Lines changed: 30 additions & 20 deletions
Original file line numberDiff line numberDiff line change
@@ -129,10 +129,12 @@ protected override SqlProvider VisitDistinct(DistinctProvider provider)
129129
if (!sourceSelect.Limit.IsNullReference() || !sourceSelect.Offset.IsNullReference()) {
130130
var queryRef = SqlDml.QueryRef(sourceSelect);
131131
query = SqlDml.Select(queryRef);
132-
query.Columns.AddRange(queryRef.Columns.Cast<SqlColumn>());
132+
query.Columns.AddRange(queryRef.Columns);
133133
}
134-
else
134+
else {
135135
query = sourceSelect.ShallowClone();
136+
}
137+
136138
query.Distinct = true;
137139
return CreateProvider(query, provider, source);
138140
}
@@ -173,7 +175,7 @@ protected override SqlProvider VisitJoin(JoinProvider provider)
173175
? left.PermanentReference
174176
: left.Request.Statement.From;
175177
var leftColumns = leftShouldUseReference
176-
? leftTable.Columns.Cast<SqlColumn>()
178+
? (IReadOnlyList<SqlColumn>) leftTable.Columns
177179
: left.Request.Statement.Columns;
178180
var leftExpressions = leftShouldUseReference
179181
? leftTable.Columns.Cast<SqlExpression>().ToList()
@@ -184,7 +186,7 @@ protected override SqlProvider VisitJoin(JoinProvider provider)
184186
? right.PermanentReference
185187
: right.Request.Statement.From;
186188
var rightColumns = rightShouldUseReference
187-
? rightTable.Columns.Cast<SqlColumn>()
189+
? (IReadOnlyList<SqlColumn>) rightTable.Columns
188190
: right.Request.Statement.Columns;
189191
var rightExpressions = rightShouldUseReference
190192
? rightTable.Columns.Cast<SqlExpression>().ToList()
@@ -205,8 +207,8 @@ protected override SqlProvider VisitJoin(JoinProvider provider)
205207
joinType,
206208
leftTable,
207209
rightTable,
208-
leftColumns.ToList(),
209-
rightColumns.ToList(),
210+
leftColumns,
211+
rightColumns,
210212
joinExpression);
211213

212214
var query = SqlDml.Select(joinedTable);
@@ -229,21 +231,21 @@ protected override SqlProvider VisitPredicateJoin(PredicateJoinProvider provider
229231
? left.PermanentReference
230232
: left.Request.Statement.From;
231233
var leftColumns = leftShouldUseReference
232-
? leftTable.Columns.Cast<SqlColumn>()
234+
? (IReadOnlyList<SqlColumn>) leftTable.Columns
233235
: left.Request.Statement.Columns;
234236
var leftExpressions = leftShouldUseReference
235-
? leftTable.Columns.Cast<SqlExpression>().ToList()
237+
? (IReadOnlyList<SqlExpression>) leftTable.Columns
236238
: ExtractColumnExpressions(left.Request.Statement);
237239

238240
var rightShouldUseReference = ShouldUseQueryReference(provider, right);
239241
var rightTable = rightShouldUseReference
240242
? right.PermanentReference
241243
: right.Request.Statement.From;
242244
var rightColumns = rightShouldUseReference
243-
? rightTable.Columns.Cast<SqlColumn>()
245+
? (IReadOnlyList<SqlColumn>) rightTable.Columns
244246
: right.Request.Statement.Columns;
245247
var rightExpressions = rightShouldUseReference
246-
? rightTable.Columns.Cast<SqlExpression>().ToList()
248+
? (IReadOnlyList<SqlExpression>) rightTable.Columns
247249
: ExtractColumnExpressions(right.Request.Statement);
248250

249251

@@ -257,8 +259,8 @@ protected override SqlProvider VisitPredicateJoin(PredicateJoinProvider provider
257259
joinType,
258260
leftTable,
259261
rightTable,
260-
leftColumns.ToList(),
261-
rightColumns.ToList(),
262+
leftColumns,
263+
rightColumns,
262264
joinExpression);
263265

264266
var query = SqlDml.Select(joinedTable);
@@ -308,10 +310,18 @@ protected override SqlProvider VisitSelect(SelectProvider provider)
308310
{
309311
var compiledSource = Compile(provider.Source);
310312

311-
SqlSelect query = ExtractSqlSelect(provider, compiledSource);
312-
var originalColumns = query.Columns.ToList();
313-
query.Columns.Clear();
314-
query.Columns.AddRange(provider.ColumnIndexes.Select(i => originalColumns[i]));
313+
var query = ExtractSqlSelect(provider, compiledSource);
314+
var queryColumns = query.Columns;
315+
var columnIndexes = provider.ColumnIndexes;
316+
317+
var newIndex = 0;
318+
var newColumns = new SqlColumn[columnIndexes.Count];
319+
foreach (var index in columnIndexes) {
320+
newColumns[newIndex++] = queryColumns[index];
321+
}
322+
323+
queryColumns.Clear();
324+
queryColumns.AddRange(newColumns);
315325

316326
return CreateProvider(query, provider, compiledSource);
317327
}
@@ -407,7 +417,7 @@ protected override SqlProvider VisitIntersect(IntersectProvider provider)
407417
var queryRef = SqlDml.QueryRef(result);
408418

409419
SqlSelect query = SqlDml.Select(queryRef);
410-
query.Columns.AddRange(queryRef.Columns.Cast<SqlColumn>());
420+
query.Columns.AddRange(queryRef.Columns);
411421

412422
return CreateProvider(query, provider, left, right);
413423
}
@@ -431,7 +441,7 @@ protected override SqlProvider VisitExcept(ExceptProvider provider)
431441
var result = SqlDml.Except(leftSelect, rightSelect);
432442
var queryRef = SqlDml.QueryRef(result);
433443
SqlSelect query = SqlDml.Select(queryRef);
434-
query.Columns.AddRange(queryRef.Columns.Cast<SqlColumn>());
444+
query.Columns.AddRange(queryRef.Columns);
435445

436446
return CreateProvider(query, provider, left, right);
437447
}
@@ -455,7 +465,7 @@ protected override SqlProvider VisitConcat(ConcatProvider provider)
455465
var result = SqlDml.UnionAll(leftSelect, rightSelect);
456466
var queryRef = SqlDml.QueryRef(result);
457467
SqlSelect query = SqlDml.Select(queryRef);
458-
query.Columns.AddRange(queryRef.Columns.Cast<SqlColumn>());
468+
query.Columns.AddRange(queryRef.Columns);
459469

460470
return CreateProvider(query, provider, left, right);
461471
}
@@ -479,7 +489,7 @@ protected override SqlProvider VisitUnion(UnionProvider provider)
479489
var result = SqlDml.Union(leftSelect, rightSelect);
480490
var queryRef = SqlDml.QueryRef(result);
481491
SqlSelect query = SqlDml.Select(queryRef);
482-
query.Columns.AddRange(queryRef.Columns.Cast<SqlColumn>());
492+
query.Columns.AddRange(queryRef.Columns);
483493

484494
return CreateProvider(query, provider, left, right);
485495
}

0 commit comments

Comments
 (0)