Example #1
0
        public async Task <FtpClientResponse> ReadAsync(FtpConfig config, Func <string, Task <string> > securePasswordCallBack,
                                                        Func <string, string, string, MemoryStream, string, string, bool> copyFileFunc)
        {
            var response = new FtpClientResponse {
                ErrorMessage = FtpConstants.NoError, Status = FtpConstants.SuccessStatus, FileData = new List <FtpClientResponseFile>()
            };

            try
            {
                await CreateFtpClientAsync(config, securePasswordCallBack);

                Func <FtpListItem, bool> predicate = f => f.Type == FtpFileSystemObjectType.File;
                if (!string.IsNullOrEmpty(config.Ftp.FilenameRegex))
                {
                    var rx = new Regex(config.Ftp.FilenameRegex, RegexOptions.IgnoreCase);
                    predicate = f => f.Type == FtpFileSystemObjectType.File && rx.IsMatch(f.Name);
                }

                var listOfFiles = _ftpPolicyRegistry.GetPolicy(FtpPolicyName.FtpCommandPolicy)
                                  .Execute((context) => _ftpClient.GetListing(config.Ftp.Path).Where(predicate), new Polly.Context($"LIST_FILE_{config.Ftp.Path}"));

                if (!string.IsNullOrEmpty(config.Ftp.ArchivedPath) && config.Ftp.ArchivedPath != config.Ftp.Path)
                {
                    var folderExisted = _ftpClient.DirectoryExists(config.Ftp.ArchivedPath);
                    if (!folderExisted)
                    {
                        _ftpPolicyRegistry.GetPolicy(FtpPolicyName.FtpCommandPolicy).Execute((context) => _ftpClient.CreateDirectory(config.Ftp.ArchivedPath), new Polly.Context("CREATE_ARCHIVE_FOLDER"));
                    }
                }

                var resolvedStorageAccountKey =
                    await securePasswordCallBack.Invoke(config.AzureBlobStorage.StorageKeyVault);

                foreach (var item in listOfFiles)
                {
                    bool copied     = false;
                    bool isArchived = false;
                    try
                    {
                        var fileName = item.Name;
                        using (var istream = await _ftpClient.OpenReadAsync(item.FullName))
                        {
                            MemoryStream memoryStream = new MemoryStream();
                            istream.CopyTo(memoryStream);
                            memoryStream.Position = 0;
                            copied = copyFileFunc.Invoke(config.AzureBlobStorage.ContainerName,
                                                         fileName,
                                                         config.Retry.StorageRetryPolicy, memoryStream, config.AzureBlobStorage.StorageAccountName, resolvedStorageAccountKey);
                        }
                        if (copied && !string.IsNullOrEmpty(config.Ftp.ArchivedPath) && config.Ftp.ArchivedPath != config.Ftp.Path)
                        {
                            isArchived = _ftpPolicyRegistry.GetPolicy(FtpPolicyName.FtpCommandPolicy).Execute((context) => _ftpClient.MoveFile(item.FullName, config.Ftp.ArchivedPath + "\\" + item.Name, FtpExists.Overwrite), new Polly.Context("COPY_FILE_TO_ARCHIVE"));
                        }
                        else if (config.Ftp.ArchivedPath == config.Ftp.Path)
                        {
                            //delete mode
                            isArchived = _ftpPolicyRegistry.GetPolicy(FtpPolicyName.FtpCommandPolicy).Execute((context) =>
                            {
                                _ftpClient.DeleteFile(item.FullName);
                                return(true);
                            }, new Polly.Context("DELETE_FILE_TO_ARCHIVE"));
                        }

                        var fres = new FtpClientResponseFile
                        {
                            Status       = (copied && isArchived) ? FtpConstants.SuccessStatus : FtpConstants.FailureStatus,
                            FileName     = item.Name,
                            ErrorMessage = (copied ? string.Empty : FtpConstants.BlobUploadError) + " " + (isArchived ? string.Empty : FtpConstants.ArchivedError)
                        };
                        response.FileData.Add(fres);
                    }
                    catch (Exception ex)
                    {
                        _logger.LogError(ex, $"ActorFtpClient failed to process the file {item.Name}, copy: {copied}, archived {isArchived}. Error: {ex.Message}");
                    }
                }
                await Stop();
            }
            catch (Exception e)
            {
                response.ErrorMessage = response.ErrorMessage + e.Message;
                response.Status       = FtpConstants.FailureStatus;
                _logger.LogError(e, $"ActorFtpClient failed to start creating the client of {config.Ftp.Host} : {e.Message}");
            }
            return(response);
        }