private static (OutStatus, Operation) DetermineReplyPattern( MessageUnit mu, IDictionary <string, MessageExchangePattern> relatedInMessageMeps, ReceivingProcessingMode receivingPMode) { if (mu is UserMessage) { return(OutStatus.NotApplicable, Operation.ToBeProcessed); } string key = mu.RefToMessageId ?? string.Empty; if (!relatedInMessageMeps.ContainsKey(key)) { return(OutStatus.Created, Operation.NotApplicable); } ReplyPattern replyPattern = receivingPMode?.ReplyHandling?.ReplyPattern ?? ReplyHandling.DefaultReplyPattern; bool userMessageWasSendViaPull = relatedInMessageMeps[key] == MessageExchangePattern.Pull; if (userMessageWasSendViaPull && replyPattern == ReplyPattern.Response) { throw new InvalidOperationException( $"Cannot determine Status and Operation because ReceivingPMode {receivingPMode?.Id} ReplyHandling.ReplyPattern = Response " + "while the UserMessage has been send via pulling. Please change the ReplyPattern to 'CallBack' or 'PiggyBack'"); } bool signalShouldBePiggyBackedToPullRequest = replyPattern == ReplyPattern.PiggyBack; if (userMessageWasSendViaPull && signalShouldBePiggyBackedToPullRequest) { return(OutStatus.Created, Operation.ToBePiggyBacked); } bool signalShouldBeRespondedAsync = replyPattern == ReplyPattern.Callback; if (signalShouldBeRespondedAsync) { return(OutStatus.Created, Operation.ToBeSent); } return(OutStatus.Sent, Operation.NotApplicable); }
public async Task Stores_SignalMessage_With_Expected_Operation_According_To_MEP_And_ReplyPattern( MessageExchangePattern mep, ReplyPattern reply, Operation op) { // Arrange string userMessageId = $"user-{Guid.NewGuid()}"; GetDataStoreContext.InsertInMessage( new InMessage(userMessageId) { MEP = mep }); var receipt = new Receipt($"receipt-{Guid.NewGuid()}", userMessageId); var context = new MessagingContext( AS4Message.Create(receipt), MessagingContextMode.Receive) { SendingPMode = new SendingProcessingMode { Id = "shortcut-send-pmode-retrieval" }, ReceivingPMode = new ReceivingProcessingMode { ReplyHandling = { ReplyPattern = reply } } }; // Act await ExerciseStoreSignalMessageAsync(context); // Assert GetDataStoreContext.AssertOutMessage( receipt.MessageId, m => { Assert.NotNull(m); Assert.Equal(op, m.Operation); }); }
public Property Returns_Empty_Soap_For_Signals_If_ReplyPattern_Is_Callback_Or_Mode_Is_PullReceive( SignalMessage signal, ReplyPattern pattern, MessagingContextMode mode) { // Arrange var context = new MessagingContext(AS4Message.Create(signal), mode) { ReceivingPMode = new ReceivingProcessingMode { ReplyHandling = { ReplyPattern = pattern } }, SendingPMode = new SendingProcessingMode { Id = "sending-pmode" } }; // Act StepResult result = ExerciseStoreSignalMessageAsync(context).GetAwaiter().GetResult(); // Assert AS4Message actual = result.MessagingContext.AS4Message; AS4Message expected = context.AS4Message; bool isCallback = pattern == ReplyPattern.Callback; bool isResponse = pattern == ReplyPattern.Response; bool isPullReceive = mode == MessagingContextMode.PullReceive; bool isSignal = expected.Equals(actual); return((actual.IsEmpty == (isCallback || isPullReceive)) .Label("Should be an empty SOAP envelope when configured Callback or in PullReceive mode") .Or(isSignal == isResponse) .Label("Should be a SignalMessage when configured Response") .Classify(actual.IsEmpty, "Empty SOAP envelope response") .Classify(isSignal, "SignalMessage response")); }
public Property ResponseConfiguration_Should_Be_Specified_When_ReplyPattern_Is_Callback(ReplyPattern pattern) { return(Prop.ForAll( Arb.Generate <string>() .Select(url => new Protocol { Url = url }) .OrNull() .Select(p => new PushConfiguration { Protocol = p }) .OrNull() .ToArbitrary(), responseConfig => { // Arrange var pmode = new ReceivingProcessingMode { Id = "receiving-pmode", ReplyHandling = { ReplyPattern = ReplyPattern.Callback, ResponseConfiguration = responseConfig } }; // Act ValidationResult result = ExerciseValidation(pmode); // Assert return result.IsValid.Equals( !String.IsNullOrEmpty(responseConfig?.Protocol?.Url) && pattern == ReplyPattern.Callback) .Label("valid when ReplyPattern = Callback and non-empty 'Url'") .Or(result.IsValid.Equals(pattern != ReplyPattern.Callback) .Label("valid when ReplyPattern != Callback")); })); }
public Property PiggyBackReliability_Is_Only_Allowed_When_ReplyPattern_Is_PiggyBack(ReplyPattern pattern) { return(Prop.ForAll( Gen.Fresh(() => new RetryReliability { IsEnabled = false }) .OrNull() .ToArbitrary(), reliability => { // Arrange var pmode = new ReceivingProcessingMode { Id = "receiving-pmode", ReplyHandling = { ReplyPattern = pattern, PiggyBackReliability = reliability, } }; // Act ValidationResult result = ExerciseValidation(pmode); // Assert return result.IsValid.Equals(pattern == ReplyPattern.PiggyBack) .Label("valid when ReplyPattern = PiggyBack") .Or(result.IsValid.Equals(pattern != ReplyPattern.PiggyBack && reliability == null) .Label("valid when ReplyPattern != PiggyBack and no PiggyBackReliability")); })); }