Implements an asynchronous transmission of data to an HTTP POST endpoint.
 /// <summary>
 /// Saves the transmission to the specified <paramref name="stream"/>.
 /// </summary>
 internal static async Task SaveAsync(Transmission transmission, Stream stream)
 {
     var writer = new StreamWriter(stream);
     try
     {
         await writer.WriteLineAsync(transmission.EndpointAddress.ToString()).ConfigureAwait(false);
         await writer.WriteLineAsync(Transmission.ContentTypeHeader + ":" + transmission.ContentType).ConfigureAwait(false);
         await writer.WriteLineAsync(Transmission.ContentEncodingHeader + ":" + transmission.ContentEncoding).ConfigureAwait(false);
         await writer.WriteLineAsync(string.Empty).ConfigureAwait(false);
         await writer.WriteAsync(Convert.ToBase64String(transmission.Content)).ConfigureAwait(false);
     }
     finally
     {
         writer.Flush();
     }
 }
예제 #2
0
 private static async Task SaveTransmissionToFileAsync(Transmission transmission, string fileFullName)
 {
     try
     {
         using (Stream stream = File.OpenWrite(fileFullName))
         {
             await StorageTransmission.SaveAsync(transmission, stream).ConfigureAwait(false);
         }
     }
     catch (UnauthorizedAccessException)
     {
         string message = string.Format("Failed to save transmission to file. UnauthorizedAccessException. File full path: {0}", fileFullName);
         CoreEventSource.Log.LogVerbose(message);
         throw;
     }
 }
예제 #3
0
        internal override async Task EnqueueAsync(Transmission transmission)
        {   
            try
            {
                if (this.StorageFolder == null)
                {
                    return;
                }

                if (transmission == null)
                {
                    CoreEventSource.Log.LogVerbose("transmission is null. EnqueueAsync is skipped");
                    return;
                }

                if (this.IsStorageLimitsReached())
                {
                    // if max storage capacity has reached, drop the transmission (but log every 100 lost transmissions). 
                    if (Interlocked.Increment(ref this.transmissionsDropped) % 100 == 0)
                    {
                        CoreEventSource.Log.LogVerbose("Total transmissions dropped: " + this.transmissionsDropped);
                    }

                    return;
                }

                // Write content to a temporaty file and only then rename to avoid the Peek method from reading the file before it is being written.
                // Creates the temp file name
                string tempFileName = Guid.NewGuid().ToString("N");
                string tempFullFilePath = Path.Combine(this.StorageFolder.FullName, tempFileName + ".tmp");

                // Saves tranmission to file
                await SaveTransmissionToFileAsync(transmission, tempFullFilePath).ConfigureAwait(false);

                // Creates a new file name
                string now = DateTime.UtcNow.ToString("yyyyMMddHHmmss");
                string newFileName = string.Format(CultureInfo.InvariantCulture, "{0}_{1}.trn", now, tempFileName);
                string newFillFilePath = Path.Combine(this.StorageFolder.FullName, newFileName);

                // Renames the file
                File.Move(tempFullFilePath, newFillFilePath);
            }
            catch (Exception e)
            {
                CoreEventSource.Log.LogVerbose(string.Format(CultureInfo.InvariantCulture, "EnqueueAsync: Exception: {0}", e));
            }
        }
예제 #4
0
        /// <summary>
        /// Persist the in-memory telemetry items.
        /// </summary>
        internal void Flush()
        {
            IEnumerable<ITelemetry> telemetryItems = this.telemetryBuffer.Dequeue();

            if (telemetryItems != null && telemetryItems.Any())
            {
                byte[] data = JsonSerializer.Serialize(telemetryItems);
                var transmission = new Transmission(
                    this.EndpointAddress,
                    data,
                    "application/x-json-stream",
                    JsonSerializer.CompressionType);

                this.storage.EnqueueAsync(transmission).ConfigureAwait(false).GetAwaiter().GetResult();
            }
        }
 internal override Task EnqueueAsync(Transmission transmission)
 {
     storage.Add(transmission);
     return Task.CompletedTask;
 }
        /// <summary>
        /// Sending the item to the endpoint immediately without persistence.
        /// </summary>
        /// <param name="item">Telemetry item.</param>
        /// <param name="endpointAddress">Server endpoint address.</param>
        internal void SendForDeveloperMode(ITelemetry item, string endpointAddress)
        {
            try
            {
                byte[] data = JsonSerializer.Serialize(item);
                var transmission = new Transmission(new Uri(endpointAddress), data, "application/x-json-stream", JsonSerializer.CompressionType);

                transmission.SendAsync().ConfigureAwait(false).GetAwaiter().GetResult();
            }
            catch (Exception exception)
            {
                CoreEventSource.Log.LogVerbose("Failed sending event in developer mode Exception:" + exception);
            }
        }
        /// <summary>
        /// Serializes a list of telemetry items and sends them.
        /// </summary>
        private async Task Send(IEnumerable<ITelemetry> telemetryItems)
        {
            if (telemetryItems == null || !telemetryItems.Any())
            {
                CoreEventSource.Log.LogVerbose("No Telemetry Items passed to Enqueue");
                return;
            }

            byte[] data = JsonSerializer.Serialize(telemetryItems);
            var transmission = new Transmission(this.endpointAddress, data, "application/x-json-stream", JsonSerializer.CompressionType);

            await transmission.SendAsync().ConfigureAwait(false);
        }