예제 #1
0
파일: Sender.cs 프로젝트: jokm1/uno-2
        /// <summary>
        ///     Send transmissions in a loop.
        /// </summary>
        protected void SendLoop()
        {
            TimeSpan prevSendingInterval = TimeSpan.Zero;
            TimeSpan sendingInterval     = _sendingIntervalOnNoData;

            try
            {
                while (!_stopped)
                {
                    using (StorageTransmission transmission = _storage.Peek())
                    {
                        if (_stopped)
                        {
                            // This second verification is required for cases where 'stopped' was set while peek was happening.
                            // Once the actual sending starts the design is to wait until it finishes and deletes the transmission.
                            // So no extra validation is required.
                            break;
                        }

                        // If there is a transmission to send - send it.
                        if (transmission != null)
                        {
                            bool shouldRetry = Send(transmission, ref sendingInterval);
                            if (!shouldRetry)
                            {
                                // If retry is not required - delete the transmission.
                                _storage.Delete(transmission);
                            }
                        }
                        else
                        {
                            sendingInterval = _sendingIntervalOnNoData;
                        }
                    }

                    LogInterval(prevSendingInterval, sendingInterval);
                    DelayHandler.WaitOne(sendingInterval);
                    prevSendingInterval = sendingInterval;
                }

                _stoppedHandler.Set();
            }
            catch (ObjectDisposedException)
            {
            }
        }
예제 #2
0
 private async Task SaveTransmissionToFileAsync(Transmission transmission, string file)
 {
     try
     {
         using (Stream stream = File.OpenWrite(Path.Combine(StorageFolder, file)))
         {
             await StorageTransmission.SaveAsync(transmission, stream).ConfigureAwait(false);
         }
     }
     catch (UnauthorizedAccessException)
     {
         string message =
             string.Format(
                 "Failed to save transmission to file. UnauthorizedAccessException. File path: {0}, FileName: {1}",
                 StorageFolder, file);
         PersistenceChannelDebugLog.WriteLine(message);
         throw;
     }
 }
예제 #3
0
        private async Task <StorageTransmission> LoadTransmissionFromFileAsync(string file)
        {
            try
            {
                using (Stream stream = File.OpenRead(Path.Combine(StorageFolder, file)))
                {
                    StorageTransmission storageTransmissionItem =
                        await StorageTransmission.CreateFromStreamAsync(stream, file).ConfigureAwait(false);

                    return(storageTransmissionItem);
                }
            }
            catch (Exception e)
            {
                string message =
                    string.Format(
                        "Failed to load transmission from file. File path: {0}, FileName: {1}, Exception: {2}",
                        "storageFolderName", file, e);
                PersistenceChannelDebugLog.WriteLine(message);
                throw;
            }
        }
예제 #4
0
        /// <summary>
        ///     Reads an item from the storage. Order is Last-In-First-Out.
        ///     When the Transmission is no longer needed (it was either sent or failed with a non-retryable error) it should be
        ///     disposed.
        /// </summary>
        internal override StorageTransmission Peek()
        {
            IEnumerable <string> files = GetFiles("*.trn", 50);

            lock (_peekLockObj)
            {
                foreach (string file in files)
                {
                    try
                    {
                        // if a file was peeked before, skip it (wait until it is disposed).
                        if (PeekedTransmissions.ContainsKey(file) == false &&
                            _deletedFilesQueue.Contains(file) == false)
                        {
                            // Load the transmission from disk.
                            StorageTransmission storageTransmissionItem = LoadTransmissionFromFileAsync(file)
                                                                          .ConfigureAwait(false).GetAwaiter().GetResult();

                            // when item is disposed it should be removed from the peeked list.
                            storageTransmissionItem.Disposing = item => OnPeekedItemDisposed(file);

                            // add the transmission to the list.
                            PeekedTransmissions.Add(file, storageTransmissionItem.FullFilePath);
                            return(storageTransmissionItem);
                        }
                    }
                    catch (Exception e)
                    {
                        PersistenceChannelDebugLog.WriteException(
                            e,
                            "Failed to load an item from the storage. file: {0}",
                            file);
                    }
                }
            }

            return(null);
        }
예제 #5
0
파일: Sender.cs 프로젝트: jokm1/uno-2
        /// <summary>
        ///     Sends a transmission and handle errors.
        /// </summary>
        /// <param name="transmission">The transmission to send.</param>
        /// <param name="nextSendInterval">
        ///     When this value returns it will hold a recommendation for when to start the next sending
        ///     iteration.
        /// </param>
        /// <returns>True, if there was sent error and we need to retry sending, otherwise false.</returns>
        protected virtual bool Send(StorageTransmission transmission, ref TimeSpan nextSendInterval)
        {
            try
            {
                if (transmission != null)
                {
                    bool isConnected = NetworkInterface.GetIsNetworkAvailable();

                    // there is no internet connection available, return than.
                    if (!isConnected)
                    {
                        PersistenceChannelDebugLog.WriteLine(
                            "Cannot send data to the server. Internet connection is not available");
                        return(true);
                    }

                    transmission.SendAsync().ConfigureAwait(false).GetAwaiter().GetResult();

                    // After a successful sending, try immediately to send another transmission.
                    nextSendInterval = SendingInterval;
                }
            }
            catch (WebException e)
            {
                int?statusCode = GetStatusCode(e);
                nextSendInterval = CalculateNextInterval(statusCode, nextSendInterval, _maxIntervalBetweenRetries);
                return(IsRetryable(statusCode, e.Status));
            }
            catch (Exception e)
            {
                nextSendInterval = CalculateNextInterval(null, nextSendInterval, _maxIntervalBetweenRetries);
                PersistenceChannelDebugLog.WriteException(e, "Unknown exception during sending");
            }

            return(false);
        }
예제 #6
0
 internal abstract void Delete(StorageTransmission transmission);