[#103] object: Add PutSingle method code

Signed-off-by: Dmitrii Stepanov <d.stepanov@yadro.com>
This commit is contained in:
Dmitrii Stepanov 2023-07-06 17:06:17 +03:00
parent 37e22b33ad
commit 98cab7ed61
2 changed files with 163 additions and 7 deletions

View file

@ -5,6 +5,8 @@ import (
"git.frostfs.info/TrueCloudLab/frostfs-sdk-go/object"
"git.frostfs.info/TrueCloudLab/frostfs-sdk-go/object/transformer"
"google.golang.org/grpc/codes"
"google.golang.org/grpc/status"
)
func (c *Client) objectPutInitTransformer(prm PrmObjectPutInit) (*objectWriterTransformer, error) {
@ -56,11 +58,12 @@ func (x *objectWriterTransformer) Close(ctx context.Context) (*ResObjectPut, err
}
type internalTarget struct {
current *object.Object
client *Client
res *ResObjectPut
prm PrmObjectPutInit
payload []byte
current *object.Object
client *Client
res *ResObjectPut
prm PrmObjectPutInit
payload []byte
useStream bool
}
func (it *internalTarget) WriteHeader(_ context.Context, object *object.Object) error {
@ -75,9 +78,19 @@ func (it *internalTarget) Write(_ context.Context, p []byte) (n int, err error)
func (it *internalTarget) Close(ctx context.Context) (*transformer.AccessIdentifiers, error) {
it.current.SetPayload(it.payload)
putSingleImplemented, err := it.tryPutSingle(ctx)
if putSingleImplemented {
return nil, err
}
it.useStream = true
return nil, it.putAsStream(ctx)
}
func (it *internalTarget) putAsStream(ctx context.Context) error {
wrt, err := it.client.objectPutInitRaw(ctx, it.prm)
if err != nil {
return nil, err
return err
}
if wrt.WriteHeader(ctx, *it.current) {
wrt.WritePayloadChunk(ctx, it.current.Payload())
@ -85,5 +98,32 @@ func (it *internalTarget) Close(ctx context.Context) (*transformer.AccessIdentif
it.res, err = wrt.Close(ctx)
it.current = nil
it.payload = nil
return nil, err
return err
}
func (it *internalTarget) tryPutSingle(ctx context.Context) (bool, error) {
if it.useStream {
return false, nil
}
var prm PrmObjectPutSingle
prm.SetCopiesNumber(it.prm.copyNum)
prm.SetObject(it.current.ToV2())
prm.UseKey(prm.key)
prm.meta = it.prm.meta
res, err := it.client.ObjectPutSingle(ctx, prm)
if err != nil && status.Code(err) == codes.Unimplemented {
return false, err
}
if err == nil {
id, _ := it.current.ID()
it.res = &ResObjectPut{
statusRes: res.statusRes,
obj: id,
}
}
it.current = nil
it.payload = nil
return true, err
}