sagar
sagar

Reputation: 177

NserviceBus not loading existing saga data

I have implemented a my connector using nservice bus saga. Below is the code

    public class ClientSaga : Saga<ClientSagaState>, 
            IAmStartedByMessages<ClientChangeMessage>, 
            IAmStartedByMessages<ClientContactChangeMessage>,
            IAmStartedByMessages<ClientPictureChangeMessage>, 
            IHandleTimeout<ClientSagaState>
        {
            [SetterProperty]
            public IClientContactChangeDb ClientContactChangeDb{get;set;}

            [SetterProperty]
            public IBusRefTranslator BusRefTranslator{get;set;}



            public void Handle(ClientContactChangeMessage message)
            {
                var state=this.Data;
                //Some handling logic
                //Check if client is not in database then store the state
                state.ClientContactChange=message;
                state.ClientRef =message.ClientRef;
                //if client is in the data base then 
                MarkAsComplete();
            }

            public void Handle(ClientChangeMessage message)
            {
                 var state=this.data;
                //Update or create the client depending on the situation
                //check for dependencies
                if(state.ClientContactChange !=null)
                {
                     //Handle the contact change
                } 
                else
                 {
                   state.ClientChangeMessage=message;
                    state.ClientRef=message.ClientRef;
                   }
            }
              public void Handle(ClientPictureChangeMessage message)
            {
                     var state=this.Data;
                 //If the client is there then update the picture else store in saga
                   state.ClientPictureChangeMessage =message;
                    state.ClientRef=message.ClientRef;
                   }
            }

            public override void ConfigureHowToFindSaga()
            {
                ConfigureMapping<ClientContactChangeMessage>(s => s.ClientRef, m => m.ClientRef);
                ConfigureMapping<ClientPictureChangeMessage>(s => s.ClientRef, m => m.ClientRef);
                ConfigureMapping<ClientChangeMessage>(s => s.ClienttnRef, m => m.Id);
            }
        }


        public class ClientSagaState: IContainSagaData
        {
            //i dont need these three fields
            public Guid Id { get; set; }
            public string Originator { get; set; }
            public string OriginalMessageId { get; set; }

           // the fields which i needed
           public Guid ClientRef {gee; set;}
           public ClientChangeMessage ClientChange {get;set;}
           public ClientContactChange ClientContactChange {get;set;}
           public ClientPictureChangeMessage  ClientPictureChangeMessage {get;set;}
        }

Now in my connector a client cannot be created w/o client contact change message being present.

Case when saga fails:

  1. When i send the the client picture message first it creates a new saga and stores it.
  2. Then i send a client change message it creates another saga and stores it i.e does not find the saga created by the client picture message
  3. Then i send the client contact change message it somehow finds the saga created by client picture change but now cannot find the staff.

I can't make out why this is happening.

Case when saga succeeds:

  1. When i send the client change message first it creates the saga.
  2. Then i send the client contact change message it finds the saga and executes fine.

Can anyone please explain why this behaviour is happening.

Please let me know if more information is needed.

Thanks

UPDATE

On checking my code again, i found the cause of this . My ClientChangeMessage was also inheriting from IContainSaga data(something which i was trying out but had forgotten to remove). After removing the inheritance link everything was working fine. (Head hanging in shame)

Upvotes: 0

Views: 884

Answers (1)

Indu Alagarsamy
Indu Alagarsamy

Reputation: 449

In all your handlers, you need to set the ClientRef on the Saga Data. So, you would have:

  public void Handle(ClientContactChangeMessage message)
        {
            Data.ClientRef = message.ClientRef
            ...
        }

As any of these messages can start the saga, you'll need to set this value in your saga state. When other messages come in, then it will be co-rrelated by this id as there is already an instance of the saga with this Id.

To refer to your saga state variables, use Data. intead of this.

Upvotes: 1

Related Questions