[C#] FluentFTP 샘플 프로그램 작성 (클린 아키텍처 적용)
- C#
- 2022. 5. 3. 21:08
목적
- FluentFTP 를 이용한 간단한 FTP 프로그램을 Clean Architecture 측면으로 샘플 프로젝트 작성 진행합니다.
- FTP 라이브러리는 추후에 바뀔 수 있으나, 샘플 프로젝트에서는
FluentFTP
NuGet Package 를 이용하였습니다.
프로젝트 구조
- 프로젝트 구조는 다음과 같습니다.
- 위와 같이 프로젝트 구조를 나눴습니다.
Application 폴더
- Application 폴더 안에 있는 클래스들 코드는 다음과 같습니다.
IFTPManager.cs
IFTPManager
인터페이스에는 크게 DownLoad, Upload, Delete, GetFiles 메서드를 정의하였습니다.
using FtpManager.Domain;
namespace FtpManager.Application
{
public interface IFTPManager
{
public bool DownLoad(string sourcePath, string targetPath);
public bool UpLoad(string sourcePath, string targetPath);
public bool Delete(string targetPath);
public FtpFiles GetFiles(string directory);
}
}
Common 폴더
- Commmon 폴더에는 프로젝트 공통으로 쓰이는 클래스들을 모아둡니다.
- 여기서는
ValueObject.cs
클래스가 있습니다.
ValueObject.cs
ValueObject.cs
클래스는 값객체 역할을 나타내는 클래스 입니다.
namespace FtpManager.Common
{
public abstract class ValueObject
{
protected static bool EqualOperator(ValueObject left, ValueObject right)
{
if (ReferenceEquals(left, null) ^ ReferenceEquals(right, null))
{
return false;
}
return ReferenceEquals(left, null) || left.Equals(right);
}
protected static bool NotEqualOperator(ValueObject left, ValueObject right)
{
return !(EqualOperator(left, right));
}
protected abstract IEnumerable<object> GetEqualityComponents();
public override bool Equals(object obj)
{
if (obj == null || obj.GetType() != GetType())
{
return false;
}
var other = (ValueObject)obj;
return this.GetEqualityComponents().SequenceEqual(other.GetEqualityComponents());
}
public override int GetHashCode()
{
return GetEqualityComponents()
.Select(x => x != null ? x.GetHashCode() : 0)
.Aggregate((x, y) => x ^ y);
}
public ValueObject GetCopy()
{
return this.MemberwiseClone() as ValueObject;
}
}
}
Domain 폴더
- 도메인 역할을 하는 클래스들이 있습니다.
- 여기서는
FtpConnectionInfo.cs
,FtpFiles.cs
,FtpProtocolEnum.cs
3개의 도메인 클래스가 있습니다.
FtpConnectionInfo.cs
using FtpManager.FtpConnectionInformation;
namespace FtpManager.Domain
{
public class FtpConnectionInfo
{
public FtpIp FtpIp { get; private set; }
public FtpPassword FtpPassword { get; private set; }
public FtpUser FtpUser { get; private set; }
public FtpHomeAddress HomeAddress { get; private set; }
public FtpProtocol FtpProtocol { get; private set; }
public FtpConnectionInfo(
FtpIp ftpIp,
FtpPassword ftpPassword,
FtpUser ftpUser,
FtpHomeAddress ftpHomeAddress,
FtpProtocol ftpProtocol)
{
FtpIp = ftpIp;
FtpPassword = ftpPassword;
FtpUser = ftpUser;
HomeAddress = ftpHomeAddress;
FtpProtocol = ftpProtocol;
}
}
}
FtpFiles.cs
using FtpManager.FtpConnectionValueObject;
namespace FtpManager.Domain
{
public class FtpFiles
{
private List<FtpFile> _files = new();
public void AddFile(FtpFile file)
{
_files.Add(file);
}
public List<FtpFile> GetFiles()
{
return _files;
}
}
}
FtpProtocolEnum.cs
namespace FtpManager.Domain
{
public enum FtpProtocol
{
FTP = 0,
SFTP = 1
}
}
FtpConnectionValueObject 폴더
- 다음은 ValueObject 역할을 하는 클래스들이 모여있는
FtpConnectionValueObject 폴더
입니다. - 여기에는 Ftp 접속에 필요한 IP, Password, User 등의 값객체 역할을 하는 클래스들이 있습니다.
FtpFile.cs
using FtpManager.Common;
namespace FtpManager.FtpConnectionValueObject
{
public class FtpFile : ValueObject
{
public string File { get; set; }
public FtpFile(string file)
{
File = file;
}
protected override IEnumerable<object> GetEqualityComponents()
{
yield return File;
}
}
}
FtpHomeAddress.cs
using FtpManager.Common;
namespace FtpManager.FtpConnectionInformation
{
public class FtpHomeAddress : ValueObject
{
public string HomeAddress { get; set; }
public FtpHomeAddress(string homeAddress)
{
HomeAddress = homeAddress;
}
protected override IEnumerable<object> GetEqualityComponents()
{
yield return HomeAddress;
}
}
}
FtpIp.cs
using FtpManager.Common;
namespace FtpManager.FtpConnectionInformation
{
public class FtpIp : ValueObject
{
public string Ip { get; set; }
public FtpIp(string ip)
{
Ip = ip;
}
protected override IEnumerable<object> GetEqualityComponents()
{
yield return Ip;
}
}
}
FtpPassword.cs
using FtpManager.Common;
namespace FtpManager.FtpConnectionInformation
{
public class FtpPassword : ValueObject
{
public string Password { get; set; }
public FtpPassword(string password)
{
Password = password;
}
protected override IEnumerable<object> GetEqualityComponents()
{
yield return Password;
}
}
}
FtpUser.cs
using FtpManager.Common;
namespace FtpManager.FtpConnectionInformation
{
public class FtpUser : ValueObject
{
public string User { get; set; }
public FtpUser(string user)
{
User = user;
}
protected override IEnumerable<object> GetEqualityComponents()
{
yield return User;
}
}
}
Service 폴더
- Service 폴더 안에는 실제
IFTPManager
인터페이스를 상속받아 각종 FTP 메서드를 구현하는 구현체 클래스가 있습니다.
FluentFtpTransfer.cs
- 현재 샘플 프로젝트에서는
FluentFtp
NuGet Package 를 설치하여 FluentFtp 로 FTP 관련 메서드들을 작성하였습니다.
using FluentFTP;
using FtpManager.Application;
using FtpManager.Domain;
using FtpManager.FtpConnectionValueObject;
namespace FtpManager
{
public class FluentFtpTransfer : IFTPManager
{
readonly FtpClient ftpClient = null!;
public FluentFtpTransfer(FtpConnectionInfo connectionInfo)
{
using var ftpClient = new FtpClient(connectionInfo.FtpIp.Ip, connectionInfo.FtpUser.User, connectionInfo.FtpPassword.Password);
ftpClient.AutoConnect();
}
public bool DownLoad(string sourcePath, string targetPath)
{
if(ftpClient.DownloadFile(sourcePath, targetPath) == FtpStatus.Success)
{
return true;
}
else
{
return false;
}
}
public FtpFiles GetFiles(string directory)
{
FtpFiles files = new();
FtpListItem[] fileList = ftpClient.GetListing(directory, FtpListOption.AllFiles)
.Where(x => x.Type == FtpFileSystemObjectType.File)
.OrderBy(x => x.Modified)
.ToArray();
foreach (FtpListItem item in fileList)
{
FtpFile file = new(item.Name);
files.AddFile(file);
}
return files;
}
public bool Delete(string targetPath)
{
ftpClient.DeleteFile(targetPath);
return true;
}
public bool UpLoad(string sourcePath, string targetPath)
{
Console.WriteLine($"{nameof(UpLoad)}");
if(ftpClient.UploadFile(sourcePath, targetPath) == FtpStatus.Success)
{
return true;
}
else
{
return false;
}
}
}
}
728x90
'C#' 카테고리의 다른 글
[C# 동시성 프로그래밍] - 비동기 프로그래밍 (0) | 2022.05.08 |
---|---|
[C# AutoMapper] AutoMapper 란? (0) | 2022.05.05 |
[C# 벤치마크] 벤치마크 닷넷 static 메서드 성능 측정하기 (0) | 2022.05.03 |
[C#] ASP.NET Core FluentValidation.AspNetCore .NET 사용법 (0) | 2022.04.21 |
[C#] Fluent Validation 이란? (0) | 2022.04.21 |
이 글을 공유하기