public override void PostSave(Saga saga, SagaContext commit, Exception error)
 {
 }
Example #2
0
        public void RunsTakeSagaWaitingForAction()
        {
            //Arrange
            var runner     = new Saga();
            var enumerator = runner.Run(this.RootSaga());

            //Act
            SagaAction returnData = null;

            runner.OnActionEvent += (data) =>
            {
                returnData = data;
            };

            for (var i = 0; i < 100; i++)
            {
                enumerator.MoveNext();
            }

            //Assert
            Assert.IsNull(returnData);

            runner.OnAction(new SagaAction <int>("start", 11));

            for (var i = 0; i < 100; i++)
            {
                enumerator.MoveNext();
            }

            //Assert
            Assert.AreEqual("test", returnData.Type);
            Assert.AreEqual(11, returnData.GetPayload <int>());
        }
 protected override void OnRegister(Saga.Templates.BaseNPC npc)
 {
     RegisterDialog(npc, DialogType.Smith, new FunctionCallback(OnBlackSmithMenu));
     RegisterDialog(npc, DialogType.Smith, 50, new FunctionCallback(OnRepairEquipment));
     RegisterDialog(npc, DialogType.Smith, 53, new FunctionCallback(OnUpgradeWeapon));
     RegisterDialog(npc, DialogType.Smith, 55, new FunctionCallback(OnChangeWeaponSuffix));
 }
        public IDataReader ExecuteDataReader(Saga.Data.IQueryProvider query, CommandBehavior behavior)
        {
            MySqlConnection connection = ConnectionPool.Request();
            MySqlCommand command = new MySqlCommand();
            MySqlDataReader reader = null;

            try
            {

                command.CommandText = query.CmdText;
                command.Connection = connection;
                foreach (KeyValuePair<string, object> pair in query.Parameters)
                {
                    command.Parameters.AddWithValue(pair.Key, pair.Value);
                }

                return command.ExecuteReader(behavior);
            }
            catch (Exception e)
            {
                __dbtracelog.WriteError("Database", e.Message);
                return null;
            }
            finally
            {
                //ALWAYS CLOSE THE CONNECTION AND REPOOL THE ITEMS
                if (reader != null && reader.IsClosed == false) reader.Close();
                ConnectionPool.Release(connection);
            }
        }
        public int ExecuteNonQuery(Saga.Data.IQueryProvider query)
        {
            //HELPER VARIABLES
            MySqlConnection connection = ConnectionPool.Request();
            MySqlCommand command = new MySqlCommand();

            try
            {
                command.CommandText = query.CmdText;
                command.Connection = connection;
                foreach (KeyValuePair<string, object> pair in query.Parameters)
                {
                    command.Parameters.AddWithValue(pair.Key, pair.Value);
                }

                return command.ExecuteNonQuery();
            }
            catch (Exception e)
            {
                __dbtracelog.WriteError("Database", e.Message);
                return 0;
            }
            finally
            {
                //ALWAYS CLOSE THE CONNECTION AND REPOOL THE ITEMS
                ConnectionPool.Release(connection);
            }
        }
Example #6
0
        public void RemoveSaga <TMessage>(Saga <TSagaData> saga)
        {
            var finder = _factory.Create <TSagaData, TMessage>();

            // Refactor
            ((ISagaDataFinderBase <TSagaData>)finder).RemoveSagaData(saga.Data);
        }
Example #7
0
    // Use this for initialization
    void Start()
    {
        var saga = new Saga();

        saga.OnActionEvent += Saga_OnActionEvent;

        this.StartCoroutine(saga.Run(this.RootSaga()));
    }
Example #8
0
        public LastNameRouteBuilder(Saga saga, string name)
        {
            _saga = saga;

            _name = name;

            _channels = new List <Channel>();
        }
        public void Dispatch(IEnvelope envelope)
        {
            var actor   = Agent.GetActor(envelope.CorrelationId);
            var message = (TMessage)envelope.Message;

            Saga.Process(actor, message);
            Agent.Memoize(actor);
        }
Example #10
0
        /// <summary>
        /// Attempt to retrieve an existing saga instance identified by the specified <paramref name="type"/> and <paramref name="id"/>.
        /// </summary>
        /// <param name="type">The type of saga to be retrieved.</param>
        /// <param name="id">The correlation id of the saga to be retrieved.</param>
        /// <param name="saga">The <see cref="Saga"/> instance if found; otherwise <value>null</value>.</param>
        public Boolean TryGetSaga(Type type, Guid id, out Saga saga)
        {
            var result = sagaStore.TryGetSaga(type, id, out saga);

            statistics.IncrementQueryCount();

            return(result);
        }
Example #11
0
        public void Continue(object message, Saga saga, Route route)
        {
            var adapter = _factory.Create <IMessageAdapter>(_configuration.MessageAdapterType);

            var interceptor = _factory.Create <IRouterInterceptor>(_configuration.RouterInterceptorType);

            var context = adapter.Read(message, route.ContentType);

            var when = true;

            if (route.When != null)
            {
                when = route.When(context);
            }

            if (when)
            {
                interceptor.OnEntry(context);

                try
                {
                    var middlewares = new List <Type> {
                        typeof(MessageExceptionHandler)
                    };

                    middlewares.AddRange(_configuration.InboundMiddlewareTypes);

                    middlewares.AddRange(route.MiddlewareTypes);

                    middlewares.Add(typeof(NextMessageHandler));

                    var parameter = new MiddlewareParameter()
                    {
                        Route = route, Saga = saga
                    };

                    context.Route = route;

                    context.Saga = saga;

                    var pipeline = new Pipeline(_factory, middlewares.ToArray(), context, parameter);

                    pipeline.Execute();

                    interceptor.OnSuccess(context);
                }
                catch (Exception ex)
                {
                    interceptor.OnException(context, ex);

                    throw;
                }
                finally
                {
                    interceptor.OnExit(context);
                }
            }
        }
Example #12
0
        public void ExceptionWithoutTryShouldCrashTheProcess()
        {
            //Arrange
            var runner = new Saga();

            //Assert
            Assert.Catch <NotImplementedException>(
                () => this.RunSaga(runner, this.DoStuff(new Ref <int>(), true)));
        }
        internal ActiveSagaInstance(Saga saga, SagaMetadata metadata, Func<DateTime> currentUtcDateTimeProvider)
        {
            this.currentUtcDateTimeProvider = currentUtcDateTimeProvider;
            Instance = saga;
            Metadata = metadata;

            Created = currentUtcDateTimeProvider();
            Modified = Created;
        }
Example #14
0
        /// <summary>
        /// Gets (most likely from a cache) the set of correlation properties relevant for the given saga handler.
        /// </summary>
        public SagaDataCorrelationProperties GetCorrelationProperties(object message, Saga saga)
        {
            var sagaDataType = saga.GetSagaDataType();

            var correlationPropertiesForThisSagaDataType = _cachedCorrelationProperties
                .GetOrAdd(sagaDataType, type => GetCorrelationProperties(saga));

            return new SagaDataCorrelationProperties(correlationPropertiesForThisSagaDataType, sagaDataType);
        }
    static void AddEntity(ILogger logger, Saga saga, List <LogEventProperty> properties)
    {
        if (!logger.BindProperty("Entity", saga.Entity, out var sagaEntityProperty))
        {
            return;
        }

        properties.Add(sagaEntityProperty);
    }
        public void MessageReceived()
        {
            var data = new OldCacheUpdateRequest()
            {
                RequestingUri = new Uri("msmq://bob/bill")
            };

            Saga.RaiseEvent(LegacySubscriptionClientSaga.OldCacheUpdateRequested, data);
        }
Example #17
0
        /// <summary>
        ///  When overriden, defines the custom behavior to be invoked after attempting to save the specified <paramref name="saga"/>.
        /// </summary>
        /// <param name="saga">The modified <see cref="Saga"/> instance if <paramref name="error"/> is <value>null</value>; otherwise the original <see cref="Saga"/> instance if <paramref name="error"/> is not <value>null</value>.</param>
        /// <param name="context">The current <see cref="SagaContext"/> assocaited with the pending saga modifications.</param>
        /// <param name="error">The <see cref="Exception"/> thrown if the save was unsuccessful; otherwise <value>null</value>.</param>
        public override void PostSave(Saga saga, SagaContext context, Exception error)
        {
            base.PostSave(saga, context, error);

            if (error is ConcurrencyException)
            {
                statistics.IncrementConflictCount();
            }
        }
Example #18
0
        /// <summary>
        /// Creates a new <see cref="ActiveSagaInstance"/> instance.
        /// </summary>
        public ActiveSagaInstance(Saga saga, SagaMetadata metadata, Func <DateTime> currentUtcDateTimeProvider)
        {
            this.currentUtcDateTimeProvider = currentUtcDateTimeProvider;
            Instance = saga;
            Metadata = metadata;

            Created  = currentUtcDateTimeProvider();
            Modified = Created;
        }
Example #19
0
        public void TestMultipleCommits()
        {
            // Arrange
            Mock <Action> rollbackStep1 = new Mock <Action>();

            rollbackStep1.Setup(m => m());

            Mock <Action> rollbackStep2 = new Mock <Action>();

            rollbackStep1.Setup(m => m());

            Mock <Action> rollbackStep3 = new Mock <Action>();

            rollbackStep1.Setup(m => m());

            Mock <Action> rollbackStep4 = new Mock <Action>();

            rollbackStep4.Setup(m => m());

            Exception exception = null;

            // Act
            try
            {
                using (Saga saga = new Saga())
                {
                    DoStep1();
                    saga.RegisterCompensation(rollbackStep1.Object);

                    saga.Commit();

                    DoStep2();
                    saga.RegisterCompensation(rollbackStep2.Object);

                    DoStep3();
                    saga.RegisterCompensation(rollbackStep3.Object);

                    DoStep4();
                    saga.RegisterCompensation(rollbackStep4.Object);

                    saga.Commit();
                }
            }
            catch (Exception ex)
            {
                exception = ex;
            }

            // Assert
            Assert.IsInstanceOfType(exception, typeof(ApplicationException));

            rollbackStep1.Verify(m => m(), Times.Never);
            rollbackStep2.Verify(m => m(), Times.Once);
            rollbackStep3.Verify(m => m(), Times.Once);
            rollbackStep4.Verify(m => m(), Times.Never);
        }
        private async Task PublishCommandsAsync(Saga saga)
        {
            var messages = saga.GetUndispatchedCommands().Select(command => {
                dynamic typeAwareCommand = command; //this cast is required to pass the correct Type to the Notify Method. Otherwise IEvent is used as the Type
                return((Task)_commandDispatcher.SendAsync(typeAwareCommand));
            });
            await Task.WhenAll(messages);

            saga.ClearUndispatchedCommands();
        }
Example #21
0
        public void test_01_all_movements_succeed_in_first_setp()
        {
            var movements = new List <Movement> {
                GetSuccesfullMovement(), GetSuccesfullMovement()
            };

            Saga.Start(movements).Should().BeTrue();
            movements.Select(x => x.InProcess).Should().AllBeEquivalentTo(true);
            movements.Select(x => x.IsSuccesfull).Should().AllBeEquivalentTo(false);
        }
 protected override void OnBlackSmithMenu(BaseNPC npc, Saga.PrimaryTypes.Character target)
 {
     Common.Actions.OpenSubmenu(target, npc,
       _BlackSmithMenu,        //Dialog script to show
       DialogType.Smith,       //Button function
       50,                     //Repair
       53,                     //Upgrade
       55                      //Change Suffix
     );
 }
Example #23
0
        protected void RunSaga(Saga runner, IEnumerator sagaToRun)
        {
            //Arrange
            var enumerator = runner.Run(sagaToRun);

            while (enumerator.MoveNext())
            {
                ;
            }
        }
Example #24
0
        public void test_03_last_movement_fails_so_all_rollback()
        {
            var movements = new List <Movement> {
                GetSuccesfullMovement(), GetFailedMovement()
            };

            Saga.Start(movements);
            movements[0].IsRollback.Should().BeTrue();
            movements.Select(x => x.Started).Should().AllBeEquivalentTo(true);
            movements.Select(x => x.InProcess).Should().AllBeEquivalentTo(false);
        }
Example #25
0
        public override void OnLeave(Saga.PrimaryTypes.Character character)
        {
            //Removes the actor from the shipzone
            base.OnLeave(character);

            //Always force to leave from shipzone
            character.map = this.CathelayaLocation.map;
            character.Position = this.CathelayaLocation.coords;

            System.Console.WriteLine("{0} {1}", this.CathelayaLocation.map, this.CathelayaLocation.coords);
        }
 /// <summary>
 /// Opens the bookstore.
 /// </summary>
 /// <param name="character">Character to show the bookstore</param>
 /// <param name="basenpc">Npc providing the bookstore</param>
 public override void Open(Saga.PrimaryTypes.Character character, Saga.Templates.BaseNPC basenpc)
 {
     character.Tag = this;
     SMSG_SENDBOOKLIST spkt = new SMSG_SENDBOOKLIST();
     spkt.SessionId = character.id;
     spkt.SourceActor = basenpc.id;
     spkt.Zeny = basenpc.Zeny;
     foreach (BaseShopCollection.ShopPair c in this.list)
         spkt.Add(c.item.info.item);
     character.client.Send((byte[])spkt);
 }
        public UpdateProcessLevyDeclarationsSagaProgressCommandHandlerTestsFixture SetScheduledSagaType()
        {
            Saga.Set(s => s.Type, LevyDeclarationSagaType.Planned)
            .Set(s => s.AccountPayeSchemeHighWaterMarkId, AccountPayeSchemes.Max(aps => aps.Id))
            .Set(s => s.ImportPayeSchemeLevyDeclarationsTasksCount, AccountPayeSchemes.Select(aps => aps.EmployerReferenceNumber).Count())
            .Set(s => s.UpdateAccountTransactionBalancesTasksCount, AccountPayeSchemes.Select(aps => aps.AccountId).Distinct().Count());

            Db.SaveChanges();

            return(this);
        }
Example #28
0
        private ISagaWithCreatedOn GetSagaData(Saga saga)
        {
            var property = _sagaDataCache.GetOrAdd(saga.GetType(), x => saga.GetType().GetProperty(nameof(Saga <ISagaData> .Data)));
            var data     = property.GetValue(saga) as ISagaWithCreatedOn;

            Guard.Against <InvalidOperationException>(data == null,
                                                      $"SagaData for saga {saga.GetType()} does not implemente {nameof(ISagaWithCreatedOn)}?!"
                                                      );

            return(data);
        }
Example #29
0
    /// <summary>
    /// Gets (most likely from a cache) the set of correlation properties relevant for the given saga handler.
    /// </summary>
    public SagaDataCorrelationProperties GetCorrelationProperties(object message, Saga saga)
    {
        var sagaType     = saga.GetType();
        var sagaDataType = saga.GetSagaDataType();
        var key          = $"{sagaType.FullName}/{sagaDataType.FullName}";

        var correlationPropertiesForThisSagaDataType = _cachedCorrelationProperties
                                                       .GetOrAdd(key, _ => GetCorrelationProperties(saga));

        return(new SagaDataCorrelationProperties(correlationPropertiesForThisSagaDataType, sagaDataType));
    }
Example #30
0
 public SagaProcess(string name, Saga saga, IEnumerator enumerator, bool isSynchronous)
 {
     this.Name                  = name;
     this.Saga                  = saga;
     this.subProcesses          = new Queue <SagaProcess>();
     this.runningProcesses      = new List <SagaProcess>();
     this.IsSynchronous         = isSynchronous;
     this.HasEnumeratorFinished = false;
     this.processEnumerator     = Utils.Flatten(enumerator);
     this.processQueue          = this.CreateProcessQueue();
 }
        public UpdateProcessLevyDeclarationsSagaProgressCommandHandlerTestsFixture SetAdHocSagaType()
        {
            Saga.Set(s => s.Type, LevyDeclarationSagaType.AdHoc)
            .Set(s => s.AccountPayeSchemeId, AccountPayeSchemes[0].Id)
            .Set(s => s.ImportPayeSchemeLevyDeclarationsTasksCount, 1)
            .Set(s => s.UpdateAccountTransactionBalancesTasksCount, 1);

            Db.SaveChanges();

            return(this);
        }
Example #32
0
        /// <summary>
        /// Gets (most likely from a cache) the set of correlation properties relevant for the given saga handler.
        /// </summary>
        public SagaDataCorrelationProperties GetCorrelationProperties(object message, Saga saga)
        {
            var sagaType = saga.GetType();
            var sagaDataType = saga.GetSagaDataType();
            var key = $"{sagaType.FullName}/{sagaDataType.FullName}";

            var correlationPropertiesForThisSagaDataType = _cachedCorrelationProperties
                .GetOrAdd(key, _ => GetCorrelationProperties(saga));

            return new SagaDataCorrelationProperties(correlationPropertiesForThisSagaDataType, sagaDataType);
        }
Example #33
0
        public RelevantSagaInfo(ISagaData sagaData, IEnumerable <CorrelationProperty> correlationProperties, Saga saga)
        {
            SagaData = sagaData;

            // only keep necessary correlation properties, i.e.
            CorrelationProperties = correlationProperties
                                    .GroupBy(p => p.PropertyName)
                                    .Select(g => g.First())
                                    .ToList();

            Saga = saga;
        }
Example #34
0
 private void StartSaga(IGameMessage @event, Saga saga)
 {
     _repository.Add(saga);
     try
     {
         saga.Handle(@event);
     }
     finally
     {
         CleanUp(saga);
     }
 }
Example #35
0
        public void test_02_first_movements_fails_so_no_rollbacks()
        {
            var movements = new List <Movement> {
                GetFailedMovement(), GetSuccesfullMovement()
            };

            Saga.Start(movements);
            movements[0].Started.Should().BeTrue();
            movements[0].InProcess.Should().BeFalse();
            movements[0].IsSuccesfull.Should().BeFalse();
            movements[1].IsRollback.Should().BeFalse();
            movements[1].Started.Should().BeFalse();
        }
Example #36
0
        public async Task <Saga> CreateAsync(Saga saga, CancellationToken cancellationToken = default)
        {
            try
            {
                await _sagas.InsertOneAsync(saga, cancellationToken : cancellationToken);
            }
            catch (MongoWriteException e)
            {
                throw new SagaNotCreatedException(saga.Id.ToString(), e);
            }

            return(saga);
        }
Example #37
0
        public void Start(object message, Saga saga, Route route)
        {
            var adapter = _factory.Create <IMessageAdapter>(_configuration.MessageAdapterType);

            var interceptor = _factory.Create <IRouterInterceptor>(_configuration.RouterInterceptorType);

            var context = adapter.Read(message, route.ContentType, route.UseClaimCheck, route.IdentityConfiguration);

            var when = true;

            if (route.When != null)
            {
                when = route.When(context);
            }

            if (when)
            {
                interceptor.OnEntry(context);

                try
                {
                    var middlewares = new List <Type> {
                        typeof(MessageExceptionHandler)
                    };

                    middlewares.AddRange(_configuration.InboundMiddlewareTypes);

                    middlewares.AddRange(saga.FirstRoute.MiddlewareTypes);

                    middlewares.Add(typeof(FirstMessageHandler));

                    context.Route = route;

                    context.Saga = saga;

                    _pipeline.Execute(middlewares.ToArray(), context);

                    interceptor.OnSuccess(context);
                }
                catch (Exception ex)
                {
                    interceptor.OnException(context, ex);

                    throw;
                }
                finally
                {
                    interceptor.OnExit(context);
                }
            }
        }
        public UpdateProcessLevyDeclarationsSagaProgressCommandHandlerTestsFixture SetTooManyUpdateAccountTransactionBalancesTasksCompleted()
        {
            Saga.Set(s => s.ImportPayeSchemeLevyDeclarationsTasksCompleteCount, AccountPayeSchemes.Count);

            Tasks = Accounts
                    .Select(a => LevyDeclarationSagaTask.CreateUpdateAccountTransactionBalancesTask(Saga.Id, a.Id))
                    .Append(LevyDeclarationSagaTask.CreateUpdateAccountTransactionBalancesTask(Saga.Id, Accounts[0].Id))
                    .ToList();

            Db.LevyDeclarationSagaTasks.AddRange(Tasks);
            Db.SaveChanges();

            return(this);
        }
Example #39
0
        /// <summary>
        /// Gets whether a message of the given type is allowed to cause a new saga data instance to be created
        /// </summary>
        public bool CanBeInitiatedBy(Type messageType)
        {
            // checks if IAmInitiatedBy<TMessage> is implemented by the saga
            return(CanBeInitiatedByCache
                   .GetOrAdd($"{Handler.GetType().FullName}::{messageType.FullName}", _ =>
            {
                var implementedInterfaces = Saga.GetType().GetInterfaces();

                var handlerTypesToLookFor = new[] { messageType }.Concat(messageType.GetBaseTypes())
                .Select(baseType => typeof(IAmInitiatedBy <>).MakeGenericType(baseType));

                return implementedInterfaces.Intersect(handlerTypesToLookFor).Any();
            }));
        }
        public UpdateProcessLevyDeclarationsSagaProgressCommandHandlerTestsFixture SetSomeUpdateAccountTransactionBalancesTasksCompleted()
        {
            Saga.Set(s => s.ImportPayeSchemeLevyDeclarationsTasksCompleteCount, AccountPayeSchemes.Count);

            Tasks = new List <LevyDeclarationSagaTask>
            {
                LevyDeclarationSagaTask.CreateUpdateAccountTransactionBalancesTask(Saga.Id, AccountPayeSchemes[0].AccountId)
            };

            Db.LevyDeclarationSagaTasks.AddRange(Tasks);
            Db.SaveChanges();

            return(this);
        }
Example #41
0
 /// <summary>
 /// Opens the shop
 /// </summary>
 /// <param name="character">Character to show the shop</param>
 /// <param name="basenpc">Npc providing the v</param>
 public override void Open(Saga.PrimaryTypes.Character character, Saga.Templates.BaseNPC basenpc)
 {
     character.Tag = this;
     SMSG_SHOPLIST spkt = new SMSG_SHOPLIST();
     spkt.SessionId = character.id;
     spkt.SourceActor = basenpc.id;
     spkt.Zeny = basenpc.Zeny;
     for (int i = 0; i < list.Count; i++)
     {
         ShopPair c = list[i];
         if (c.NoStock == true || c.item.count > 0)
             spkt.AddItem(c.item, c.NoStock, i);
     }
     character.client.Send((byte[])spkt);
     CommonFunctions.SendRebuylist(character);
 }
Example #42
0
 internal void RaiseUncorrelatedMessage(object message, Saga saga)
 {
     UncorrelatedMessage(message, saga);
 }
 internal void RaiseUncorrelatedMessage(IBus bus, object message, Saga saga)
 {
     UncorrelatedMessage(bus, message, saga);
 }
 public override void PostSave(Saga saga, SagaContext context, Exception error)
 {
     base.PostSave(null, null, null); PostSaveInvoked = true;
 }
 public override void PreSave(Saga saga, SagaContext context)
 {
 }
Example #46
0
            public RelevantSagaInfo(ISagaData sagaData, IEnumerable<CorrelationProperty> correlationProperties, Saga saga)
            {
                SagaData = sagaData;

                // only keep necessary correlation properties, i.e.
                CorrelationProperties = correlationProperties
                    .GroupBy(p => p.PropertyName)
                    .Select(g => g.First())
                    .ToList();

                Saga = saga;
            }
Example #47
0
 /// <summary>
 /// Creates a new instance of the saga's saga data
 /// </summary>
 public ISagaData CreateNewSagaData(Saga saga)
 {
     return saga.CreateNewSagaData();
 }
Example #48
0
 static Dictionary<Type, CorrelationProperty[]> GetCorrelationProperties(Saga saga)
 {
     return saga.GenerateCorrelationProperties()
         .ToLookup(p => p.MessageType)
         .ToDictionary(kvp => kvp.Key, kvp => kvp.ToArray());
 }
Example #49
0
 IEnumerable<MarketItemArgument> IDatabase.SearchMarket(Saga.Map.Definitions.Misc.MarketSearchArgument Argument)
 {
     return SearchMarket(Argument);
 }
Example #50
0
 int IDatabase.ExecuteNonQuery(Saga.Data.IQueryProvider query)
 {
     return ExecuteNonQuery(query);
 }
Example #51
0
 System.Data.IDataReader IDatabase.ExecuteDataReader(Saga.Data.IQueryProvider query)
 {
     return ExecuteDataReader(query);
 }
Example #52
0
 System.Data.IDataReader IDatabase.ExecuteDataReader(Saga.Data.IQueryProvider query, System.Data.CommandBehavior behavior)
 {
     return ExecuteDataReader(query, behavior);
 }
        /// <summary>
        /// Update an existing saga instance.
        /// </summary>
        /// <param name="saga">The saga instance to update.</param>
        private void UpdateSaga(Saga saga)
        {
            var state = serializer.Serialize(saga);
            var typeId = GetSagaTypeId(saga.GetType());

            using (var command = dialect.CreateCommand(dialect.UpdateSaga))
            {
                Log.Trace("Updating existing saga {0}", saga);

                command.Parameters.Add(dialect.CreateTypeIdParameter(typeId));
                command.Parameters.Add(dialect.CreateIdParameter(saga.CorrelationId));
                command.Parameters.Add(dialect.CreateVersionParameter(saga.Version));
                command.Parameters.Add(dialect.CreateTimeoutParameter(saga.Timeout));
                command.Parameters.Add(dialect.CreateStateParameter(state));

                if (dialect.ExecuteNonQuery(command) == 0)
                    throw new ConcurrencyException(Exceptions.SagaConcurrencyConflict.FormatWith(saga.GetType(), saga.CorrelationId));
            }

            saga.Version++;
        }
        /// <summary>
        /// Save the specified <paramref name="context"/> changes for the given <paramref name="saga"/>.
        /// </summary>
        /// <param name="saga">The current saga version for which the context applies.</param>
        /// <param name="context">The saga context containing the saga changes to be applied.</param>
        public Saga Save(Saga saga, SagaContext context)
        {
            Verify.NotNull(saga, nameof(saga));

            if (saga.Version == 0 && saga.Completed)
                return saga;

            if (saga.Completed)
            {
                if (saga.Version > 0)
                    DeleteSaga(saga);
            }
            else
            {
                if (saga.Version == 0)
                    InsertSaga(saga);
                else
                    UpdateSaga(saga);
            }

            return saga;
        }
        /// <summary>
        /// Attempt to retrieve an existing saga instance identified by the specified <paramref name="type"/> and <paramref name="id"/>.
        /// </summary>
        /// <param name="type">The type of saga to be retrieved.</param>
        /// <param name="id">The correlation id of the saga to be retrieved.</param>
        /// <param name="saga">The <see cref="Saga"/> instance if found; otherwise <value>null</value>.</param>
        public Boolean TryGetSaga(Type type, Guid id, out Saga saga)
        {
            Verify.NotNull(type, nameof(type));

            using (var command = dialect.CreateCommand(dialect.GetSaga))
            {
                Log.Trace("Getting saga {0} - {1}", type, id);

                command.Parameters.Add(dialect.CreateIdParameter(id));
                command.Parameters.Add(dialect.CreateTypeIdParameter(GetSagaTypeId(type)));

                saga = dialect.QuerySingle(command, CreateSaga);
            }

            return saga != null;
        }
 public override void PostGet(Saga saga)
 {
     base.PostGet(null); PostGetInvoked = true;
 }
 protected EventContext CreateEventContext(Saga saga, DateTime timeout)
 {
     return new EventContext(saga.CorrelationId, HeaderCollection.Empty, new Timeout(saga.GetType(), timeout));
 }
 public override void PreSave(Saga saga, SagaContext context)
 {
     base.PreSave(null, null); PreSaveInvoked = true;
 }
        /// <summary>
        /// Delete an existing saga instance.
        /// </summary>
        /// <param name="saga">The saga instance to delete.</param>
        private void DeleteSaga(Saga saga)
        {
            var typeId = GetSagaTypeId(saga.GetType());

            using (var command = dialect.CreateCommand(dialect.DeleteSaga))
            {
                Log.Trace("Completing existing saga {0}", saga);

                command.Parameters.Add(dialect.CreateTypeIdParameter(typeId));
                command.Parameters.Add(dialect.CreateIdParameter(saga.CorrelationId));
                command.Parameters.Add(dialect.CreateVersionParameter(saga.Version));

                if (dialect.ExecuteNonQuery(command) == 0)
                    throw new ConcurrencyException(Exceptions.SagaConcurrencyConflict.FormatWith(saga.GetType(), saga.CorrelationId));
            }
        }
 public override void PostGet(Saga saga)
 {
 }