dotnet / dotnet/efcore

Support ExecuteUpdate when the value selector is a collection

Open
#32,494 1 comment 0 reactions 0 assignees View on GitHub
area-bulkupdate area-primitive-collections customer-reported
Dominant language
C#
Stars
14.8k
Forks
3.4k
PR merge metrics
PR metrics pending

Description

The following query fails:

```c#
await db.Test
.ExecuteUpdateAsync(c => c.SetProperty(x => x.TextParts, x => x.TextParts.Concat(arr)));
```

The 1st reason for the failure is #32493; this can be worked around by extracting the lambda to a preceding Select:

```c#
await ctx.Blogs
.Select(b => new { Blog = b, NewTextParts = b.TextParts.Concat(arr) })
.ExecuteUpdateAsync(c => c.SetProperty(x => x.Blog.TextParts, x => x.NewTextParts));
```

At this point we run against other failures:

1. If the type of the property being set (Blog.TextParts) and the type coming out of the value lambda is different, we attempt to apply a Convert node ([code](https://github.com/dotnet/efcore/blob/main/src/EFCore.Relational/Query/RelationalQueryableMethodTranslatingExpressionVisitor.cs#L1512)) which can fail (e.g. array property, List coming out of the selector - at least in PG).
2. More importantly, the expression translated for NewTextParts in the anonymous object above is a CollectionResultExpression - this is what Select() returns when the thing being selected is an enumerable. We then attempt to (re-)translate that and fail.
* We should be able to make this work.
* But more generally, this raises the question of why we attempt to translate twice - once when translating the Select, and another time when translating the ExecuteUpdate's value selector lambda, into which we remap the lambda parameter (inserting a CollectionResultExpression into the lambda).
* This can be another argument against out general remapping approach. Instead of doing a pre-pass the remap the lambda parameter, and then having to skip re-translating the thing we remapped, if SQL translator simply encountered a parameter it could process it accordingly.

Originally raised by @srasch in https://github.com/npgsql/efcore.pg/issues/3001

Contributor guide

Open the contributing guide

Assessment

This issue has not been assessed yet.

Get new issues in your inbox

A short digest of beginner-friendly GitHub issues.