예제 #1
0
 public async Task RingMyself()
 {
     var message = new DoorbellMessage()
     {
         ProcessId = processId,
         Guid      = Guid.NewGuid()
     };
     var messageBytes = DoorbellMessage.Serialize(message);
     var sender       = Connections.GetDoorbellSender(processId);
     await sender.SendAsync(new EventData(messageBytes));
 }
예제 #2
0
        public static byte[] Serialize(DoorbellMessage message)
        {
            MemoryStream stream = new MemoryStream();

            using (var binaryDictionaryWriter = XmlDictionaryWriter.CreateBinaryWriter(stream))
            {
                Serializer.WriteObject(binaryDictionaryWriter, message);
                stream.Flush();
            }
            return(stream.ToArray());
        }
예제 #3
0
        protected override async Task Send(List <IMessage> toSend)
        {
            // serialize payload

            MemoryStream stream = new MemoryStream();

            using (var binaryDictionaryWriter = XmlDictionaryWriter.CreateBinaryWriter(stream))
            {
                payloadSerializer.WriteObject(binaryDictionaryWriter, toSend);
                stream.Flush();
            }

            var now = DateTime.UtcNow;

            // send message

            var message = new ProcessMessage()
            {
                DeploymentTimestamp = default(DateTime),
                Source    = processId,
                LastClock = null,
                Payload   = stream.ToArray()
            };

            var messageBytes = ProcessMessage.Serialize(message);

            await sender.SendAsync(new EventData(messageBytes));

            logger.LogTrace($"{DateTime.UtcNow:o} Sent {message}->{destination} ({messageBytes.Length / 1024}kB)");

            if (lastSendOrDoorbell + configuration.ReceiveWaitTime < now)
            {
                // send doorbell message
                var doorbellMessage = new DoorbellMessage()
                {
                    ProcessId = destination,
                    Guid      = Guid.NewGuid()
                };
                var doorbell = connections.GetDoorbellSender(destination);
                await doorbell.SendAsync(new EventData(DoorbellMessage.Serialize(doorbellMessage)));

                logger.LogTrace($"{DateTime.UtcNow:o} Sent {doorbellMessage}");
            }

            lastSendOrDoorbell = now;
        }
예제 #4
0
        public static async Task Doorbell(Microsoft.Azure.WebJobs.ExecutionContext executionContext, ILogger logger, EventData[] messages)
        {
            var stopwatch = new System.Diagnostics.Stopwatch();

            stopwatch.Start();

            var msg = DoorbellMessage.Deserialize(messages[0].Body.Array);

            var processId = msg.ProcessId;

            var applicationInfo = new TStaticApplicationInfo();

            var configuration = applicationInfo.GetHostConfiguration();

            var hostlogger = new LoggerWrapper(logger, $"[p{processId:d3} doorbell] ");

            var lastRing = messages[messages.Length - 1].SystemProperties.SequenceNumber;


            try
            {
                var cloudBlobContainer = await AzureBlobStorageStateManager.GetCloudBlobContainer(configuration.StorageConnectionString, hostlogger);

                var stateBlob = cloudBlobContainer.GetBlockBlobReference(AzureBlobStorageStateManager.BlobName(processId));

                var leaseManager = new LeaseManager(stateBlob);

                if (await leaseManager.TryGetLease(hostlogger))
                {
                    hostlogger.LogInformation($"{DateTime.UtcNow:o} Rings x{messages.Length} on {Environment.MachineName}, through #{lastRing}, lease acquired");
                    await RunHost(applicationInfo, configuration, processId, hostlogger, logger, leaseManager, stopwatch, executionContext.InvocationId);
                }
                else
                {
                    hostlogger.LogInformation($"{DateTime.UtcNow:o} Rings x{messages.Length} on {Environment.MachineName}, through #{lastRing}, ignored");
                }
            }
            catch (Exception e)
            {
                hostlogger.LogError($"Doorbell failed: {e}");
            }
        }
예제 #5
0
        public static async Task <string> InitializeService(Microsoft.Azure.WebJobs.ExecutionContext executionContext, ILogger logger)
        {
            var stopwatch = new System.Diagnostics.Stopwatch();

            stopwatch.Start();

            var applicationInfo = new TStaticApplicationInfo();

            logger = new LoggerWrapper(logger, "[initialize] ");

            try
            {
                var configuration = applicationInfo.GetHostConfiguration();

                var host = new Host <TStaticApplicationInfo>(applicationInfo, configuration, logger, 0, stopwatch, executionContext.InvocationId);

                var deploymentTimestamp = DateTime.UtcNow;
                var deploymentId        = applicationInfo.GetDeploymentId(deploymentTimestamp);
                host.SetDeploymentTimestamp(deploymentTimestamp);

                // generate blobs
                var cloudBlobContainer = await AzureBlobStorageStateManager.GetCloudBlobContainer(
                    storageConnectionString : configuration.StorageConnectionString,
                    logger : logger,
                    initialize : true
                    );

                // check the current position in all the queues, and start from there
                var initTasks = new List <Task>();
                for (uint i = 0; i < host.NumberProcesses; i++)
                {
                    StartTask(initTasks, async() =>
                    {
                        uint processId   = i;
                        var lastEnqueued = await host.GetLastEnqueuedSequenceNumber(processId);
                        await AzureBlobStorageStateManager.Save(
                            cloudBlobContainer,
                            deploymentId,
                            logger,
                            processId,
                            new ProcessState(deploymentTimestamp, lastEnqueued));
                    });
                }
                await Task.WhenAll(initTasks);

                // send ping message to process 0
                var guid    = Guid.NewGuid();
                var message = new DoorbellMessage()
                {
                    ProcessId = 0,
                    Guid      = guid
                };
                var messageBytes = DoorbellMessage.Serialize(message);
                await host.Connections.GetDoorbellSender(0).SendAsync(new EventData(messageBytes));

                await host.Cleanup(true);

                return(deploymentId);
            }
            catch (Exception e)
            {
                logger.LogError($"Initialize failed: {e}");
                throw;
            }
        }