Ho investigato ore per trovare una soluzione o soluzione per il mio problema. Tutto ciò che ho trovato è l'errore "deve essere nodo riducibile" in combinazione con Linq Join o versioni EF precedenti. Quindi devo fare di nuovo questa domanda.
Ambiente attuale:
Il mio codice sorgente per questo errore è:
// this query works...
var projectEfforts = from projectEntry in _context.ProjectTrackingEntry
where projectEntry.ProjectId == projectId
group projectEntry by new { projectEntry.Day.Year, projectEntry.Day.Month } into g
select new
{
PeDate = new DateTime(g.Key.Year, g.Key.Month, 1),
Month = g.Key,
MonthlyWorkingHours = g.Sum(x => x.WorkingHours)
};
// and here the query is executed with a valid result
string jsonprojectEfforts = Newtonsoft.Json.JsonConvert.SerializeObject(projectEfforts);
// following Linq will produce an error
var effHours = from projectEffort in projectEfforts
where (projectEffort.PeDate < fromDate)
select projectEffort.MonthlyWorkingHours;
// work with the result above will cause the 'must be reducible node' error
string jsoneffHours = Newtonsoft.Json.JsonConvert.SerializeObject(effHours);
Per una migliore comprensione ecco il risultato della prima operazione di Linq:
[{"PeDate": "2017-01-01T00: 00: 00", "Month": {"Year": 2017, "Month": 1}, "MonthlyWorkingHours": 128.00}, {"PeDate": "2018 -01-01T00: 00: 00 "," Month ": {" Year ": 2018," Month ": 1}," MonthlyWorkingHours ": 40.00}, {" PeDate ":" 2017-02-01T00: 00: 00 "," Mese ": {" Anno ": 2017," Mese ": 2}," MonthlyWorkingHours ": 80.00}, {" PeDate ":" 2017-03-01T00: 00: 00 "," Mese ": {" Anno ": 2017," Mese ": 3}," MonthlyWorkingHours ": 88.00}, {" PeDate ":" 2018-03-01T00: 00: 00 "," Mese ": {" Anno ": 2018," Mese " : 3}, "MonthlyWorkingHours": 64.00}, {"PeDate": "2017-04-01T00: 00: 00", "Month": {"Year": 2017, "Month": 4}, "MonthlyWorkingHours": 104.00}, {"PeDate": "2018-04-01T00: 00: 00", "Month": {"Year": 2018, "Month": 4}, "MonthlyWorkingHours": 76.00}, {"PeDate": "2017-05-01T00: 00: 00", "Month": {"Year": 2017, "Month": 5}, "MonthlyWorkingHours": 16.00}, {"PeDate": "2018-05-01T00: 00 : 00 "," Month ": {" Year ": 2018," Month ": 5}," MonthlyWorkingHours ": 24.00}, {" PeDate ":" 2017-06-01T00: 00: 00 "," Month ": {"Anno": 2017, "Mese": 6}, "MonthlyWorkingHours": 60.00}, {"PeDate": "2018-06-01T00: 00: 00", "Mese": {"Anno": 2018, " Mon th ": 6}," MonthlyWorkingHours ": 24.00}, {" PeDate ":" 2017-07-01T00: 00: 00 "," Month ": {" Year ": 2017," Month ": 7}," MonthlyWorkingHours ": 48.00}, {" PeDate ":" 2018-07-01T00: 00: 00 "," Month ": {" Year ": 2018," Month ": 7}," MonthlyWorkingHours ": 80.00}, {" PeDate ":" 2017-08-01T00: 00: 00 "," Mese ": {" Anno ": 2017," Mese ": 8}," MonthlyWorkingHours ": 104.00}, {" PeDate ":" 2017-09-01T00 : 00: 00 "," Mese ": {" Anno ": 2017," Mese ": 9}," MonthlyWorkingHours ": 48.00}, {" PeDate ":" 2017-10-01T00: 00: 00 "," Mese ": {" Anno ": 2017," Mese ": 10}," MonthlyWorkingHours ": 72.00}, {" PeDate ":" 2017-12-01T00: 00: 00 "," Mese ": {" Anno ": 2017 , "Mese": 12}, "MonthlyWorkingHours": 213.75}]
E l'errore per la seconda operazione di Linq (effHours) si verifica con il tentativo di serializzare il risultato in JSON (ultima riga di codice nello snippet sopra):
a System.Linq.Expressions.Expression.ReduceAndCheck () a System.Linq.Expressions.Expression.ReduceExtensions () a System.Linq.Expressions.Compiler.StackSpiller.RewriteExtensionExpression (Expression expr, Stack stack) su System.Linq.Expressions. Compiler.StackSpiller.RewriteExpression (nodo Espressione, Stack stack) su System.Linq.Expressions.Compiler.StackSpiller.RewriteMemberExpression (Expression expr, Stack stack) su System.Linq.Expressions.Compiler.StackSpiller.RewriteExpression (nodo Espressione, Stack stack) a System.Linq.Expressions.Compiler.StackSpiller.RewriteMemberExpression (Expression expr, Stack stack) su System.Linq.Expressions.Compiler.StackSpiller.RewriteExpression (nodo Espressione, Stack stack) su System.Linq.Expressions.Compiler.StackSpiller.ChildRewriter .Add (espressione espressione) su System.Linq.Expressions.Compiler.StackSpiller.ChildRewriter.AddArguments (espressioni IArgumentProvider) su System.Linq.Expressions.Compiler.StackSpiller.RewriteNewExpression (Expression expr, S tack stack) su System.Linq.Expressions.Compiler.StackSpiller.RewriteExpression (nodo Espressione, Stack stack) su System.Linq.Expressions.Compiler.StackSpiller.ChildRewriter.Add (espressione espressione) su System.Linq.Expressions.Compiler.StackSpiller .RewriteBinaryExpression (Expression expr, Stack stack) su System.Linq.Expressions.Compiler.StackSpiller.RewriteExpression (nodo Expression, Stack stack) su System.Linq.Expressions.Compiler.StackSpiller.RewriteExpressionFreeTemps (espressione espressione, stack stack) sul sistema. Linq.Expressions.Compiler.StackSpiller.Rewrite [T] (Expression
1 lambda) at System.Linq.Expressions.Expression
1.Accept (StackSpiller spiller) su System.Linq.Expressions.Compiler.StackSpiller.RewriteLambdaExpression (Expression expr) su System .Linq.Expressions.Compiler.StackSpiller.RewriteExpression (nodo Espressione, Stack stack) su System.Linq.Expressions.Compiler.StackSpiller.ChildRewriter.Add (Espressione espressione) su System.Linq.Expressions.Compiler.StackSpiller.ChildRewriter .AddArguments (espressioni IArgumentProvider) su System.Linq.Expressions.Compiler.StackSpiller.RewriteMethodCallExpression (Expression expr, Stack stack) su System.Linq.Expressions.Compiler.StackSpiller.RewriteExpression (nodo Espressione, Stack stack) su System.Linq.Expressions .Compiler.StackSpiller.ChildRewriter.Add (Espressione espressione) su System.Linq.Expressions.Compiler.StackSpiller.ChildRewriter.AddArguments (espressioni IArgumentProvider) su System.Linq.Expressions.Compiler.StackSpiller.RewriteMethodCallExpression (Expression expr, Stack stack) a System.Linq.Expressions.Compiler.StackSpiller.RewriteExpression (Nodo espressione, Stack stack) su System.Linq.Expressions.Compiler.StackSpiller.ChildRewriter.Add (Espressione espressione) su System.Linq.Expressions.Compiler.StackSpiller.ChildRewriter.AddArguments (Espressioni IArgumentProvider) su System.Linq.Expressions.Compiler.StackSpiller.RewriteMethodCallExpression (Expression expr, Stack stack) su System.Linq.Expressions.Compiler.StackSpill er.RewriteExpression (Expression node, Stack stack) su System.Linq.Expressions.Compiler.StackSpiller.RewriteExpressionFreeTemps (espressione di espressione, Stack stack) su System.Linq.Expressions.Compiler.StackSpiller.Rewrite [T] (Expression1 lambda) at System.Linq.Expressions.Expression
(StackSpiller spiller) su System.Linq.Expressions.Compiler.LambdaCompiler.Compile (LambdaExpression lambda) su System.Linq.Expressions.Expression1.Compile(Boolean preferInterpretation) at Microsoft.EntityFrameworkCore.Query.EntityQueryModelVisitor.CreateExecutorLambda[TResults]() at Microsoft.EntityFrameworkCore.Query.EntityQueryModelVisitor.CreateQueryExecutor[TResult](QueryModel queryModel) --- End of stack trace from previous location where exception was thrown --- at System.Runtime.ExceptionServices.ExceptionDispatchInfo.Throw() at Microsoft.EntityFrameworkCore.Query.Internal.QueryCompiler.CompileQueryCore[TResult](Expression query, IQueryModelGenerator queryModelGenerator, IDatabase database, IDiagnosticsLogger
1 logger, Type contextType) in Microsoft.EntityFrameworkCore.Query.Internal.QueryCompiler. <> c__DisplayClass13_01.<Execute>b__0() at Microsoft.EntityFrameworkCore.Query.Internal.CompiledQueryCache.GetOrAddQueryCore[TFunc](Object cacheKey, Func
1 compilatore) in Microsoft.EntityFrameworkCore.Query.Internal.QueryCompiler.Execute [TResult] (query di espressione) in Remotion.Linq.QueryableBase`1.System.Collections.IEnumerable.GetEnumerator () in Newtonsoft.Json.Serialization.JsonSerializerInternalWriter.SerializeList ( JSONWriter writer, IEnumerable values, JsonArrayContract contract, JsonProperty member, JsonContainerContract collectionContract, JsonProperty containerProperty) su Newtonsoft.Json.Serialization.JsonSerializerInternalWriter.Serialize (JsonWriter jsonWriter, Object value, Type objectType) su Newtonsoft.Json.JsonSerializer.SerializeInternal (JsonWriter jsonWriter, Valore dell'oggetto, Tipo oggettoTipo) in Newtonsoft.Json.JsonConvert.SerializeObjectInternal (Valore oggetto, Tipo tipo, J sonSerializer jsonSerializer) su My.api.MyController.MyServiceMethod (Guid projectId, DateTime fromDate, DateTime toDate) in C: \ Sources [...] MyController.cs: riga 347
Perché questo è tutto sotto il cofano, non so come procedere con quel problema. Sono soddisfatto anche di una soluzione o di alcuni suggerimenti.
Qualcuno può aiutarmi?
Il tuo progettoEfforts non è una collezione. È una query e la stai eseguendo due volte. La seconda volta genera un errore.
Quindi la soluzione alternativa è eseguire la query una volta sola e derivare effHours dai risultati invece di renderla una seconda query.
var projectEffortsQuery = from projectEntry in _context.ProjectTrackingEntry
where projectEntry.ProjectId == projectId
group projectEntry by new { projectEntry.Day.Year, projectEntry.Day.Month } into g
select new
{
PeDate = new DateTime(g.Key.Year, g.Key.Month, 1),
Month = g.Key,
MonthlyWorkingHours = g.Sum(x => x.WorkingHours)
};
var projectEfforts = projectEffortsQuery.ToList();