Example #1
0
        static void EnableBestPracticeEnforcement(Conventions conventions, PipelineSettings pipeline)
        {
            var validations = new Validations(conventions);

            pipeline.Register(
                "EnforceSendBestPractices",
                new EnforceSendBestPracticesBehavior(validations),
                "Enforces send messaging best practices");

            pipeline.Register(
                "EnforceReplyBestPractices",
                new EnforceReplyBestPracticesBehavior(validations),
                "Enforces reply messaging best practices");

            pipeline.Register(
                "EnforcePublishBestPractices",
                new EnforcePublishBestPracticesBehavior(validations),
                "Enforces publish messaging best practices");

            pipeline.Register(
                "EnforceSubscribeBestPractices",
                new EnforceSubscribeBestPracticesBehavior(validations),
                "Enforces subscribe messaging best practices");

            pipeline.Register(
                "EnforceUnsubscribeBestPractices",
                new EnforceUnsubscribeBestPracticesBehavior(validations),
                "Enforces unsubscribe messaging best practices");
        }
Example #2
0
        public static HostingComponent Initialize(Configuration configuration,
                                                  ContainerComponent containerComponent,
                                                  PipelineSettings pipelineSettings)
        {
            var hostingComponent = new HostingComponent(configuration);

            containerComponent.ContainerConfiguration.ConfigureComponent(() => hostingComponent.HostInformation, DependencyLifecycle.SingleInstance);

            pipelineSettings.Register("AuditHostInformation", new AuditHostInformationBehavior(hostingComponent.HostInformation, configuration.EndpointName), "Adds audit host information");
            pipelineSettings.Register("AddHostInfoHeaders", new AddHostInfoHeadersBehavior(hostingComponent.HostInformation, configuration.EndpointName), "Adds host info headers to outgoing headers");


            hostingComponent.AddStartupDiagnosticsSection("Hosting", new
            {
                hostingComponent.HostInformation.HostId,
                HostDisplayName = hostingComponent.HostInformation.DisplayName,
                RuntimeEnvironment.MachineName,
                OSPlatform = Environment.OSVersion.Platform,
                OSVersion  = Environment.OSVersion.VersionString,
                GCSettings.IsServerGC,
                GCLatencyMode = GCSettings.LatencyMode,
                Environment.ProcessorCount,
                Environment.Is64BitProcess,
                CLRVersion = Environment.Version,
                Environment.WorkingSet,
                Environment.SystemPageSize,
                HostName = Dns.GetHostName(),
                Environment.UserName,
                PathToExe = PathUtilities.SanitizedPath(Environment.CommandLine)
            });

            return(hostingComponent);
        }
Example #3
0
        public void Initialize(ReadOnlySettings settings, TransportInfrastructure transportInfrastructure, PipelineSettings pipelineSettings)
        {
            var unicastBusConfig        = settings.GetConfigSection <UnicastBusConfig>();
            var conventions             = settings.Get <Conventions>();
            var configuredUnicastRoutes = settings.GetOrDefault <ConfiguredUnicastRoutes>();
            var distributorAddress      = settings.GetOrDefault <string>("LegacyDistributor.Address");

            List <DistributionStrategy> distributionStrategies;

            if (settings.TryGet(out distributionStrategies))
            {
                foreach (var distributionStrategy in distributionStrategies)
                {
                    DistributionPolicy.SetDistributionStrategy(distributionStrategy);
                }
            }

            unicastBusConfig?.MessageEndpointMappings.Apply(Publishers, UnicastRoutingTable, transportInfrastructure.MakeCanonicalForm, conventions);
            configuredUnicastRoutes?.Apply(UnicastRoutingTable, conventions);

            pipelineSettings.Register(b =>
            {
                var router = new UnicastSendRouter(settings.GetOrDefault <string>("BaseInputQueueName"), settings.EndpointName(), settings.InstanceSpecificQueue(), distributorAddress, DistributionPolicy, UnicastRoutingTable, EndpointInstances, i => transportInfrastructure.ToTransportAddress(LogicalAddress.CreateRemoteAddress(i)));
                return(new UnicastSendRouterConnector(router));
            }, "Determines how the message being sent should be routed");

            pipelineSettings.Register(new UnicastReplyRouterConnector(), "Determines how replies should be routed");

            EnforceBestPractices = ShouldEnforceBestPractices(settings);
            if (EnforceBestPractices)
            {
                EnableBestPracticeEnforcement(conventions, pipelineSettings);
            }
        }
Example #4
0
        public void Initialize(ReadOnlySettings settings, Func <LogicalAddress, string> toTransportAddress, PipelineSettings pipelineSettings, ReceiveConfiguration receiveConfiguration)
        {
            var conventions             = settings.Get <Conventions>();
            var configuredUnicastRoutes = settings.GetOrDefault <ConfiguredUnicastRoutes>();

            if (settings.TryGet(out List <DistributionStrategy> distributionStrategies))
            {
                foreach (var distributionStrategy in distributionStrategies)
                {
                    DistributionPolicy.SetDistributionStrategy(distributionStrategy);
                }
            }

            configuredUnicastRoutes?.Apply(UnicastRoutingTable, conventions);

            pipelineSettings.Register(b =>
            {
                var router = new UnicastSendRouter(receiveConfiguration == null, receiveConfiguration?.QueueNameBase, receiveConfiguration?.InstanceSpecificQueue, DistributionPolicy, UnicastRoutingTable, EndpointInstances, i => toTransportAddress(LogicalAddress.CreateRemoteAddress(i)));
                return(new UnicastSendRouterConnector(router));
            }, "Determines how the message being sent should be routed");

            pipelineSettings.Register(new UnicastReplyRouterConnector(), "Determines how replies should be routed");

            EnforceBestPractices = ShouldEnforceBestPractices(settings);
            if (EnforceBestPractices)
            {
                EnableBestPracticeEnforcement(conventions, pipelineSettings);
            }
        }
Example #5
0
        public static PipelineSettings StripAssemblyVersionFromEnclosedMessageTypePipeline(this PipelineSettings pipeline)
        {
            pipeline.Register(
                behavior: new OutgoingHeaderBehavior(),
                description: "Strips assembly version from enclosed message type");

            return(pipeline);
        }
Example #6
0
        protected override void Setup(FeatureConfigurationContext context)
        {
            PipelineSettings satelliteMessagePipeline = context.AddSatellitePipeline("CustomSatellite", TransportTransactionMode.TransactionScope, PushRuntimeSettings.Default, "targetQueue");

            // register the critical error
            satelliteMessagePipeline.Register("Satellite Identifier", b => new MyAdvancedSatelliteBehavior(b.Build <CriticalError>()),
                                              "Description of what the advanced satellite does");
        }
Example #7
0
        public void Register_ThrowsWhenChangesArePrevented()
        {
            var settingsHolder   = new SettingsHolder();
            var pipelineSettings = new PipelineSettings(settingsHolder);

            pipelineSettings.PreventChanges();

            Assert.Throws <InvalidOperationException>(() => pipelineSettings.Register(typeof(Behavior1), "newStep"));
            Assert.Throws <InvalidOperationException>(() => pipelineSettings.Replace("newStep", typeof(Behavior1)));
        }
Example #8
0
        public static SendComponent Initialize(PipelineSettings pipelineSettings, HostingComponent.Configuration hostingConfiguration, RoutingComponent routingComponent, IMessageMapper messageMapper)
        {
            pipelineSettings.Register(new AttachSenderRelatedInfoOnMessageBehavior(), "Makes sure that outgoing messages contains relevant info on the sending endpoint.");
            pipelineSettings.Register("AuditHostInformation", new AuditHostInformationBehavior(hostingConfiguration.HostInformation, hostingConfiguration.EndpointName), "Adds audit host information");
            pipelineSettings.Register("AddHostInfoHeaders", new AddHostInfoHeadersBehavior(hostingConfiguration.HostInformation, hostingConfiguration.EndpointName), "Adds host info headers to outgoing headers");

            pipelineSettings.Register("UnicastSendRouterConnector", new SendConnector(routingComponent.UnicastSendRouter), "Determines how the message being sent should be routed");
            pipelineSettings.Register("UnicastReplyRouterConnector", new ReplyConnector(), "Determines how replies should be routed");


            pipelineSettings.Register(new OutgoingPhysicalToRoutingConnector(), "Starts the message dispatch pipeline");
            pipelineSettings.Register(new RoutingToDispatchConnector(), "Decides if the current message should be batched or immediately be dispatched to the transport");
            pipelineSettings.Register(new BatchToDispatchConnector(), "Passes batched messages over to the immediate dispatch part of the pipeline");
            pipelineSettings.Register(b => new ImmediateDispatchTerminator(b.GetRequiredService <IMessageDispatcher>()), "Hands the outgoing messages over to the transport for immediate delivery");

            var sendComponent = new SendComponent(messageMapper);

            return(sendComponent);
        }
Example #9
0
        public static RoutingComponent Initialize(
            Configuration configuration,
            TransportSeam transportSeam,
            ReceiveComponent.Configuration receiveConfiguration,
            Conventions conventions,
            PipelineSettings pipelineSettings)
        {
            var distributionPolicy  = configuration.DistributionPolicy;
            var unicastRoutingTable = configuration.UnicastRoutingTable;
            var endpointInstances   = configuration.EndpointInstances;

            foreach (var distributionStrategy in configuration.CustomDistributionStrategies)
            {
                distributionPolicy.SetDistributionStrategy(distributionStrategy);
            }

            configuration.ConfiguredUnicastRoutes?.Apply(unicastRoutingTable, conventions);

            var isSendOnlyEndpoint = receiveConfiguration.IsSendOnlyEndpoint;

            if (!isSendOnlyEndpoint)
            {
                pipelineSettings.Register(
                    new ApplyReplyToAddressBehavior(
                        receiveConfiguration.LocalAddress,
                        receiveConfiguration.InstanceSpecificQueue,
                        configuration.PublicReturnAddress),
                    "Applies the public reply to address to outgoing messages");
            }

            var sendRouter = new UnicastSendRouter(
                isSendOnlyEndpoint,
                receiveConfiguration?.QueueNameBase,
                receiveConfiguration?.InstanceSpecificQueue,
                distributionPolicy,
                unicastRoutingTable,
                endpointInstances,
                i => transportSeam.TransportDefinition.ToTransportAddress(new QueueAddress(i.Endpoint, i.Discriminator, i.Properties, null)));

            if (configuration.EnforceBestPractices)
            {
                EnableBestPracticeEnforcement(pipelineSettings, new Validations(conventions));
            }

            return(new RoutingComponent(
                       sendRouter,
                       configuration.EnforceBestPractices));
        }
Example #10
0
        public static RoutingComponent Initialize(Configuration configuration,
                                                  TransportComponent.Configuration transportConfiguration,
                                                  ReceiveConfiguration receiveConfiguration,
                                                  Conventions conventions,
                                                  PipelineSettings pipelineSettings)
        {
            var distributionPolicy  = configuration.DistributionPolicy;
            var unicastRoutingTable = configuration.UnicastRoutingTable;
            var endpointInstances   = configuration.EndpointInstances;

            foreach (var distributionStrategy in configuration.DistributionStrategies)
            {
                distributionPolicy.SetDistributionStrategy(distributionStrategy);
            }

            configuration.ConfiguredUnicastRoutes?.Apply(unicastRoutingTable, conventions);

            var isSendOnlyEndpoint = receiveConfiguration == null;

            if (isSendOnlyEndpoint == false)
            {
                pipelineSettings.Register(new ApplyReplyToAddressBehavior(
                                              receiveConfiguration.LocalAddress,
                                              receiveConfiguration.InstanceSpecificQueue,
                                              configuration.PublicReturnAddress),
                                          "Applies the public reply to address to outgoing messages");
            }

            var sendRouter = new UnicastSendRouter(
                isSendOnlyEndpoint,
                receiveConfiguration?.QueueNameBase,
                receiveConfiguration?.InstanceSpecificQueue,
                distributionPolicy,
                unicastRoutingTable,
                endpointInstances,
                i => transportConfiguration.ToTransportAddress(LogicalAddress.CreateRemoteAddress(i)));

            return(new RoutingComponent(
                       unicastRoutingTable,
                       distributionPolicy,
                       endpointInstances,
                       configuration.Publishers,
                       sendRouter,
                       configuration.EnforceBestPractices,
                       new Validations(conventions)));
        }
Example #11
0
        public static ReceiveComponent Configure(
            Configuration configuration,
            string errorQueue,
            HostingComponent.Configuration hostingConfiguration,
            PipelineSettings pipelineSettings)
        {
            if (configuration.IsSendOnlyEndpoint)
            {
                configuration.transportSeam.Configure(new ReceiveSettings[0]);
                return(new ReceiveComponent(configuration));
            }

            var receiveComponent = new ReceiveComponent(configuration);

            pipelineSettings.Register("TransportReceiveToPhysicalMessageProcessingConnector", b =>
            {
                var storage = b.GetService <IOutboxStorage>() ?? new NoOpOutboxStorage();
                return(new TransportReceiveToPhysicalMessageConnector(storage));
            }, "Allows to abort processing the message");

            pipelineSettings.Register("LoadHandlersConnector", b =>
            {
                var adapter     = b.GetService <ISynchronizedStorageAdapter>() ?? new NoOpSynchronizedStorageAdapter();
                var syncStorage = b.GetService <ISynchronizedStorage>() ?? new NoOpSynchronizedStorage();

                return(new LoadHandlersConnector(b.GetRequiredService <MessageHandlerRegistry>(), syncStorage, adapter));
            }, "Gets all the handlers to invoke from the MessageHandler registry based on the message type.");

            pipelineSettings.Register("ExecuteUnitOfWork", new UnitOfWorkBehavior(), "Executes the UoW");

            pipelineSettings.Register("InvokeHandlers", new InvokeHandlerTerminator(), "Calls the IHandleMessages<T>.Handle(T)");

            var handlerDiagnostics = new Dictionary <string, List <string> >();


            var messageHandlerRegistry = configuration.messageHandlerRegistry;

            RegisterMessageHandlers(messageHandlerRegistry, configuration.ExecuteTheseHandlersFirst, hostingConfiguration.Services, hostingConfiguration.AvailableTypes);

            foreach (var messageType in messageHandlerRegistry.GetMessageTypes())
            {
                handlerDiagnostics[messageType.FullName] = messageHandlerRegistry.GetHandlersFor(messageType)
                                                           .Select(handler => handler.HandlerType.FullName)
                                                           .ToList();
            }

            var receiveSettings = new List <ReceiveSettings>
            {
                new ReceiveSettings(
                    MainReceiverId,
                    configuration.LocalAddress,
                    configuration.transportSeam.TransportDefinition.SupportsPublishSubscribe,
                    configuration.PurgeOnStartup,
                    errorQueue)
            };


            if (!string.IsNullOrWhiteSpace(configuration.InstanceSpecificQueue))
            {
                receiveSettings.Add(new ReceiveSettings(
                                        InstanceSpecificReceiverId,
                                        configuration.InstanceSpecificQueue,
                                        false,
                                        configuration.PurgeOnStartup,
                                        errorQueue));
            }

            receiveSettings.AddRange(configuration.SatelliteDefinitions.Select(definition => new ReceiveSettings(
                                                                                   definition.Name,
                                                                                   definition.ReceiveAddress,
                                                                                   false,
                                                                                   configuration.PurgeOnStartup,
                                                                                   errorQueue)));

            hostingConfiguration.Services.ConfigureComponent(() => receiveComponent.mainReceiverSubscriptionManager, DependencyLifecycle.SingleInstance);
            // get a reference to the subscription manager as soon as the transport has been created:
            configuration.transportSeam.TransportInfrastructureCreated += (_, infrastructure) =>
                                                                          receiveComponent.mainReceiverSubscriptionManager =
                infrastructure.Receivers[MainReceiverId].Subscriptions;

            configuration.transportSeam.Configure(receiveSettings.ToArray());

            hostingConfiguration.AddStartupDiagnosticsSection("Receiving", new
            {
                configuration.LocalAddress,
                configuration.InstanceSpecificQueue,
                configuration.PurgeOnStartup,
                configuration.QueueNameBase,
                TransactionMode = configuration.transportSeam.TransportDefinition.TransportTransactionMode.ToString("G"),
                configuration.PushRuntimeSettings.MaxConcurrency,
                Satellites = configuration.SatelliteDefinitions.Select(s => new
                {
                    s.Name,
                    s.ReceiveAddress,
                    s.RuntimeSettings.MaxConcurrency
                }).ToArray(),
                MessageHandlers = handlerDiagnostics
            });

            return(receiveComponent);
        }
        public static ReceiveComponent Initialize(
            Configuration configuration,
            string errorQueue,
            HostingComponent.Configuration hostingConfiguration,
            PipelineSettings pipelineSettings)
        {
            TransportReceiveInfrastructure transportReceiveInfrastructure = null;

            if (!configuration.IsSendOnlyEndpoint)
            {
                transportReceiveInfrastructure = configuration.transportSeam.TransportInfrastructure.ConfigureReceiveInfrastructure();

                if (configuration.CreateQueues)
                {
                    hostingConfiguration.AddInstaller(identity =>
                    {
                        var queueCreator = transportReceiveInfrastructure.QueueCreatorFactory();
                        return(queueCreator.CreateQueueIfNecessary(configuration.transportSeam.QueueBindings, identity));
                    });
                }
            }

            var receiveComponent = new ReceiveComponent(
                configuration,
                hostingConfiguration.CriticalError,
                errorQueue,
                transportReceiveInfrastructure);

            if (configuration.IsSendOnlyEndpoint)
            {
                return(receiveComponent);
            }

            receiveComponent.BindQueues(configuration.transportSeam.QueueBindings);

            pipelineSettings.Register("TransportReceiveToPhysicalMessageProcessingConnector", b =>
            {
                var storage = hostingConfiguration.Container.HasComponent <IOutboxStorage>() ? b.Build <IOutboxStorage>() : new NoOpOutboxStorage();
                return(new TransportReceiveToPhysicalMessageConnector(storage));
            }, "Allows to abort processing the message");

            pipelineSettings.Register("LoadHandlersConnector", b =>
            {
                var adapter     = hostingConfiguration.Container.HasComponent <ISynchronizedStorageAdapter>() ? b.Build <ISynchronizedStorageAdapter>() : new NoOpSynchronizedStorageAdapter();
                var syncStorage = hostingConfiguration.Container.HasComponent <ISynchronizedStorage>() ? b.Build <ISynchronizedStorage>() : new NoOpSynchronizedStorage();

                return(new LoadHandlersConnector(b.Build <MessageHandlerRegistry>(), syncStorage, adapter));
            }, "Gets all the handlers to invoke from the MessageHandler registry based on the message type.");

            pipelineSettings.Register("ExecuteUnitOfWork", new UnitOfWorkBehavior(), "Executes the UoW");

            pipelineSettings.Register("InvokeHandlers", new InvokeHandlerTerminator(), "Calls the IHandleMessages<T>.Handle(T)");

            var externalHandlerRegistryUsed = hostingConfiguration.Container.HasComponent <MessageHandlerRegistry>();
            var handlerDiagnostics          = new Dictionary <string, List <string> >();

            if (!externalHandlerRegistryUsed)
            {
                var messageHandlerRegistry = configuration.messageHandlerRegistry;

                RegisterMessageHandlers(messageHandlerRegistry, configuration.ExecuteTheseHandlersFirst, hostingConfiguration.Container, hostingConfiguration.AvailableTypes);

                foreach (var messageType in messageHandlerRegistry.GetMessageTypes())
                {
                    handlerDiagnostics[messageType.FullName] = messageHandlerRegistry.GetHandlersFor(messageType)
                                                               .Select(handler => handler.HandlerType.FullName)
                                                               .ToList();
                }
            }

            hostingConfiguration.AddStartupDiagnosticsSection("Receiving", new
            {
                configuration.LocalAddress,
                configuration.InstanceSpecificQueue,
                configuration.LogicalAddress,
                configuration.PurgeOnStartup,
                configuration.QueueNameBase,
                TransactionMode = configuration.TransactionMode.ToString("G"),
                configuration.PushRuntimeSettings.MaxConcurrency,
                Satellites = configuration.SatelliteDefinitions.Select(s => new
                {
                    s.Name,
                    s.ReceiveAddress,
                    TransactionMode = s.RequiredTransportTransactionMode.ToString("G"),
                    s.RuntimeSettings.MaxConcurrency
                }).ToArray(),
                ExternalHandlerRegistry = externalHandlerRegistryUsed,
                MessageHandlers         = handlerDiagnostics
            });

            return(receiveComponent);
        }
        protected override void Setup(FeatureConfigurationContext context)
        {
            PipelineSettings satelliteMessagePipeline = context.AddSatellitePipeline("CustomSatellite", TransportTransactionMode.TransactionScope, PushRuntimeSettings.Default, "targetQueue");

            satelliteMessagePipeline.Register("Satellite Identifier", new MySatelliteBehavior(), "Description of what the satellite does");
        }
Example #14
0
        public static ReceiveComponent Initialize(Configuration configuration,
                                                  ReceiveConfiguration transportReceiveConfiguration,
                                                  TransportComponent.Configuration transportConfiguration,
                                                  PipelineComponent pipelineComponent,
                                                  string errorQueue,
                                                  HostingComponent.Configuration hostingConfiguration,
                                                  PipelineSettings pipelineSettings)

        {
            var receiveComponent = new ReceiveComponent(transportReceiveConfiguration,
                                                        pipelineComponent,
                                                        hostingConfiguration.CriticalError,
                                                        errorQueue);

            receiveComponent.BindQueues(transportConfiguration.QueueBindings);

            pipelineSettings.Register("TransportReceiveToPhysicalMessageProcessingConnector", b =>
            {
                var storage = hostingConfiguration.Container.HasComponent <IOutboxStorage>() ? b.Build <IOutboxStorage>() : new NoOpOutboxStorage();
                return(new TransportReceiveToPhysicalMessageConnector(storage));
            }, "Allows to abort processing the message");

            pipelineSettings.Register("LoadHandlersConnector", b =>
            {
                var adapter     = hostingConfiguration.Container.HasComponent <ISynchronizedStorageAdapter>() ? b.Build <ISynchronizedStorageAdapter>() : new NoOpSynchronizedStorageAdapter();
                var syncStorage = hostingConfiguration.Container.HasComponent <ISynchronizedStorage>() ? b.Build <ISynchronizedStorage>() : new NoOpSynchronizedStorage();

                return(new LoadHandlersConnector(b.Build <MessageHandlerRegistry>(), syncStorage, adapter));
            }, "Gets all the handlers to invoke from the MessageHandler registry based on the message type.");

            pipelineSettings.Register("ExecuteUnitOfWork", new UnitOfWorkBehavior(), "Executes the UoW");

            pipelineSettings.Register("InvokeHandlers", new InvokeHandlerTerminator(), "Calls the IHandleMessages<T>.Handle(T)");

            if (!hostingConfiguration.Container.HasComponent <MessageHandlerRegistry>())
            {
                var orderedHandlers = configuration.ExecuteTheseHandlersFirst;

                LoadMessageHandlers(configuration, orderedHandlers, hostingConfiguration.Container, hostingConfiguration.AvailableTypes);
            }

            if (transportReceiveConfiguration != null)
            {
                hostingConfiguration.AddStartupDiagnosticsSection("Receiving", new
                {
                    transportReceiveConfiguration.LocalAddress,
                    transportReceiveConfiguration.InstanceSpecificQueue,
                    transportReceiveConfiguration.LogicalAddress,
                    transportReceiveConfiguration.PurgeOnStartup,
                    transportReceiveConfiguration.QueueNameBase,
                    TransactionMode = transportReceiveConfiguration.TransactionMode.ToString("G"),
                    transportReceiveConfiguration.PushRuntimeSettings.MaxConcurrency,
                    Satellites = transportReceiveConfiguration.SatelliteDefinitions.Select(s => new
                    {
                        s.Name,
                        s.ReceiveAddress,
                        TransactionMode = s.RequiredTransportTransactionMode.ToString("G"),
                        s.RuntimeSettings.MaxConcurrency
                    }).ToArray()
                });
            }

            return(receiveComponent);
        }