0

I would like to write a LINQ query using EF Core that would get results from multiple matching columns in a SQL table based on an array of serverside data that I would provide for matching. SQL query should look/do something like this:

SELECT * FROM (VALUES ('a', 'one'), ('b', 'two'), ('c', 'three')) AS myserverdata (TransactionId, OrderId)
join ReportExecution re ON myserverdata.OrderId = re.OrderId AND myserverdata.TransactionId = re.TransactionId

Is this even possible?

I had few attempts where all end up crashing on generaing a SQL from expression:

  1. using join
var query =
    from execution in context.ReportExecutions
    join candidate in insertCandidates // serverside array of data I'd like to match in SQL
        on new {execution.OrderId, execution.TransactionId} equals new{candidate.OrderId, candidate.TransactionId}
        select execution;

return query.ToListAsync();
  1. using Contains and similarly with .Any (this would work for array of strings and then generate WHERE IN (...), but I can't pull it off for matching multiple columns.
var keys = candidates.Select(x => new { x.TransactionId, x.OrderId });
return context.ReportExecutions
    .Where(rme => keys.Contains(new { rme.TransactionId, rme.OrderId } ))
    .ToListAsync();

Thanks for the feedback.

Gert Arnold
  • 105,341
  • 31
  • 202
  • 291
the berserker
  • 1,553
  • 3
  • 22
  • 39
  • Does this answer your question? [Entity framework core add multible where as OR](https://stackoverflow.com/questions/71661316/entity-framework-core-add-multible-where-as-or) – Svyatoslav Danyliv Feb 01 '23 at 20:19
  • Doesn't fit my purpose 1:1, but I see the idea, thanks @SvyatoslavDanyliv . Due to the time pressure I will have to go for partially client-evaluated result set. – the berserker Feb 02 '23 at 10:04

1 Answers1

1

EF Core supports only Contains with local collection, but there is workaround. You can use my function FilterByItems and rewire query in the following way:

var query =
    from execution in context.ReportExecutions
        .FilterByItems(insertCandidates, (e, c) => e.OrderId == c.OrderId && e.TransactionId == c.TransactionId, true)
    select execution;
Svyatoslav Danyliv
  • 21,911
  • 3
  • 16
  • 32
  • Thanks for the proposal @SvyatoslavDanyliv . I will go for the simpler query with Cointains over one attribute and then filter on client. The issue I hit with larger amount of parameters (these could be few hundred) is `Some part of your SQL statement is nested too deeply. Rewrite the query or break it up into smaller queries.` due to the format of the SQL generated. – the berserker Feb 06 '23 at 12:47
  • Yes this function for relative small record count, will never propose this answer for big amount of records. And also EF Core has problem with parenthes. Actually you have no choice - third party extensions which work with temporary tables. – Svyatoslav Danyliv Feb 06 '23 at 12:51