130 lines
No EOL
3.6 KiB
C#
130 lines
No EOL
3.6 KiB
C#
using FrostFS.Object;
|
|
using FrostFS.Refs;
|
|
using FrostFS.SDK.ClientV2.Mappers.GRPC;
|
|
using FrostFS.SDK.Cryptography;
|
|
using FrostFS.SDK.ModelsV2;
|
|
using FrostFS.Session;
|
|
using Google.Protobuf;
|
|
using Grpc.Core;
|
|
|
|
namespace FrostFS.SDK.ClientV2;
|
|
|
|
public partial class Client
|
|
{
|
|
public async Task<HeadResponse> GetObjectHeadAsync(ContainerID cid, ObjectID oid)
|
|
{
|
|
var request = new HeadRequest
|
|
{
|
|
Body = new HeadRequest.Types.Body
|
|
{
|
|
Address = new Address
|
|
{
|
|
ContainerId = cid,
|
|
ObjectId = oid
|
|
}
|
|
},
|
|
};
|
|
request.AddMetaHeader();
|
|
request.Sign(_key);
|
|
return await _objectServiceClient.HeadAsync(request);
|
|
}
|
|
|
|
public async Task<PutResponse> PutObjectAsync(ContainerID cid, Stream data)
|
|
{
|
|
var sessionToken = await CreateSessionAsync(uint.MaxValue);
|
|
var header = new Header
|
|
{
|
|
ContainerId = cid,
|
|
OwnerId = _owner.ToGrpcMessage(),
|
|
Version = Version.ToGrpcMessage()
|
|
};
|
|
var oid = new ObjectID
|
|
{
|
|
Value = header.Sha256()
|
|
};
|
|
var request = new PutRequest
|
|
{
|
|
Body = new PutRequest.Types.Body
|
|
{
|
|
Init = new PutRequest.Types.Body.Types.Init
|
|
{
|
|
Header = header,
|
|
},
|
|
}
|
|
};
|
|
request.AddMetaHeader();
|
|
request.AddObjectSessionToken(sessionToken, cid, oid, ObjectSessionContext.Types.Verb.Put, _key);
|
|
request.Sign(_key);
|
|
|
|
using var stream = await InitObject(request);
|
|
var buffer = new byte[Constants.ObjectChunkSize];
|
|
var bufferLength = data.Read(buffer, 0, Constants.ObjectChunkSize);
|
|
while (bufferLength > 0)
|
|
{
|
|
request.Body = new PutRequest.Types.Body
|
|
{
|
|
Chunk = ByteString.CopyFrom(buffer[..bufferLength]),
|
|
};
|
|
request.VerifyHeader = null;
|
|
request.Sign(_key);
|
|
await stream.Write(request);
|
|
bufferLength = data.Read(buffer, 0, Constants.ObjectChunkSize);
|
|
}
|
|
return await stream.Close();
|
|
}
|
|
|
|
private async Task<ObjectStreamer> InitObject(PutRequest initRequest)
|
|
{
|
|
if (initRequest is null)
|
|
{
|
|
throw new ArgumentNullException(nameof(initRequest));
|
|
}
|
|
var call = _objectServiceClient.Put();
|
|
await call.RequestStream.WriteAsync(initRequest);
|
|
return new ObjectStreamer { Call = call };
|
|
}
|
|
|
|
public async Task<DeleteResponse> DeleteObjectAsync(ContainerID cid, ObjectID oid)
|
|
{
|
|
var request = new DeleteRequest
|
|
{
|
|
Body = new DeleteRequest.Types.Body
|
|
{
|
|
Address = new Address
|
|
{
|
|
ContainerId = cid,
|
|
ObjectId = oid
|
|
}
|
|
}
|
|
};
|
|
request.AddMetaHeader();
|
|
request.Sign(_key);
|
|
return await _objectServiceClient.DeleteAsync(request);
|
|
}
|
|
}
|
|
|
|
internal class ObjectStreamer : IDisposable
|
|
{
|
|
public AsyncClientStreamingCall<PutRequest, PutResponse> Call { get; init; }
|
|
|
|
public void Dispose()
|
|
{
|
|
Call.Dispose();
|
|
}
|
|
|
|
public async Task Write(PutRequest request)
|
|
{
|
|
if (request is null)
|
|
{
|
|
throw new ArgumentNullException(nameof(request));
|
|
}
|
|
|
|
await Call.RequestStream.WriteAsync(request);
|
|
}
|
|
|
|
public async Task<PutResponse> Close()
|
|
{
|
|
await Call.RequestStream.CompleteAsync();
|
|
return await Call.ResponseAsync;
|
|
}
|
|
} |