TransferClientBase
using Relativity.Transfer.Resources;
using System;
using System.Runtime.CompilerServices;
using System.Threading;
using System.Threading.Tasks;
namespace Relativity.Transfer
{
public abstract class TransferClientBase : ITransferClient, IDisposable
{
private static readonly object SyncRoot = new object();
private bool disposed;
private Workspace workspace;
public WellKnownTransferClient Client { get; }
public RelativityConnectionInfo ConnectionInfo { get; }
public ClientConfiguration Configuration { get; }
public string DisplayName { get; }
public Guid Id { get; }
public string Name { get; }
internal IRelativityServiceFactory ServiceFactory { get; }
protected IFileSystemService FileSystemService { get; }
protected ITransferLog Log { get; }
protected IPathValidationProvider PathValidationProvider => ServiceFactory.PathValidationProvider;
protected Workspace Workspace {
get {
lock (SyncRoot) {
return workspace;
}
}
private set {
lock (SyncRoot) {
workspace = value;
}
}
}
protected IWorkspaceService WorkspaceService { get; }
protected TransferClientBase(RelativityConnectionInfo connectionInfo, ClientConfiguration configuration, IWorkspaceService workspaceService, ITransferLog log, Guid id, WellKnownTransferClient client, string name, string displayName)
: this(connectionInfo, configuration, workspaceService, log, ServiceObjectLocator.GetService<IFileSystemService>(), id, client, name, displayName, new DefaultPathValidationFactory())
{
}
protected TransferClientBase(RelativityConnectionInfo connectionInfo, ClientConfiguration configuration, IWorkspaceService workspaceService, ITransferLog log, Guid id, WellKnownTransferClient client, string name, string displayName, IPathValidationFactory pathValidationFactory)
: this(connectionInfo, configuration, workspaceService, log, ServiceObjectLocator.GetService<IFileSystemService>(), id, client, name, displayName, pathValidationFactory)
{
}
protected TransferClientBase(RelativityConnectionInfo connectionInfo, ClientConfiguration configuration, IWorkspaceService workspaceService, ITransferLog log, IFileSystemService fileSystemService, Guid id, WellKnownTransferClient client, string name, string displayName, IPathValidationFactory pathValidationFactory)
{
if (connectionInfo == null)
throw new ArgumentNullException("connectionInfo");
if (connectionInfo.Credential == null)
throw new ArgumentException(CoreStrings.RelativityConnectionCredentialsArgumentExceptionMessage, "connectionInfo");
if (connectionInfo.Host == (Uri)null)
throw new ArgumentException(CoreStrings.RelativityConnectionHostArgumentExceptionMessage, "connectionInfo");
if (connectionInfo.WorkspaceId < 1 && connectionInfo.WorkspaceId != -1)
throw new ArgumentOutOfRangeException("connectionInfo", CoreStrings.RelativityConnectionWorkspaceArgumentExceptionMessage);
if (configuration == null)
throw new ArgumentNullException("configuration");
if (workspaceService == null)
throw new ArgumentNullException("workspaceService");
if (log == null)
throw new ArgumentNullException("log");
if (id == Guid.Empty)
throw new ArgumentNullException("id");
if (string.IsNullOrEmpty(name))
throw new ArgumentNullException("name");
if (string.IsNullOrEmpty(displayName))
throw new ArgumentNullException("displayName");
if (fileSystemService == null)
throw new ArgumentNullException("fileSystemService");
if (pathValidationFactory == null)
throw new ArgumentNullException("pathValidationFactory");
Client = client;
Configuration = configuration;
ConnectionInfo = connectionInfo;
Log = log;
Id = id;
Name = name;
DisplayName = displayName;
Workspace = null;
WorkspaceService = workspaceService;
FileSystemService = fileSystemService;
ServiceFactory = new ServiceFactory(ConnectionInfo, Configuration, Log, pathValidationFactory.CreatePathValidationProvider());
}
public void Dispose()
{
Dispose(true);
GC.SuppressFinalize(this);
}
public Task<ITransferJob> CreateJobAsync(ITransferRequest request)
{
if (request == null)
throw new ArgumentNullException("request");
return CreateJobAsync(request, CancellationToken.None);
}
[Obsolete("This enumeration support will be removed in next release. In order to perform file enumeration use EnumerationBuilder and IEnumerationOrchestrator")]
public IPathEnumerator CreatePathEnumerator(bool local)
{
if (!local)
return OnCreateRemotePathEnumerator();
return OnCreateLocalPathEnumerator();
}
public IBatchSerializer CreateBatchSerializer(string batchDirectory, TransferDirection direction, PathEnumeratorContext context)
{
return new BatchSerializer(batchDirectory, direction, context, PathValidationProvider, Log);
}
[AsyncStateMachine(typeof(<CreateJobAsync>d__45))]
public virtual Task<ITransferJob> CreateJobAsync(ITransferRequest request, CancellationToken token)
{
<CreateJobAsync>d__45 stateMachine = default(<CreateJobAsync>d__45);
stateMachine.<>t__builder = AsyncTaskMethodBuilder<ITransferJob>.Create();
stateMachine.<>4__this = this;
stateMachine.request = request;
stateMachine.token = token;
stateMachine.<>1__state = -1;
stateMachine.<>t__builder.Start(ref stateMachine);
return stateMachine.<>t__builder.Task;
}
public Task<Workspace> GetWorkspaceAsync()
{
return GetWorkspaceAsync(CancellationToken.None);
}
public Task<Workspace> GetWorkspaceAsync(CancellationToken token)
{
return GetWorkspaceAsync(ConnectionInfo.WorkspaceId, CancellationToken.None);
}
[AsyncStateMachine(typeof(<GetWorkspaceAsync>d__48))]
public Task<Workspace> GetWorkspaceAsync(int workspaceArtifactId, CancellationToken token)
{
<GetWorkspaceAsync>d__48 stateMachine = default(<GetWorkspaceAsync>d__48);
stateMachine.<>t__builder = AsyncTaskMethodBuilder<Workspace>.Create();
stateMachine.<>4__this = this;
stateMachine.workspaceArtifactId = workspaceArtifactId;
stateMachine.token = token;
stateMachine.<>1__state = -1;
stateMachine.<>t__builder.Start(ref stateMachine);
return stateMachine.<>t__builder.Task;
}
public virtual Task<ITransferResult> TransferAsync(ITransferRequest request)
{
if (request == null)
throw new ArgumentNullException("request");
return TransferAsync(request, CancellationToken.None);
}
[AsyncStateMachine(typeof(<TransferAsync>d__50))]
public virtual Task<ITransferResult> TransferAsync(ITransferRequest request, CancellationToken token)
{
<TransferAsync>d__50 stateMachine = default(<TransferAsync>d__50);
stateMachine.<>t__builder = AsyncTaskMethodBuilder<ITransferResult>.Create();
stateMachine.<>4__this = this;
stateMachine.request = request;
stateMachine.token = token;
stateMachine.<>1__state = -1;
stateMachine.<>t__builder.Start(ref stateMachine);
return stateMachine.<>t__builder.Task;
}
public Task<ISupportCheckResult> SupportCheckAsync()
{
return SupportCheckAsync(CancellationToken.None);
}
[AsyncStateMachine(typeof(<SupportCheckAsync>d__52))]
public Task<ISupportCheckResult> SupportCheckAsync(CancellationToken token)
{
<SupportCheckAsync>d__52 stateMachine = default(<SupportCheckAsync>d__52);
stateMachine.<>t__builder = AsyncTaskMethodBuilder<ISupportCheckResult>.Create();
stateMachine.<>4__this = this;
stateMachine.token = token;
stateMachine.<>1__state = -1;
stateMachine.<>t__builder.Start(ref stateMachine);
return stateMachine.<>t__builder.Task;
}
public Task<IConnectionCheckResult> ConnectionCheckAsync(DiagnosticsContext context)
{
if (context == null)
throw new ArgumentNullException("context");
return ConnectionCheckAsync(context, CancellationToken.None);
}
[AsyncStateMachine(typeof(<ConnectionCheckAsync>d__54))]
public Task<IConnectionCheckResult> ConnectionCheckAsync(DiagnosticsContext context, CancellationToken token)
{
<ConnectionCheckAsync>d__54 stateMachine = default(<ConnectionCheckAsync>d__54);
stateMachine.<>t__builder = AsyncTaskMethodBuilder<IConnectionCheckResult>.Create();
stateMachine.<>4__this = this;
stateMachine.context = context;
stateMachine.token = token;
stateMachine.<>1__state = -1;
stateMachine.<>t__builder.Start(ref stateMachine);
return stateMachine.<>t__builder.Task;
}
public override string ToString()
{
return $"""{Name}""{Id}";
}
protected IRelativityServiceFactory CreateRelativityServiceFactory()
{
return new ServiceFactory(ConnectionInfo, Configuration, Log);
}
protected virtual ITransferJobService CreateTransferJobService(ITransferRequest request, CancellationToken token)
{
return CreateTransferJobService(request, Configuration, token);
}
protected virtual ITransferJobService CreateTransferJobService(ITransferRequest request, ClientConfiguration configuration, CancellationToken token)
{
return new TransferJobService(request, configuration, Log, token);
}
protected virtual Task OnAutoConfigAsync(CancellationToken token)
{
return Task.FromResult(true);
}
[Obsolete("This enumeration support will be removed in next release. In order to perform file enumeration use EnumerationBuilder and IEnumerationOrchestrator")]
protected virtual IPathEnumerator OnCreateLocalPathEnumerator()
{
return new LocalPathEnumerator(FileSystemService, PathValidationProvider, Log);
}
[Obsolete("This enumeration support will be removed in next release. In order to perform file enumeration use EnumerationBuilder and IEnumerationOrchestrator")]
protected virtual IPathEnumerator OnCreateRemotePathEnumerator()
{
throw new NotSupportedException(CoreStrings.RemotePathEnumeratorNotSupported);
}
protected abstract Task<ISupportCheckResult> OnSupportCheckAsync(CancellationToken token);
protected abstract Task<ITransferJob> OnCreateJobAsync(ITransferRequest request, CancellationToken token);
protected abstract Task<IConnectionCheckResult> OnExecConnectionCheckAsync(DiagnosticsContext context, CancellationToken token);
protected virtual void Dispose(bool disposing)
{
if (!disposed)
disposed = true;
}
[AsyncStateMachine(typeof(<InitializeClientAsync>d__66))]
private Task InitializeClientAsync(CancellationToken token)
{
<InitializeClientAsync>d__66 stateMachine = default(<InitializeClientAsync>d__66);
stateMachine.<>t__builder = AsyncTaskMethodBuilder.Create();
stateMachine.<>4__this = this;
stateMachine.token = token;
stateMachine.<>1__state = -1;
stateMachine.<>t__builder.Start(ref stateMachine);
return stateMachine.<>t__builder.Task;
}
[AsyncStateMachine(typeof(<InitializeWorkspaceAsync>d__67))]
private Task InitializeWorkspaceAsync(CancellationToken token)
{
<InitializeWorkspaceAsync>d__67 stateMachine = default(<InitializeWorkspaceAsync>d__67);
stateMachine.<>t__builder = AsyncTaskMethodBuilder.Create();
stateMachine.<>4__this = this;
stateMachine.token = token;
stateMachine.<>1__state = -1;
stateMachine.<>t__builder.Start(ref stateMachine);
return stateMachine.<>t__builder.Task;
}
private void VerifyIfTargetPathExists(ITransferRequest request)
{
if (string.IsNullOrEmpty(request.TargetPath)) {
foreach (TransferPath path in request.Paths) {
if (string.IsNullOrEmpty(path.TargetPath))
Log.LogTransferWarning(request, "Transfer Path (Source: {SourcePath}) has no target path set, neither does transfer job itself. Transfer may fail.", path.SourcePath, LogRedaction.OnPositions(default(int)));
}
}
}
}
}