private GeneratedMethod buildDetermineOperationMethod() { var method = _inlineType.MethodFor(nameof(AggregationRuntime <string, string> .DetermineOperation)); // This gets you the EventSlice aggregate Id method.DerivedVariables.Add(new Variable(_aggregateMapping.IdType, $"slice.{nameof(EventSlice<string, string>.Id)}")); method.DerivedVariables.Add(Variable.For <ITenant>($"slice.{nameof(EventSlice<string, string>.Tenant)}")); method.DerivedVariables.Add(Variable.For <ITenant>($"slice.{nameof(EventSlice<string, string>.Tenant)}")); method.DerivedVariables.Add(Variable.For <IEvent>("@event")); method.DerivedVariables.Add(Variable.For <IMartenSession>($"({typeof(IMartenSession).FullNameInCode()})session")); method.DerivedVariables.Add(Variable.For <IQuerySession>("session")); method.DerivedVariables.Add( Variable.For <IAggregateProjection>(nameof(AggregationRuntime <string, string> .Projection))); var createFrame = new CallCreateAggregateFrame(_createMethods); method.Frames.Add(new InitializeLiveAggregateFrame(typeof(T), _aggregateMapping.IdType, createFrame)); method.Frames.Add(new MethodCall(_storageType, "SetIdentity")); var handlers = MethodCollection.AddEventHandling(typeof(T), _aggregateMapping, _applyMethods, _shouldDeleteMethods); var iterate = new ForEachEventFrame((IReadOnlyList <Frame>)handlers); method.Frames.Add(iterate); return(method); }
private void buildInlineAggregationType() { var inlineBaseType = typeof(InlineAggregationBase <,>).MakeGenericType(typeof(T), _aggregateMapping.IdType); _inlineType = _assembly.AddType(GetType().NameInCode().Sanitize() + "InlineHandler", inlineBaseType); _createMethods.BuildCreateMethod(_inlineType, _aggregateMapping); _inlineType.AllInjectedFields.Add(new InjectedField(_storageType)); _inlineType.AllInjectedFields.Add(new InjectedField(GetType())); var method = _inlineType.MethodFor(nameof(InlineAggregationBase <string, string> .DetermineOperation)); // This gets you the EventSlice aggregate Id method.DerivedVariables.Add(Variable.For <Guid>($"slice.{nameof(EventSlice<string, string>.Id)}")); method.DerivedVariables.Add(Variable.For <string>($"slice.{nameof(EventSlice<string, string>.Id)}")); // TODO -- this is hokey. Just pass in ITenant? method.DerivedVariables.Add(Variable.For <ITenant>($"(({typeof(IMartenSession).FullNameInCode()})session).{nameof(IMartenSession.Tenant)}")); method.DerivedVariables.Add(Variable.For <IEvent>("@event")); method.DerivedVariables.Add(Variable.For <IMartenSession>($"({typeof(IMartenSession).FullNameInCode()})session")); method.DerivedVariables.Add(Variable.For <IQuerySession>("session")); method.DerivedVariables.Add(Variable.For <IAggregateProjection>(nameof(InlineAggregationBase <string, string> .Projection))); var sliceType = typeof(EventSlice <,>).MakeGenericType(_aggregateMapping.DocumentType, _aggregateMapping.IdType); if (DeleteEvents.Any()) { method.Frames.Code($"if (Projection.{nameof(MatchesAnyDeleteType)}({{0}})) return {{1}}.{nameof(IDocumentStorage<string, string>.DeleteForId)}({{2}});", new Use(sliceType), new Use(_storageType), new Use(_aggregateMapping.IdType)); } var createFrame = new CallCreateAggregateFrame(_createMethods); method.Frames.Add(new InitializeLiveAggregateFrame(typeof(T), _aggregateMapping.IdType, createFrame)); method.Frames.Add(new MethodCall(_storageType, "SetIdentity")); var handlers = MethodCollection.AddEventHandling(typeof(T), _aggregateMapping, _applyMethods, _shouldDeleteMethods); var iterate = new ForEachEventFrame((IReadOnlyList <Frame>)handlers); method.Frames.Add(iterate); var upsertMethod = typeof(IDocumentStorage <>).MakeGenericType(typeof(T)).GetMethod("Upsert"); var upsert = new MethodCall(_storageType, upsertMethod) { ReturnAction = ReturnAction.Return }; method.Frames.Add(upsert); _inlineType.Setters.AddRange(_applyMethods.Setters()); _inlineType.Setters.AddRange(_createMethods.Setters()); _inlineType.Setters.AddRange(_shouldDeleteMethods.Setters()); }
private void buildDetermineOperationMethodForDaemonRunner(bool daemonBuilderIsAsync) { var methodName = daemonBuilderIsAsync ? "DetermineOperation" : "DetermineOperationSync"; var method = _asyncDaemonType.MethodFor(methodName); if (daemonBuilderIsAsync) { method.AsyncMode = AsyncMode.AsyncTask; } method.DerivedVariables.Add(Variable.For <ITenant>($"fragment.{nameof(StreamFragment<string, string>.Tenant)}")); method.DerivedVariables.Add(Variable.For <IEvent>("@event")); method.DerivedVariables.Add(Variable.For <IQuerySession>($"(({typeof(IQuerySession).FullNameInCode()})session)")); // At most, only one of these would be used method.DerivedVariables.Add(Variable.For <Guid>($"fragment.Id")); method.DerivedVariables.Add(Variable.For <string>($"fragment.Id")); var aggregate = new Variable(typeof(T), $"fragment.{nameof(StreamFragment<string, string>.Aggregate)}"); method.DerivedVariables.Add(aggregate); var createFrame = new CallCreateAggregateFrame(_createMethods, aggregate) { FirstEventExpression = $"fragment.{nameof(StreamFragment<string, string>.Events)}[0]", Action = CreateAggregateAction.NullCoalesce }; method.Frames.Add(createFrame); method.Frames.Add(new MethodCall(_storageType, "SetIdentity")); var handlers = MethodCollection.AddEventHandling(typeof(T), _aggregateMapping, _applyMethods, _shouldDeleteMethods); var iterate = new ForEachEventFrame((IReadOnlyList <Frame>)handlers) { EventIteration = "fragment.Events" }; method.Frames.Add(iterate); var upsertMethod = typeof(IDocumentStorage <>).MakeGenericType(typeof(T)).GetMethod("Upsert"); var upsert = new MethodCall(_storageType, upsertMethod) { ReturnAction = ReturnAction.Return }; method.Frames.Add(upsert); }
private void buildLiveAggregationType() { var liveBaseType = _isAsync ? typeof(AsyncLiveAggregatorBase <>) : typeof(SyncLiveAggregatorBase <>); liveBaseType = liveBaseType.MakeGenericType(typeof(T)); _liveType = _assembly.AddType(GetType().NameInCode().Sanitize() + "LiveAggregation", liveBaseType); var overrideMethodName = _isAsync ? "BuildAsync" : "Build"; var buildMethod = _liveType.MethodFor(overrideMethodName); buildMethod.DerivedVariables.Add(Variable.For <IQuerySession>("(IQuerySession)session")); buildMethod.Frames.Code("if (!events.Any()) return null;"); buildMethod.Frames.Add(new DeclareAggregateFrame(typeof(T))); var callCreateAggregateFrame = new CallCreateAggregateFrame(_createMethods); // This is the existing snapshot passed into the LiveAggregator var snapshot = buildMethod.Arguments.Single(x => x.VariableType == typeof(T)); callCreateAggregateFrame.CoalesceAssignTo(snapshot); buildMethod.Frames.Add(callCreateAggregateFrame); buildMethod.Frames.Add(new CallApplyAggregateFrame(_applyMethods) { InsideForEach = true }); buildMethod.Frames.Return(typeof(T)); _liveType.AllInjectedFields.Add(new InjectedField(GetType())); _createMethods.BuildCreateMethod(_liveType, _aggregateMapping); _applyMethods.BuildApplyMethod(_liveType, _aggregateMapping); _liveType.Setters.AddRange(_applyMethods.Setters()); _liveType.Setters.AddRange(_createMethods.Setters()); _liveType.Setters.AddRange(_shouldDeleteMethods.Setters()); }