[#92] client: Accept structured parameters in non-object operations

Define `XPrm` type for each `X` client operation which structures
parameters. Export setters of each parameterized value. Emphasize that
some parameters are required. Make the client panic when the parameters
are incorrectly set. Get rid of vadiadic call options and `CallOption`
type. Improve documentation of client behavior.

Signed-off-by: Leonard Lyubich <leonard@nspcc.ru>
This commit is contained in:
Leonard Lyubich 2021-12-02 15:21:54 +03:00 committed by Alex Vanin
parent 596774ce5b
commit 213d20e3fb
13 changed files with 1100 additions and 885 deletions

View file

@ -2,82 +2,99 @@ package client
import ( import (
"context" "context"
"fmt"
v2accounting "github.com/nspcc-dev/neofs-api-go/v2/accounting" v2accounting "github.com/nspcc-dev/neofs-api-go/v2/accounting"
rpcapi "github.com/nspcc-dev/neofs-api-go/v2/rpc" rpcapi "github.com/nspcc-dev/neofs-api-go/v2/rpc"
"github.com/nspcc-dev/neofs-api-go/v2/rpc/client" "github.com/nspcc-dev/neofs-api-go/v2/rpc/client"
v2signature "github.com/nspcc-dev/neofs-api-go/v2/signature"
"github.com/nspcc-dev/neofs-sdk-go/accounting" "github.com/nspcc-dev/neofs-sdk-go/accounting"
"github.com/nspcc-dev/neofs-sdk-go/owner" "github.com/nspcc-dev/neofs-sdk-go/owner"
) )
type BalanceOfRes struct { // GetBalancePrm groups parameters of GetBalance operation.
type GetBalancePrm struct {
ownerSet bool
ownerID owner.ID
}
// SetAccount sets identifier of the NeoFS account for which the balance is requested.
// Required parameter. Must be a valid ID according to NeoFS API protocol.
func (x *GetBalancePrm) SetAccount(id owner.ID) {
x.ownerID = id
x.ownerSet = true
}
// GetBalanceRes groups resulting values of GetBalance operation.
type GetBalanceRes struct {
statusRes statusRes
amount *accounting.Decimal amount *accounting.Decimal
} }
func (x *BalanceOfRes) setAmount(v *accounting.Decimal) { func (x *GetBalanceRes) setAmount(v *accounting.Decimal) {
x.amount = v x.amount = v
} }
func (x BalanceOfRes) Amount() *accounting.Decimal { // Amount returns current amount of funds on the NeoFS account as decimal number.
//
// Client doesn't retain value so modification is safe.
func (x GetBalanceRes) Amount() *accounting.Decimal {
return x.amount return x.amount
} }
// GetBalance receives owner balance through NeoFS API call. // GetBalance requests current balance of the NeoFS account.
// //
// Any client's internal or transport errors are returned as `error`, // Any client's internal or transport errors are returned as `error`,
// If WithNeoFSErrorParsing option has been provided, unsuccessful // If WithNeoFSErrorParsing option has been provided, unsuccessful
// NeoFS status codes are returned as `error`, otherwise, are included // NeoFS status codes are returned as `error`, otherwise, are included
// in the returned result structure. // in the returned result structure.
func (c *Client) GetBalance(ctx context.Context, owner *owner.ID, opts ...CallOption) (*BalanceOfRes, error) { //
// apply all available options // Immediately panics if parameters are set incorrectly (see GetBalancePrm docs).
callOptions := c.defaultCallOptions() // Context is required and must not be nil. It is used for network communication.
//
for i := range opts { // Exactly one return value is non-nil. Server status return is returned in GetBalanceRes.
opts[i](callOptions) // Reflects all internal errors in second return value (transport problems, response processing, etc.).
func (c *Client) GetBalance(ctx context.Context, prm GetBalancePrm) (*GetBalanceRes, error) {
switch {
case ctx == nil:
panic(panicMsgMissingContext)
case !prm.ownerSet:
panic("account not set")
case !prm.ownerID.Valid():
panic("invalid account ID")
} }
reqBody := new(v2accounting.BalanceRequestBody) // form request body
reqBody.SetOwnerID(owner.ToV2()) var body v2accounting.BalanceRequestBody
req := new(v2accounting.BalanceRequest) body.SetOwnerID(prm.ownerID.ToV2())
req.SetBody(reqBody)
req.SetMetaHeader(v2MetaHeaderFromOpts(callOptions))
err := v2signature.SignServiceMessage(callOptions.key, req) // form request
if err != nil { var req v2accounting.BalanceRequest
return nil, err
}
resp, err := rpcapi.Balance(c.Raw(), req, client.WithContext(ctx)) req.SetBody(&body)
if err != nil {
return nil, fmt.Errorf("transport error: %w", err) // init call context
}
var ( var (
res = new(BalanceOfRes) cc contextCall
procPrm processResponseV2Prm res GetBalanceRes
procRes processResponseV2Res
) )
procPrm.callOpts = callOptions c.initCallContext(&cc)
procPrm.resp = resp cc.req = &req
cc.statusRes = &res
procRes.statusRes = res cc.call = func() (responseV2, error) {
return rpcapi.Balance(c.Raw(), &req, client.WithContext(ctx))
// process response in general
if c.processResponseV2(&procRes, procPrm) {
if procRes.cliErr != nil {
return nil, procRes.cliErr
} }
cc.result = func(r responseV2) {
return res, nil resp := r.(*v2accounting.BalanceResponse)
}
res.setAmount(accounting.NewDecimalFromV2(resp.GetBody().GetBalance())) res.setAmount(accounting.NewDecimalFromV2(resp.GetBody().GetBalance()))
}
return res, nil // process call
if !cc.processCall() {
return nil, cc.err
}
return &res, nil
} }

View file

@ -1,10 +1,14 @@
package client package client
import ( import (
"crypto/ecdsa"
"fmt" "fmt"
v2session "github.com/nspcc-dev/neofs-api-go/v2/session"
"github.com/nspcc-dev/neofs-api-go/v2/signature" "github.com/nspcc-dev/neofs-api-go/v2/signature"
apistatus "github.com/nspcc-dev/neofs-sdk-go/client/status" apistatus "github.com/nspcc-dev/neofs-sdk-go/client/status"
"github.com/nspcc-dev/neofs-sdk-go/session"
"github.com/nspcc-dev/neofs-sdk-go/version"
) )
// common interface of resulting structures with API status. // common interface of resulting structures with API status.
@ -87,3 +91,175 @@ func (c *Client) processResponseV2(res *processResponseV2Res, prm processRespons
return unsuccessfulStatus return unsuccessfulStatus
} }
type prmSession struct {
tokenSessionSet bool
tokenSession session.Token
}
// SetSessionToken sets token of the session within which request should be sent.
func (x *prmSession) SetSessionToken(tok session.Token) {
x.tokenSession = tok
x.tokenSessionSet = true
}
func (x prmSession) writeToMetaHeader(meta *v2session.RequestMetaHeader) {
if x.tokenSessionSet {
meta.SetSessionToken(x.tokenSession.ToV2())
}
}
// panic messages.
const (
panicMsgMissingContext = "missing context"
panicMsgMissingContainer = "missing container"
)
// groups all the details required to send a single request and process a response to it.
type contextCall struct {
// ==================================================
// state vars that do not require explicit initialization
// final error to be returned from client method
err error
// received response
resp responseV2
// ==================================================
// shared parameters which are set uniformly on all calls
// request signing key
key ecdsa.PrivateKey
// callback prior to processing the response by the client
callbackResp func(ResponseMetaInfo) error
// if set, protocol errors will be expanded into a final error
resolveAPIFailures bool
// NeoFS network magic
netMagic uint64
// ==================================================
// custom call parameters
// structure of the call result
statusRes resCommon
// request to be signed with a key and sent
req interface {
GetMetaHeader() *v2session.RequestMetaHeader
SetMetaHeader(*v2session.RequestMetaHeader)
}
// function to send a request (unary) and receive a response
call func() (responseV2, error)
// function of writing response fields to the resulting structure (optional)
result func(v2 responseV2)
}
func (x contextCall) prepareRequest() {
meta := x.req.GetMetaHeader()
if meta == nil {
meta = new(v2session.RequestMetaHeader)
x.req.SetMetaHeader(meta)
}
if meta.GetTTL() == 0 {
meta.SetTTL(2)
}
if meta.GetVersion() == nil {
meta.SetVersion(version.Current().ToV2())
}
meta.SetNetworkMagic(x.netMagic)
}
// performs common actions of response processing and writes any problem as a result status or client error
// (in both cases returns false).
//
// Actions:
// * verify signature (internal);
// * call response callback (internal);
// * unwrap status error (optional).
func (x *contextCall) processResponse() bool {
// call response callback if set
if x.callbackResp != nil {
x.err = x.callbackResp(ResponseMetaInfo{
key: x.resp.GetVerificationHeader().GetBodySignature().GetKey(),
})
if x.err != nil {
x.err = fmt.Errorf("response callback error: %w", x.err)
return false
}
}
// note that we call response callback before signature check since it is expected more lightweight
// while verification needs marshaling
// verify response signature
x.err = signature.VerifyServiceMessage(x.resp)
if x.err != nil {
x.err = fmt.Errorf("invalid response signature: %w", x.err)
return false
}
// get result status
st := apistatus.FromStatusV2(x.resp.GetMetaHeader().GetStatus())
// unwrap unsuccessful status and return it
// as error if client has been configured so
successfulStatus := apistatus.IsSuccessful(st)
if !successfulStatus && x.resolveAPIFailures {
x.err = apistatus.ErrFromStatus(st)
return false
}
x.statusRes.setStatus(st)
return successfulStatus
}
// goes through all stages of sending a request and processing a response. Returns true if successful.
func (x *contextCall) processCall() bool {
// prepare the request
x.prepareRequest()
// sign the request
x.err = signature.SignServiceMessage(&x.key, x.req)
if x.err != nil {
x.err = fmt.Errorf("sign request: %w", x.err)
return false
}
// perform RPC
x.resp, x.err = x.call()
if x.err != nil {
x.err = fmt.Errorf("transport error: %w", x.err)
return false
}
// process the response
ok := x.processResponse()
if !ok {
return false
}
// write response to resulting structure
if x.result != nil {
x.result(x.resp)
}
return true
}
// initializes static cross-call parameters inherited from client.
func (c *Client) initCallContext(ctx *contextCall) {
ctx.key = *c.opts.key
ctx.resolveAPIFailures = c.opts.parseNeoFSErrors
ctx.callbackResp = c.opts.cbRespInfo
ctx.netMagic = c.opts.netMagic
}

View file

@ -2,14 +2,13 @@ package client
import ( import (
"context" "context"
"fmt"
v2container "github.com/nspcc-dev/neofs-api-go/v2/container" v2container "github.com/nspcc-dev/neofs-api-go/v2/container"
"github.com/nspcc-dev/neofs-api-go/v2/refs" "github.com/nspcc-dev/neofs-api-go/v2/refs"
rpcapi "github.com/nspcc-dev/neofs-api-go/v2/rpc" rpcapi "github.com/nspcc-dev/neofs-api-go/v2/rpc"
"github.com/nspcc-dev/neofs-api-go/v2/rpc/client" "github.com/nspcc-dev/neofs-api-go/v2/rpc/client"
v2session "github.com/nspcc-dev/neofs-api-go/v2/session"
v2signature "github.com/nspcc-dev/neofs-api-go/v2/signature" v2signature "github.com/nspcc-dev/neofs-api-go/v2/signature"
apistatus "github.com/nspcc-dev/neofs-sdk-go/client/status"
"github.com/nspcc-dev/neofs-sdk-go/container" "github.com/nspcc-dev/neofs-sdk-go/container"
cid "github.com/nspcc-dev/neofs-sdk-go/container/id" cid "github.com/nspcc-dev/neofs-sdk-go/container/id"
"github.com/nspcc-dev/neofs-sdk-go/eacl" "github.com/nspcc-dev/neofs-sdk-go/eacl"
@ -17,44 +16,35 @@ import (
"github.com/nspcc-dev/neofs-sdk-go/session" "github.com/nspcc-dev/neofs-sdk-go/session"
"github.com/nspcc-dev/neofs-sdk-go/signature" "github.com/nspcc-dev/neofs-sdk-go/signature"
sigutil "github.com/nspcc-dev/neofs-sdk-go/util/signature" sigutil "github.com/nspcc-dev/neofs-sdk-go/util/signature"
"github.com/nspcc-dev/neofs-sdk-go/version"
) )
type delContainerSignWrapper struct { // ContainerPutPrm groups parameters of PutContainer operation.
body *v2container.DeleteRequestBody type ContainerPutPrm struct {
prmSession
cnrSet bool
cnr container.Container
} }
// EACLWithSignature represents eACL table/signature pair. // SetContainer sets structured information about new NeoFS container.
type EACLWithSignature struct { // Required parameter.
table *eacl.Table func (x *ContainerPutPrm) SetContainer(cnr container.Container) {
} x.cnr = cnr
x.cnrSet = true
func (c delContainerSignWrapper) ReadSignedData(bytes []byte) ([]byte, error) {
return c.body.GetContainerID().GetValue(), nil
}
func (c delContainerSignWrapper) SignedDataSize() int {
return len(c.body.GetContainerID().GetValue())
}
// EACL returns eACL table.
func (e EACLWithSignature) EACL() *eacl.Table {
return e.table
}
// Signature returns table signature.
//
// Deprecated: use EACL().Signature() instead.
func (e EACLWithSignature) Signature() *signature.Signature {
return e.table.Signature()
} }
// ContainerPutRes groups resulting values of PutContainer operation.
type ContainerPutRes struct { type ContainerPutRes struct {
statusRes statusRes
id *cid.ID id *cid.ID
} }
// ID returns identifier of the container declared to be stored in the system.
// Used as a link to information about the container (in particular, you can
// asynchronously check if the save was successful).
//
// Client doesn't retain value so modification is safe.
func (x ContainerPutRes) ID() *cid.ID { func (x ContainerPutRes) ID() *cid.ID {
return x.id return x.id
} }
@ -63,37 +53,42 @@ func (x *ContainerPutRes) setID(id *cid.ID) {
x.id = id x.id = id
} }
// PutContainer puts container through NeoFS API call. // PutContainer sends request to save container in NeoFS.
// //
// Any client's internal or transport errors are returned as `error`. // Any client's internal or transport errors are returned as `error`.
// If WithNeoFSErrorParsing option has been provided, unsuccessful // If WithNeoFSErrorParsing option has been provided, unsuccessful
// NeoFS status codes are returned as `error`, otherwise, are included // NeoFS status codes are returned as `error`, otherwise, are included
// in the returned result structure. // in the returned result structure.
func (c *Client) PutContainer(ctx context.Context, cnr *container.Container, opts ...CallOption) (*ContainerPutRes, error) { //
// apply all available options // Operation is asynchronous and no guaranteed even in the absence of errors.
callOptions := c.defaultCallOptions() // The required time is also not predictable.
//
for i := range opts { // Success can be verified by reading by identifier (see ContainerPutRes.ID).
opts[i](callOptions) //
// Immediately panics if parameters are set incorrectly (see ContainerPutPrm docs).
// Context is required and must not be nil. It is used for network communication.
//
// Exactly one return value is non-nil. Server status return is returned in ContainerPutRes.
// Reflects all internal errors in second return value (transport problems, response processing, etc.).
func (c *Client) PutContainer(ctx context.Context, prm ContainerPutPrm) (*ContainerPutRes, error) {
// check parameters
switch {
case ctx == nil:
panic(panicMsgMissingContext)
case !prm.cnrSet:
panic(panicMsgMissingContainer)
} }
// set transport version // TODO: check private key is set before forming the request
cnr.SetVersion(version.Current())
// if container owner is not set, then use client key as owner
if cnr.OwnerID() == nil {
ownerID := owner.NewIDFromPublicKey(&callOptions.key.PublicKey)
cnr.SetOwnerID(ownerID)
}
// form request body
reqBody := new(v2container.PutRequestBody) reqBody := new(v2container.PutRequestBody)
reqBody.SetContainer(cnr.ToV2()) reqBody.SetContainer(prm.cnr.ToV2())
// sign container // sign container
signWrapper := v2signature.StableMarshalerWrapper{SM: reqBody.GetContainer()} signWrapper := v2signature.StableMarshalerWrapper{SM: reqBody.GetContainer()}
err := sigutil.SignDataWithHandler(callOptions.key, signWrapper, func(key []byte, sig []byte) { err := sigutil.SignDataWithHandler(c.opts.key, signWrapper, func(key []byte, sig []byte) {
containerSignature := new(refs.Signature) containerSignature := new(refs.Signature)
containerSignature.SetKey(key) containerSignature.SetKey(key)
containerSignature.SetSign(sig) containerSignature.SetSign(sig)
@ -103,62 +98,66 @@ func (c *Client) PutContainer(ctx context.Context, cnr *container.Container, opt
return nil, err return nil, err
} }
req := new(v2container.PutRequest) // form meta header
var meta v2session.RequestMetaHeader
prm.prmSession.writeToMetaHeader(&meta)
// form request
var req v2container.PutRequest
req.SetBody(reqBody) req.SetBody(reqBody)
req.SetMetaHeader(&meta)
meta := v2MetaHeaderFromOpts(callOptions) // init call context
meta.SetSessionToken(cnr.SessionToken().ToV2())
req.SetMetaHeader(meta)
err = v2signature.SignServiceMessage(callOptions.key, req)
if err != nil {
return nil, err
}
resp, err := rpcapi.PutContainer(c.Raw(), req, client.WithContext(ctx))
if err != nil {
return nil, err
}
var ( var (
res = new(ContainerPutRes) cc contextCall
procPrm processResponseV2Prm res ContainerPutRes
procRes processResponseV2Res
) )
procPrm.callOpts = callOptions c.initCallContext(&cc)
procPrm.resp = resp cc.req = &req
cc.statusRes = &res
procRes.statusRes = res cc.call = func() (responseV2, error) {
return rpcapi.PutContainer(c.Raw(), &req, client.WithContext(ctx))
// process response in general
if c.processResponseV2(&procRes, procPrm) {
if procRes.cliErr != nil {
return nil, procRes.cliErr
} }
cc.result = func(r responseV2) {
return res, nil resp := r.(*v2container.PutResponse)
}
// sets result status
st := apistatus.FromStatusV2(resp.GetMetaHeader().GetStatus())
res.setStatus(st)
if apistatus.IsSuccessful(st) {
res.setID(cid.NewFromV2(resp.GetBody().GetContainerID())) res.setID(cid.NewFromV2(resp.GetBody().GetContainerID()))
} }
return res, nil // process call
if !cc.processCall() {
return nil, cc.err
}
return &res, nil
} }
// ContainerGetPrm groups parameters of GetContainer operation.
type ContainerGetPrm struct {
idSet bool
id cid.ID
}
// SetContainer sets identifier of the container to be read.
// Required parameter.
func (x *ContainerGetPrm) SetContainer(id cid.ID) {
x.id = id
x.idSet = true
}
// ContainerGetRes groups resulting values of GetContainer operation.
type ContainerGetRes struct { type ContainerGetRes struct {
statusRes statusRes
cnr *container.Container cnr *container.Container
} }
// Container returns structured information about the requested container.
//
// Client doesn't retain value so modification is safe.
func (x ContainerGetRes) Container() *container.Container { func (x ContainerGetRes) Container() *container.Container {
return x.cnr return x.cnr
} }
@ -167,56 +166,50 @@ func (x *ContainerGetRes) setContainer(cnr *container.Container) {
x.cnr = cnr x.cnr = cnr
} }
// GetContainer receives container structure through NeoFS API call. // GetContainer reads NeoFS container from by ID.
// //
// Any client's internal or transport errors are returned as `error`. // Any client's internal or transport errors are returned as `error`.
// If WithNeoFSErrorParsing option has been provided, unsuccessful // If WithNeoFSErrorParsing option has been provided, unsuccessful
// NeoFS status codes are returned as `error`, otherwise, are included // NeoFS status codes are returned as `error`, otherwise, are included
// in the returned result structure. // in the returned result structure.
func (c *Client) GetContainer(ctx context.Context, id *cid.ID, opts ...CallOption) (*ContainerGetRes, error) { //
// apply all available options // Immediately panics if parameters are set incorrectly (see ContainerGetPrm docs).
callOptions := c.defaultCallOptions() // Context is required and must not be nil. It is used for network communication.
//
for i := range opts { // Exactly one return value is non-nil. Server status return is returned in ContainerGetRes.
opts[i](callOptions) // Reflects all internal errors in second return value (transport problems, response processing, etc.).
func (c *Client) GetContainer(ctx context.Context, prm ContainerGetPrm) (*ContainerGetRes, error) {
switch {
case ctx == nil:
panic(panicMsgMissingContext)
case !prm.idSet:
panic(panicMsgMissingContainer)
} }
// form request body
reqBody := new(v2container.GetRequestBody) reqBody := new(v2container.GetRequestBody)
reqBody.SetContainerID(id.ToV2()) reqBody.SetContainerID(prm.id.ToV2())
// form request
var req v2container.GetRequest
req := new(v2container.GetRequest)
req.SetBody(reqBody) req.SetBody(reqBody)
req.SetMetaHeader(v2MetaHeaderFromOpts(callOptions))
err := v2signature.SignServiceMessage(callOptions.key, req) // init call context
if err != nil {
return nil, err
}
resp, err := rpcapi.GetContainer(c.Raw(), req, client.WithContext(ctx))
if err != nil {
return nil, fmt.Errorf("transport error: %w", err)
}
var ( var (
res = new(ContainerGetRes) cc contextCall
procPrm processResponseV2Prm res ContainerGetRes
procRes processResponseV2Res
) )
procPrm.callOpts = callOptions c.initCallContext(&cc)
procPrm.resp = resp cc.req = &req
cc.statusRes = &res
procRes.statusRes = res cc.call = func() (responseV2, error) {
return rpcapi.GetContainer(c.Raw(), &req, client.WithContext(ctx))
// process response in general
if c.processResponseV2(&procRes, procPrm) {
if procRes.cliErr != nil {
return nil, procRes.cliErr
}
return res, nil
} }
cc.result = func(r responseV2) {
resp := r.(*v2container.GetResponse)
body := resp.GetBody() body := resp.GetBody()
@ -231,78 +224,94 @@ func (c *Client) GetContainer(ctx context.Context, id *cid.ID, opts ...CallOptio
) )
res.setContainer(cnr) res.setContainer(cnr)
}
return res, nil // process call
if !cc.processCall() {
return nil, cc.err
}
return &res, nil
} }
// ContainerListPrm groups parameters of ListContainers operation.
type ContainerListPrm struct {
ownerSet bool
ownerID owner.ID
}
// SetAccount sets identifier of the NeoFS account to list the containers.
// Required parameter. Must be a valid ID according to NeoFS API protocol.
func (x *ContainerListPrm) SetAccount(id owner.ID) {
x.ownerID = id
x.ownerSet = true
}
// ContainerListRes groups resulting values of ListContainers operation.
type ContainerListRes struct { type ContainerListRes struct {
statusRes statusRes
ids []*cid.ID ids []*cid.ID
} }
func (x ContainerListRes) IDList() []*cid.ID { // Containers returns list of identifiers of the account-owned containers.
//
// Client doesn't retain value so modification is safe.
func (x ContainerListRes) Containers() []*cid.ID {
return x.ids return x.ids
} }
func (x *ContainerListRes) setIDList(ids []*cid.ID) { func (x *ContainerListRes) setContainers(ids []*cid.ID) {
x.ids = ids x.ids = ids
} }
// ListContainers receives all owner's containers through NeoFS API call. // ListContainers requests identifiers of the account-owned containers.
// //
// Any client's internal or transport errors are returned as `error`. // Any client's internal or transport errors are returned as `error`.
// If WithNeoFSErrorParsing option has been provided, unsuccessful // If WithNeoFSErrorParsing option has been provided, unsuccessful
// NeoFS status codes are returned as `error`, otherwise, are included // NeoFS status codes are returned as `error`, otherwise, are included
// in the returned result structure. // in the returned result structure.
func (c *Client) ListContainers(ctx context.Context, ownerID *owner.ID, opts ...CallOption) (*ContainerListRes, error) { //
// apply all available options // Immediately panics if parameters are set incorrectly (see ContainerListPrm docs).
callOptions := c.defaultCallOptions() // Context is required and must not be nil. It is used for network communication.
//
for i := range opts { // Exactly one return value is non-nil. Server status return is returned in ContainerListRes.
opts[i](callOptions) // Reflects all internal errors in second return value (transport problems, response processing, etc.).
} func (c *Client) ListContainers(ctx context.Context, prm ContainerListPrm) (*ContainerListRes, error) {
// check parameters
if ownerID == nil { switch {
ownerID = owner.NewIDFromPublicKey(&callOptions.key.PublicKey) case ctx == nil:
panic(panicMsgMissingContext)
case !prm.ownerSet:
panic("account not set")
case !prm.ownerID.Valid():
panic("invalid account")
} }
// form request body
reqBody := new(v2container.ListRequestBody) reqBody := new(v2container.ListRequestBody)
reqBody.SetOwnerID(ownerID.ToV2()) reqBody.SetOwnerID(prm.ownerID.ToV2())
// form request
var req v2container.ListRequest
req := new(v2container.ListRequest)
req.SetBody(reqBody) req.SetBody(reqBody)
req.SetMetaHeader(v2MetaHeaderFromOpts(callOptions))
err := v2signature.SignServiceMessage(callOptions.key, req) // init call context
if err != nil {
return nil, err
}
resp, err := rpcapi.ListContainers(c.Raw(), req, client.WithContext(ctx))
if err != nil {
return nil, fmt.Errorf("transport error: %w", err)
}
var ( var (
res = new(ContainerListRes) cc contextCall
procPrm processResponseV2Prm res ContainerListRes
procRes processResponseV2Res
) )
procPrm.callOpts = callOptions c.initCallContext(&cc)
procPrm.resp = resp cc.req = &req
cc.statusRes = &res
procRes.statusRes = res cc.call = func() (responseV2, error) {
return rpcapi.ListContainers(c.Raw(), &req, client.WithContext(ctx))
// process response in general
if c.processResponseV2(&procRes, procPrm) {
if procRes.cliErr != nil {
return nil, procRes.cliErr
}
return res, nil
} }
cc.result = func(r responseV2) {
resp := r.(*v2container.ListResponse)
ids := make([]*cid.ID, 0, len(resp.GetBody().GetContainerIDs())) ids := make([]*cid.ID, 0, len(resp.GetBody().GetContainerIDs()))
@ -310,34 +319,82 @@ func (c *Client) ListContainers(ctx context.Context, ownerID *owner.ID, opts ...
ids = append(ids, cid.NewFromV2(cidV2)) ids = append(ids, cid.NewFromV2(cidV2))
} }
res.setIDList(ids) res.setContainers(ids)
}
return res, nil // process call
if !cc.processCall() {
return nil, cc.err
}
return &res, nil
} }
// ContainerDeletePrm groups parameters of DeleteContainer operation.
type ContainerDeletePrm struct {
prmSession
idSet bool
id cid.ID
}
// SetContainer sets identifier of the NeoFS container to be removed.
// Required parameter.
func (x *ContainerDeletePrm) SetContainer(id cid.ID) {
x.id = id
x.idSet = true
}
// ContainerDeleteRes groups resulting values of DeleteContainer operation.
type ContainerDeleteRes struct { type ContainerDeleteRes struct {
statusRes statusRes
} }
// DeleteContainer deletes specified container through NeoFS API call. // implements github.com/nspcc-dev/neofs-sdk-go/util/signature.DataSource.
type delContainerSignWrapper struct {
body *v2container.DeleteRequestBody
}
func (c delContainerSignWrapper) ReadSignedData([]byte) ([]byte, error) {
return c.body.GetContainerID().GetValue(), nil
}
func (c delContainerSignWrapper) SignedDataSize() int {
return len(c.body.GetContainerID().GetValue())
}
// DeleteContainer sends request to remove the NeoFS container.
// //
// Any client's internal or transport errors are returned as `error`. // Any client's internal or transport errors are returned as `error`.
// If WithNeoFSErrorParsing option has been provided, unsuccessful // If WithNeoFSErrorParsing option has been provided, unsuccessful
// NeoFS status codes are returned as `error`, otherwise, are included // NeoFS status codes are returned as `error`, otherwise, are included
// in the returned result structure. // in the returned result structure.
func (c *Client) DeleteContainer(ctx context.Context, id *cid.ID, opts ...CallOption) (*ContainerDeleteRes, error) { //
// apply all available options // Operation is asynchronous and no guaranteed even in the absence of errors.
callOptions := c.defaultCallOptions() // The required time is also not predictable.
//
for i := range opts { // Success can be verified by reading by identifier (see GetContainer).
opts[i](callOptions) //
// Immediately panics if parameters are set incorrectly (see ContainerDeletePrm docs).
// Context is required and must not be nil. It is used for network communication.
//
// Exactly one return value is non-nil. Server status return is returned in ContainerDeleteRes.
// Reflects all internal errors in second return value (transport problems, response processing, etc.).
func (c *Client) DeleteContainer(ctx context.Context, prm ContainerDeletePrm) (*ContainerDeleteRes, error) {
// check parameters
switch {
case ctx == nil:
panic(panicMsgMissingContext)
case !prm.idSet:
panic(panicMsgMissingContainer)
} }
// form request body
reqBody := new(v2container.DeleteRequestBody) reqBody := new(v2container.DeleteRequestBody)
reqBody.SetContainerID(id.ToV2()) reqBody.SetContainerID(prm.id.ToV2())
// sign container // sign container
err := sigutil.SignDataWithHandler(callOptions.key, err := sigutil.SignDataWithHandler(c.opts.key,
delContainerSignWrapper{ delContainerSignWrapper{
body: reqBody, body: reqBody,
}, },
@ -352,107 +409,115 @@ func (c *Client) DeleteContainer(ctx context.Context, id *cid.ID, opts ...CallOp
return nil, err return nil, err
} }
req := new(v2container.DeleteRequest) // form meta header
var meta v2session.RequestMetaHeader
prm.prmSession.writeToMetaHeader(&meta)
// form request
var req v2container.DeleteRequest
req.SetBody(reqBody) req.SetBody(reqBody)
req.SetMetaHeader(v2MetaHeaderFromOpts(callOptions)) req.SetMetaHeader(&meta)
err = v2signature.SignServiceMessage(callOptions.key, req) // init call context
if err != nil {
return nil, err
}
resp, err := rpcapi.DeleteContainer(c.Raw(), req, client.WithContext(ctx))
if err != nil {
return nil, fmt.Errorf("transport error: %w", err)
}
var ( var (
res = new(ContainerDeleteRes) cc contextCall
procPrm processResponseV2Prm res ContainerDeleteRes
procRes processResponseV2Res
) )
procPrm.callOpts = callOptions c.initCallContext(&cc)
procPrm.resp = resp cc.req = &req
cc.statusRes = &res
procRes.statusRes = res cc.call = func() (responseV2, error) {
return rpcapi.DeleteContainer(c.Raw(), &req, client.WithContext(ctx))
// process response in general
if c.processResponseV2(&procRes, procPrm) {
if procRes.cliErr != nil {
return nil, procRes.cliErr
} }
return res, nil // process call
if !cc.processCall() {
return nil, cc.err
} }
return res, nil return &res, nil
} }
// EACLPrm groups parameters of EACL operation.
type EACLPrm struct {
idSet bool
id cid.ID
}
// SetContainer sets identifier of the NeoFS container to read the eACL table.
// Required parameter.
func (x *EACLPrm) SetContainer(id cid.ID) {
x.id = id
x.idSet = true
}
// EACLRes groups resulting values of EACL operation.
type EACLRes struct { type EACLRes struct {
statusRes statusRes
table *eacl.Table table *eacl.Table
} }
// Table returns eACL table of the requested container.
//
// Client doesn't retain value so modification is safe.
func (x EACLRes) Table() *eacl.Table { func (x EACLRes) Table() *eacl.Table {
return x.table return x.table
} }
func (x *EACLRes) SetTable(table *eacl.Table) { func (x *EACLRes) setTable(table *eacl.Table) {
x.table = table x.table = table
} }
// EACL receives eACL of the specified container through NeoFS API call. // EACL reads eACL table of the NeoFS container.
// //
// Any client's internal or transport errors are returned as `error`. // Any client's internal or transport errors are returned as `error`.
// If WithNeoFSErrorParsing option has been provided, unsuccessful // If WithNeoFSErrorParsing option has been provided, unsuccessful
// NeoFS status codes are returned as `error`, otherwise, are included // NeoFS status codes are returned as `error`, otherwise, are included
// in the returned result structure. // in the returned result structure.
func (c *Client) EACL(ctx context.Context, id *cid.ID, opts ...CallOption) (*EACLRes, error) { //
// apply all available options // Immediately panics if parameters are set incorrectly (see EACLPrm docs).
callOptions := c.defaultCallOptions() // Context is required and must not be nil. It is used for network communication.
//
for i := range opts { // Exactly one return value is non-nil. Server status return is returned in EACLRes.
opts[i](callOptions) // Reflects all internal errors in second return value (transport problems, response processing, etc.).
func (c *Client) EACL(ctx context.Context, prm EACLPrm) (*EACLRes, error) {
// check parameters
switch {
case ctx == nil:
panic(panicMsgMissingContext)
case !prm.idSet:
panic(panicMsgMissingContainer)
} }
// form request body
reqBody := new(v2container.GetExtendedACLRequestBody) reqBody := new(v2container.GetExtendedACLRequestBody)
reqBody.SetContainerID(id.ToV2()) reqBody.SetContainerID(prm.id.ToV2())
// form request
var req v2container.GetExtendedACLRequest
req := new(v2container.GetExtendedACLRequest)
req.SetBody(reqBody) req.SetBody(reqBody)
req.SetMetaHeader(v2MetaHeaderFromOpts(callOptions))
err := v2signature.SignServiceMessage(callOptions.key, req) // init call context
if err != nil {
return nil, err
}
resp, err := rpcapi.GetEACL(c.Raw(), req, client.WithContext(ctx))
if err != nil {
return nil, fmt.Errorf("transport error: %w", err)
}
var ( var (
res = new(EACLRes) cc contextCall
procPrm processResponseV2Prm res EACLRes
procRes processResponseV2Res
) )
procPrm.callOpts = callOptions c.initCallContext(&cc)
procPrm.resp = resp cc.req = &req
cc.statusRes = &res
procRes.statusRes = res cc.call = func() (responseV2, error) {
return rpcapi.GetEACL(c.Raw(), &req, client.WithContext(ctx))
// process response in general
if c.processResponseV2(&procRes, procPrm) {
if procRes.cliErr != nil {
return nil, procRes.cliErr
}
return res, nil
} }
cc.result = func(r responseV2) {
resp := r.(*v2container.GetExtendedACLResponse)
body := resp.GetBody() body := resp.GetBody()
@ -466,35 +531,71 @@ func (c *Client) EACL(ctx context.Context, id *cid.ID, opts ...CallOption) (*EAC
signature.NewFromV2(body.GetSignature()), signature.NewFromV2(body.GetSignature()),
) )
res.SetTable(table) res.setTable(table)
}
return res, nil // process call
if !cc.processCall() {
return nil, cc.err
}
return &res, nil
} }
// SetEACLPrm groups parameters of SetEACL operation.
type SetEACLPrm struct {
prmSession
tableSet bool
table eacl.Table
}
// SetTable sets eACL table structure to be set for the container.
// Required parameter.
func (x *SetEACLPrm) SetTable(table eacl.Table) {
x.table = table
x.tableSet = true
}
// SetEACLRes groups resulting values of SetEACL operation.
type SetEACLRes struct { type SetEACLRes struct {
statusRes statusRes
} }
// SetEACL sets eACL through NeoFS API call. // SetEACL sends request to update eACL table of the NeoFS container.
// //
// Any client's internal or transport errors are returned as `error`. // Any client's internal or transport errors are returned as `error`.
// If WithNeoFSErrorParsing option has been provided, unsuccessful // If WithNeoFSErrorParsing option has been provided, unsuccessful
// NeoFS status codes are returned as `error`, otherwise, are included // NeoFS status codes are returned as `error`, otherwise, are included
// in the returned result structure. // in the returned result structure.
func (c *Client) SetEACL(ctx context.Context, eacl *eacl.Table, opts ...CallOption) (*SetEACLRes, error) { //
// apply all available options // Operation is asynchronous and no guaranteed even in the absence of errors.
callOptions := c.defaultCallOptions() // The required time is also not predictable.
//
for i := range opts { // Success can be verified by reading by identifier (see EACL).
opts[i](callOptions) //
// Immediately panics if parameters are set incorrectly (see SetEACLPrm docs).
// Context is required and must not be nil. It is used for network communication.
//
// Exactly one return value is non-nil. Server status return is returned in ContainerDeleteRes.
// Reflects all internal errors in second return value (transport problems, response processing, etc.).
func (c *Client) SetEACL(ctx context.Context, prm SetEACLPrm) (*SetEACLRes, error) {
// check parameters
switch {
case ctx == nil:
panic(panicMsgMissingContext)
case !prm.tableSet:
panic("eACL table not set")
} }
// form request body
reqBody := new(v2container.SetExtendedACLRequestBody) reqBody := new(v2container.SetExtendedACLRequestBody)
reqBody.SetEACL(eacl.ToV2()) reqBody.SetEACL(prm.table.ToV2())
// sign the eACL table
signWrapper := v2signature.StableMarshalerWrapper{SM: reqBody.GetEACL()} signWrapper := v2signature.StableMarshalerWrapper{SM: reqBody.GetEACL()}
err := sigutil.SignDataWithHandler(callOptions.key, signWrapper, func(key []byte, sig []byte) { err := sigutil.SignDataWithHandler(c.opts.key, signWrapper, func(key []byte, sig []byte) {
eaclSignature := new(refs.Signature) eaclSignature := new(refs.Signature)
eaclSignature.SetKey(key) eaclSignature.SetKey(key)
eaclSignature.SetSign(sig) eaclSignature.SetSign(sig)
@ -504,113 +605,116 @@ func (c *Client) SetEACL(ctx context.Context, eacl *eacl.Table, opts ...CallOpti
return nil, err return nil, err
} }
req := new(v2container.SetExtendedACLRequest) // form meta header
var meta v2session.RequestMetaHeader
prm.prmSession.writeToMetaHeader(&meta)
// form request
var req v2container.SetExtendedACLRequest
req.SetBody(reqBody) req.SetBody(reqBody)
req.SetMetaHeader(&meta)
meta := v2MetaHeaderFromOpts(callOptions) // init call context
meta.SetSessionToken(eacl.SessionToken().ToV2())
req.SetMetaHeader(meta)
err = v2signature.SignServiceMessage(callOptions.key, req)
if err != nil {
return nil, err
}
resp, err := rpcapi.SetEACL(c.Raw(), req, client.WithContext(ctx))
if err != nil {
return nil, fmt.Errorf("transport error: %w", err)
}
var ( var (
res = new(SetEACLRes) cc contextCall
procPrm processResponseV2Prm res SetEACLRes
procRes processResponseV2Res
) )
procPrm.callOpts = callOptions c.initCallContext(&cc)
procPrm.resp = resp cc.req = &req
cc.statusRes = &res
procRes.statusRes = res cc.call = func() (responseV2, error) {
return rpcapi.SetEACL(c.Raw(), &req, client.WithContext(ctx))
// process response in general
if c.processResponseV2(&procRes, procPrm) {
if procRes.cliErr != nil {
return nil, procRes.cliErr
} }
return res, nil // process call
if !cc.processCall() {
return nil, cc.err
} }
return res, nil return &res, nil
} }
// AnnounceSpacePrm groups parameters of AnnounceContainerUsedSpace operation.
type AnnounceSpacePrm struct {
announcements []container.UsedSpaceAnnouncement
}
// SetValues sets values describing volume of space that is used for the container objects.
// Required parameter. Must not be empty.
//
// Must not be mutated before the end of the operation.
func (x *AnnounceSpacePrm) SetValues(announcements []container.UsedSpaceAnnouncement) {
x.announcements = announcements
}
// AnnounceSpaceRes groups resulting values of AnnounceContainerUsedSpace operation.
type AnnounceSpaceRes struct { type AnnounceSpaceRes struct {
statusRes statusRes
} }
// AnnounceContainerUsedSpace used by storage nodes to estimate their container // AnnounceContainerUsedSpace sends request to announce volume of the space used for the container objects.
// sizes during lifetime. Use it only in storage node applications.
// //
// Any client's internal or transport errors are returned as `error`. // Any client's internal or transport errors are returned as `error`.
// If WithNeoFSErrorParsing option has been provided, unsuccessful // If WithNeoFSErrorParsing option has been provided, unsuccessful
// NeoFS status codes are returned as `error`, otherwise, are included // NeoFS status codes are returned as `error`, otherwise, are included
// in the returned result structure. // in the returned result structure.
func (c *Client) AnnounceContainerUsedSpace( //
ctx context.Context, // Operation is asynchronous and no guaranteed even in the absence of errors.
announce []container.UsedSpaceAnnouncement, // The required time is also not predictable.
opts ...CallOption, //
) (*AnnounceSpaceRes, error) { // At this moment success can not be checked.
callOptions := c.defaultCallOptions() // apply all available options //
// Immediately panics if parameters are set incorrectly (see AnnounceSpacePrm docs).
for i := range opts { // Context is required and must not be nil. It is used for network communication.
opts[i](callOptions) //
// Exactly one return value is non-nil. Server status return is returned in AnnounceSpaceRes.
// Reflects all internal errors in second return value (transport problems, response processing, etc.).
func (c *Client) AnnounceContainerUsedSpace(ctx context.Context, prm AnnounceSpacePrm) (*AnnounceSpaceRes, error) {
// check parameters
switch {
case ctx == nil:
panic(panicMsgMissingContext)
case len(prm.announcements) == 0:
panic("missing announcements")
} }
// convert list of SDK announcement structures into NeoFS-API v2 list // convert list of SDK announcement structures into NeoFS-API v2 list
v2announce := make([]*v2container.UsedSpaceAnnouncement, 0, len(announce)) v2announce := make([]*v2container.UsedSpaceAnnouncement, 0, len(prm.announcements))
for i := range announce { for i := range prm.announcements {
v2announce = append(v2announce, announce[i].ToV2()) v2announce = append(v2announce, prm.announcements[i].ToV2())
} }
// prepare body of the NeoFS-API v2 request and request itself // prepare body of the NeoFS-API v2 request and request itself
reqBody := new(v2container.AnnounceUsedSpaceRequestBody) reqBody := new(v2container.AnnounceUsedSpaceRequestBody)
reqBody.SetAnnouncements(v2announce) reqBody.SetAnnouncements(v2announce)
req := new(v2container.AnnounceUsedSpaceRequest) // form request
var req v2container.AnnounceUsedSpaceRequest
req.SetBody(reqBody) req.SetBody(reqBody)
req.SetMetaHeader(v2MetaHeaderFromOpts(callOptions))
// sign the request // init call context
err := v2signature.SignServiceMessage(callOptions.key, req)
if err != nil {
return nil, err
}
resp, err := rpcapi.AnnounceUsedSpace(c.Raw(), req, client.WithContext(ctx))
if err != nil {
return nil, fmt.Errorf("transport error: %w", err)
}
var ( var (
res = new(AnnounceSpaceRes) cc contextCall
procPrm processResponseV2Prm res AnnounceSpaceRes
procRes processResponseV2Res
) )
procPrm.callOpts = callOptions c.initCallContext(&cc)
procPrm.resp = resp cc.req = &req
cc.statusRes = &res
procRes.statusRes = res cc.call = func() (responseV2, error) {
return rpcapi.AnnounceUsedSpace(c.Raw(), &req, client.WithContext(ctx))
// process response in general
if c.processResponseV2(&procRes, procPrm) {
if procRes.cliErr != nil {
return nil, procRes.cliErr
} }
return res, nil // process call
if !cc.processCall() {
return nil, cc.err
} }
return res, nil return &res, nil
} }

View file

@ -2,116 +2,120 @@ package client
import ( import (
"context" "context"
"fmt"
v2netmap "github.com/nspcc-dev/neofs-api-go/v2/netmap" v2netmap "github.com/nspcc-dev/neofs-api-go/v2/netmap"
rpcapi "github.com/nspcc-dev/neofs-api-go/v2/rpc" rpcapi "github.com/nspcc-dev/neofs-api-go/v2/rpc"
"github.com/nspcc-dev/neofs-api-go/v2/rpc/client" "github.com/nspcc-dev/neofs-api-go/v2/rpc/client"
v2signature "github.com/nspcc-dev/neofs-api-go/v2/signature"
"github.com/nspcc-dev/neofs-sdk-go/netmap" "github.com/nspcc-dev/neofs-sdk-go/netmap"
"github.com/nspcc-dev/neofs-sdk-go/version" "github.com/nspcc-dev/neofs-sdk-go/version"
) )
// EndpointInfo represents versioned information about the node // EndpointInfoPrm groups parameters of EndpointInfo operation.
// specified in the client. //
type EndpointInfo struct { // At the moment the operation is not parameterized, however,
// the structure is still declared for backward compatibility.
type EndpointInfoPrm struct{}
// EndpointInfoRes group resulting values of EndpointInfo operation.
type EndpointInfoRes struct {
statusRes
version *version.Version version *version.Version
ni *netmap.NodeInfo ni *netmap.NodeInfo
} }
// LatestVersion returns latest NeoFS API version in use. // LatestVersion returns latest NeoFS API protocol's version in use.
func (e *EndpointInfo) LatestVersion() *version.Version { //
return e.version // Client doesn't retain value so modification is safe.
func (x EndpointInfoRes) LatestVersion() *version.Version {
return x.version
} }
// NodeInfo returns information about the NeoFS node. func (x *EndpointInfoRes) setLatestVersion(ver *version.Version) {
func (e *EndpointInfo) NodeInfo() *netmap.NodeInfo { x.version = ver
return e.ni
} }
type EndpointInfoRes struct { // NodeInfo returns information about the NeoFS node served on the remote endpoint.
statusRes //
// Client doesn't retain value so modification is safe.
info *EndpointInfo func (x EndpointInfoRes) NodeInfo() *netmap.NodeInfo {
return x.ni
} }
func (x EndpointInfoRes) Info() *EndpointInfo { func (x *EndpointInfoRes) setNodeInfo(info *netmap.NodeInfo) {
return x.info x.ni = info
} }
func (x *EndpointInfoRes) setInfo(info *EndpointInfo) { // EndpointInfo requests information about the storage node served on the remote endpoint.
x.info = info //
} // Method can be used as a health check to see if node is alive and responds to requests.
// EndpointInfo returns attributes, address and public key of the node, specified
// in client constructor via address or open connection. This can be used as a
// health check to see if node is alive and responses to requests.
// //
// Any client's internal or transport errors are returned as `error`. // Any client's internal or transport errors are returned as `error`.
// If WithNeoFSErrorParsing option has been provided, unsuccessful // If WithNeoFSErrorParsing option has been provided, unsuccessful
// NeoFS status codes are returned as `error`, otherwise, are included // NeoFS status codes are returned as `error`, otherwise, are included
// in the returned result structure. // in the returned result structure.
func (c *Client) EndpointInfo(ctx context.Context, opts ...CallOption) (*EndpointInfoRes, error) { //
// apply all available options // Immediately panics if parameters are set incorrectly (see EndpointInfoPrm docs).
callOptions := c.defaultCallOptions() // Context is required and must not be nil. It is used for network communication.
//
for i := range opts { // Exactly one return value is non-nil. Server status return is returned in EndpointInfoRes.
opts[i](callOptions) // Reflects all internal errors in second return value (transport problems, response processing, etc.).
func (c *Client) EndpointInfo(ctx context.Context, _ EndpointInfoPrm) (*EndpointInfoRes, error) {
// check context
if ctx == nil {
panic(panicMsgMissingContext)
} }
reqBody := new(v2netmap.LocalNodeInfoRequestBody) // form request
var req v2netmap.LocalNodeInfoRequest
req := new(v2netmap.LocalNodeInfoRequest) // init call context
req.SetBody(reqBody)
req.SetMetaHeader(v2MetaHeaderFromOpts(callOptions))
err := v2signature.SignServiceMessage(callOptions.key, req)
if err != nil {
return nil, err
}
resp, err := rpcapi.LocalNodeInfo(c.Raw(), req)
if err != nil {
return nil, fmt.Errorf("transport error: %w", err)
}
var ( var (
res = new(EndpointInfoRes) cc contextCall
procPrm processResponseV2Prm res EndpointInfoRes
procRes processResponseV2Res
) )
procPrm.callOpts = callOptions c.initCallContext(&cc)
procPrm.resp = resp cc.req = &req
cc.statusRes = &res
procRes.statusRes = res cc.call = func() (responseV2, error) {
return rpcapi.LocalNodeInfo(c.Raw(), &req, client.WithContext(ctx))
// process response in general
if c.processResponseV2(&procRes, procPrm) {
if procRes.cliErr != nil {
return nil, procRes.cliErr
}
return res, nil
} }
cc.result = func(r responseV2) {
resp := r.(*v2netmap.LocalNodeInfoResponse)
body := resp.GetBody() body := resp.GetBody()
res.setInfo(&EndpointInfo{ res.setLatestVersion(version.NewFromV2(body.GetVersion()))
version: version.NewFromV2(body.GetVersion()), res.setNodeInfo(netmap.NewNodeInfoFromV2(body.GetNodeInfo()))
ni: netmap.NewNodeInfoFromV2(body.GetNodeInfo()), }
})
return res, nil // process call
if !cc.processCall() {
return nil, cc.err
}
return &res, nil
} }
// NetworkInfoPrm groups parameters of NetworkInfo operation.
//
// At the moment the operation is not parameterized, however,
// the structure is still declared for backward compatibility.
type NetworkInfoPrm struct{}
// NetworkInfoRes groups resulting values of NetworkInfo operation.
type NetworkInfoRes struct { type NetworkInfoRes struct {
statusRes statusRes
info *netmap.NetworkInfo info *netmap.NetworkInfo
} }
// Info returns structured information about the NeoFS network.
//
// Client doesn't retain value so modification is safe.
func (x NetworkInfoRes) Info() *netmap.NetworkInfo { func (x NetworkInfoRes) Info() *netmap.NetworkInfo {
return x.info return x.info
} }
@ -120,57 +124,50 @@ func (x *NetworkInfoRes) setInfo(info *netmap.NetworkInfo) {
x.info = info x.info = info
} }
// NetworkInfo returns information about the NeoFS network of which the remote server is a part. // NetworkInfo requests information about the NeoFS network of which the remote server is a part.
// //
// Any client's internal or transport errors are returned as `error`. // Any client's internal or transport errors are returned as `error`.
// If WithNeoFSErrorParsing option has been provided, unsuccessful // If WithNeoFSErrorParsing option has been provided, unsuccessful
// NeoFS status codes are returned as `error`, otherwise, are included // NeoFS status codes are returned as `error`, otherwise, are included
// in the returned result structure. // in the returned result structure.
func (c *Client) NetworkInfo(ctx context.Context, opts ...CallOption) (*NetworkInfoRes, error) { //
// apply all available options // Immediately panics if parameters are set incorrectly (see NetworkInfoPrm docs).
callOptions := c.defaultCallOptions() // Context is required and must not be nil. It is used for network communication.
//
for i := range opts { // Exactly one return value is non-nil. Server status return is returned in NetworkInfoRes.
opts[i](callOptions) // Reflects all internal errors in second return value (transport problems, response processing, etc.).
func (c *Client) NetworkInfo(ctx context.Context, _ NetworkInfoPrm) (*NetworkInfoRes, error) {
// check context
if ctx == nil {
panic(panicMsgMissingContext)
} }
reqBody := new(v2netmap.NetworkInfoRequestBody) // form request
var req v2netmap.NetworkInfoRequest
req := new(v2netmap.NetworkInfoRequest) // init call context
req.SetBody(reqBody)
req.SetMetaHeader(v2MetaHeaderFromOpts(callOptions))
err := v2signature.SignServiceMessage(callOptions.key, req)
if err != nil {
return nil, err
}
resp, err := rpcapi.NetworkInfo(c.Raw(), req, client.WithContext(ctx))
if err != nil {
return nil, fmt.Errorf("v2 NetworkInfo RPC failure: %w", err)
}
var ( var (
res = new(NetworkInfoRes) cc contextCall
procPrm processResponseV2Prm res NetworkInfoRes
procRes processResponseV2Res
) )
procPrm.callOpts = callOptions c.initCallContext(&cc)
procPrm.resp = resp cc.req = &req
cc.statusRes = &res
procRes.statusRes = res cc.call = func() (responseV2, error) {
return rpcapi.NetworkInfo(c.Raw(), &req, client.WithContext(ctx))
// process response in general
if c.processResponseV2(&procRes, procPrm) {
if procRes.cliErr != nil {
return nil, procRes.cliErr
}
return res, nil
} }
cc.result = func(r responseV2) {
resp := r.(*v2netmap.NetworkInfoResponse)
res.setInfo(netmap.NewNetworkInfoFromV2(resp.GetBody().GetNetworkInfo())) res.setInfo(netmap.NewNetworkInfoFromV2(resp.GetBody().GetNetworkInfo()))
}
return res, nil // process call
if !cc.processCall() {
return nil, cc.err
}
return &res, nil
} }

View file

@ -1461,17 +1461,11 @@ func (c *Client) attachV2SessionToken(opts *callOptions, hdr *v2session.RequestM
opCtx.SetAddress(info.addr) opCtx.SetAddress(info.addr)
opCtx.SetVerb(info.verb) opCtx.SetVerb(info.verb)
lt := new(v2session.TokenLifetime)
lt.SetIat(info.iat)
lt.SetNbf(info.nbf)
lt.SetExp(info.exp)
body := new(v2session.SessionTokenBody) body := new(v2session.SessionTokenBody)
body.SetID(opts.session.ID()) body.SetID(opts.session.ID())
body.SetOwnerID(opts.session.OwnerID().ToV2()) body.SetOwnerID(opts.session.OwnerID().ToV2())
body.SetSessionKey(opts.session.SessionKey()) body.SetSessionKey(opts.session.SessionKey())
body.SetContext(opCtx) body.SetContext(opCtx)
body.SetLifetime(lt)
token := new(v2session.SessionToken) token := new(v2session.SessionToken)
token.SetBody(body) token.SetBody(body)

View file

@ -1,94 +0,0 @@
package client
import (
"io"
"testing"
"github.com/nspcc-dev/neofs-api-go/v2/object"
"github.com/nspcc-dev/neofs-api-go/v2/signature"
"github.com/nspcc-dev/neofs-crypto/test"
"github.com/stretchr/testify/require"
)
type singleResponseStream struct {
called bool
resp object.GetResponse
}
func (x *singleResponseStream) Read(r *object.GetResponse) error {
if x.called {
return io.EOF
}
x.called = true
*r = x.resp
return nil
}
var key = test.DecodeKey(0)
func chunkResponse(c []byte) (r object.GetResponse) {
chunkPart := new(object.GetObjectPartChunk)
chunkPart.SetChunk(c)
body := new(object.GetResponseBody)
body.SetObjectPart(chunkPart)
r.SetBody(body)
if err := signature.SignServiceMessage(key, &r); err != nil {
panic(err)
}
return
}
func data(sz int) []byte {
data := make([]byte, sz)
for i := range data {
data[i] = byte(i) % ^byte(0)
}
return data
}
func checkFullRead(t *testing.T, r io.Reader, buf, payload []byte) {
var (
restored []byte
read int
)
for {
n, err := r.Read(buf)
read += n
restored = append(restored, buf[:n]...)
if err != nil {
require.Equal(t, err, io.EOF)
break
}
}
require.Equal(t, payload, restored)
require.EqualValues(t, len(payload), read)
}
func TestObjectPayloadReader_Read(t *testing.T) {
t.Run("read with tail", func(t *testing.T) {
payload := data(10)
buf := make([]byte, len(payload)-1)
var r io.Reader = &objectPayloadReader{
stream: &singleResponseStream{
resp: chunkResponse(payload),
},
}
checkFullRead(t, r, buf, payload)
})
}

View file

@ -51,8 +51,6 @@ type (
v2SessionReqInfo struct { v2SessionReqInfo struct {
addr *refs.Address addr *refs.Address
verb v2session.ObjectSessionVerb verb v2session.ObjectSessionVerb
exp, nbf, iat uint64
} }
) )

View file

@ -6,7 +6,6 @@ import (
v2reputation "github.com/nspcc-dev/neofs-api-go/v2/reputation" v2reputation "github.com/nspcc-dev/neofs-api-go/v2/reputation"
rpcapi "github.com/nspcc-dev/neofs-api-go/v2/rpc" rpcapi "github.com/nspcc-dev/neofs-api-go/v2/rpc"
"github.com/nspcc-dev/neofs-api-go/v2/rpc/client" "github.com/nspcc-dev/neofs-api-go/v2/rpc/client"
v2signature "github.com/nspcc-dev/neofs-api-go/v2/signature"
"github.com/nspcc-dev/neofs-sdk-go/reputation" "github.com/nspcc-dev/neofs-sdk-go/reputation"
) )
@ -14,26 +13,20 @@ import (
type AnnounceLocalTrustPrm struct { type AnnounceLocalTrustPrm struct {
epoch uint64 epoch uint64
trusts []*reputation.Trust trusts []reputation.Trust
} }
// Epoch returns epoch in which the trust was assessed. // SetEpoch sets number of NeoFS epoch in which the trust was assessed.
func (x AnnounceLocalTrustPrm) Epoch() uint64 { // Required parameter, must not be zero.
return x.epoch
}
// SetEpoch sets epoch in which the trust was assessed.
func (x *AnnounceLocalTrustPrm) SetEpoch(epoch uint64) { func (x *AnnounceLocalTrustPrm) SetEpoch(epoch uint64) {
x.epoch = epoch x.epoch = epoch
} }
// Trusts returns list of local trust values. // SetValues sets values describing trust of the client to the NeoFS network participants.
func (x AnnounceLocalTrustPrm) Trusts() []*reputation.Trust { // Required parameter. Must not be empty.
return x.trusts //
} // Must not be mutated before the end of the operation.
func (x *AnnounceLocalTrustPrm) SetValues(trusts []reputation.Trust) {
// SetTrusts sets list of local trust values.
func (x *AnnounceLocalTrustPrm) SetTrusts(trusts []*reputation.Trust) {
x.trusts = trusts x.trusts = trusts
} }
@ -42,59 +35,66 @@ type AnnounceLocalTrustRes struct {
statusRes statusRes
} }
// AnnounceLocalTrust announces node's local trusts through NeoFS API call. // AnnounceLocalTrust sends client's trust values to the NeoFS network participants.
// //
// Any client's internal or transport errors are returned as `error`. // Any client's internal or transport errors are returned as `error`.
// If WithNeoFSErrorParsing option has been provided, unsuccessful // If WithNeoFSErrorParsing option has been provided, unsuccessful
// NeoFS status codes are returned as `error`, otherwise, are included // NeoFS status codes are returned as `error`, otherwise, are included
// in the returned result structure. // in the returned result structure.
func (c *Client) AnnounceLocalTrust(ctx context.Context, prm AnnounceLocalTrustPrm, opts ...CallOption) (*AnnounceLocalTrustRes, error) { //
// apply all available options // Immediately panics if parameters are set incorrectly (see AnnounceLocalTrustPrm docs).
callOptions := c.defaultCallOptions() // Context is required and must not be nil. It is used for network communication.
//
for i := range opts { // Exactly one return value is non-nil. Server status return is returned in AnnounceLocalTrustRes.
opts[i](callOptions) // Reflects all internal errors in second return value (transport problems, response processing, etc.).
func (c *Client) AnnounceLocalTrust(ctx context.Context, prm AnnounceLocalTrustPrm) (*AnnounceLocalTrustRes, error) {
// check parameters
switch {
case ctx == nil:
panic(panicMsgMissingContext)
case prm.epoch == 0:
panic("zero epoch")
case len(prm.trusts) == 0:
panic("missing trusts")
} }
// form request body
reqBody := new(v2reputation.AnnounceLocalTrustRequestBody) reqBody := new(v2reputation.AnnounceLocalTrustRequestBody)
reqBody.SetEpoch(prm.Epoch()) reqBody.SetEpoch(prm.epoch)
reqBody.SetTrusts(reputation.TrustsToV2(prm.Trusts()))
trusts := make([]*reputation.Trust, 0, len(prm.trusts))
for i := range prm.trusts {
trusts = append(trusts, &prm.trusts[i])
}
reqBody.SetTrusts(reputation.TrustsToV2(trusts))
// form request
var req v2reputation.AnnounceLocalTrustRequest
req := new(v2reputation.AnnounceLocalTrustRequest)
req.SetBody(reqBody) req.SetBody(reqBody)
req.SetMetaHeader(v2MetaHeaderFromOpts(callOptions))
err := v2signature.SignServiceMessage(callOptions.key, req) // init call context
if err != nil {
return nil, err
}
resp, err := rpcapi.AnnounceLocalTrust(c.Raw(), req, client.WithContext(ctx))
if err != nil {
return nil, err
}
var ( var (
res = new(AnnounceLocalTrustRes) cc contextCall
procPrm processResponseV2Prm res AnnounceLocalTrustRes
procRes processResponseV2Res
) )
procPrm.callOpts = callOptions c.initCallContext(&cc)
procPrm.resp = resp cc.req = &req
cc.statusRes = &res
procRes.statusRes = res cc.call = func() (responseV2, error) {
return rpcapi.AnnounceLocalTrust(c.Raw(), &req, client.WithContext(ctx))
// process response in general
if c.processResponseV2(&procRes, procPrm) {
if procRes.cliErr != nil {
return nil, procRes.cliErr
} }
return res, nil // process call
if !cc.processCall() {
return nil, cc.err
} }
return res, nil return &res, nil
} }
// AnnounceIntermediateTrustPrm groups parameters of AnnounceIntermediateTrust operation. // AnnounceIntermediateTrustPrm groups parameters of AnnounceIntermediateTrust operation.
@ -103,35 +103,27 @@ type AnnounceIntermediateTrustPrm struct {
iter uint32 iter uint32
trust *reputation.PeerToPeerTrust trustSet bool
} trust reputation.PeerToPeerTrust
func (x *AnnounceIntermediateTrustPrm) Epoch() uint64 {
return x.epoch
} }
// SetEpoch sets number of NeoFS epoch with which client's calculation algorithm is initialized.
// Required parameter, must not be zero.
func (x *AnnounceIntermediateTrustPrm) SetEpoch(epoch uint64) { func (x *AnnounceIntermediateTrustPrm) SetEpoch(epoch uint64) {
x.epoch = epoch x.epoch = epoch
} }
// Iteration returns sequence number of the iteration. // SetIteration sets current sequence number of the client's calculation algorithm.
func (x AnnounceIntermediateTrustPrm) Iteration() uint32 { // By default, corresponds to initial (zero) iteration.
return x.iter
}
// SetIteration sets sequence number of the iteration.
func (x *AnnounceIntermediateTrustPrm) SetIteration(iter uint32) { func (x *AnnounceIntermediateTrustPrm) SetIteration(iter uint32) {
x.iter = iter x.iter = iter
} }
// Trust returns current global trust value computed at the specified iteration. // SetCurrentValue sets current global trust value computed at the specified iteration
func (x AnnounceIntermediateTrustPrm) Trust() *reputation.PeerToPeerTrust { //of the client's calculation algorithm. Required parameter.
return x.trust func (x *AnnounceIntermediateTrustPrm) SetCurrentValue(trust reputation.PeerToPeerTrust) {
}
// SetTrust sets current global trust value computed at the specified iteration.
func (x *AnnounceIntermediateTrustPrm) SetTrust(trust *reputation.PeerToPeerTrust) {
x.trust = trust x.trust = trust
x.trustSet = true
} }
// AnnounceIntermediateTrustRes groups results of AnnounceIntermediateTrust operation. // AnnounceIntermediateTrustRes groups results of AnnounceIntermediateTrust operation.
@ -139,58 +131,59 @@ type AnnounceIntermediateTrustRes struct {
statusRes statusRes
} }
// AnnounceIntermediateTrust announces node's intermediate trusts through NeoFS API call. // AnnounceIntermediateTrust sends global trust values calculated for the specified NeoFS network participants
// at some stage of client's calculation algorithm.
// //
// Any client's internal or transport errors are returned as `error`. // Any client's internal or transport errors are returned as `error`.
// If WithNeoFSErrorParsing option has been provided, unsuccessful // If WithNeoFSErrorParsing option has been provided, unsuccessful
// NeoFS status codes are returned as `error`, otherwise, are included // NeoFS status codes are returned as `error`, otherwise, are included
// in the returned result structure. // in the returned result structure.
func (c *Client) AnnounceIntermediateTrust(ctx context.Context, prm AnnounceIntermediateTrustPrm, opts ...CallOption) (*AnnounceIntermediateTrustRes, error) { //
// apply all available options // Immediately panics if parameters are set incorrectly (see AnnounceIntermediateTrustPrm docs).
callOptions := c.defaultCallOptions() // Context is required and must not be nil. It is used for network communication.
//
for i := range opts { // Exactly one return value is non-nil. Server status return is returned in AnnounceIntermediateTrustRes.
opts[i](callOptions) // Reflects all internal errors in second return value (transport problems, response processing, etc.).
func (c *Client) AnnounceIntermediateTrust(ctx context.Context, prm AnnounceIntermediateTrustPrm) (*AnnounceIntermediateTrustRes, error) {
// check parameters
switch {
case ctx == nil:
panic(panicMsgMissingContext)
case prm.epoch == 0:
panic("zero epoch")
case !prm.trustSet:
panic("current trust value not set")
} }
// form request body
reqBody := new(v2reputation.AnnounceIntermediateResultRequestBody) reqBody := new(v2reputation.AnnounceIntermediateResultRequestBody)
reqBody.SetEpoch(prm.Epoch()) reqBody.SetEpoch(prm.epoch)
reqBody.SetIteration(prm.Iteration()) reqBody.SetIteration(prm.iter)
reqBody.SetTrust(prm.Trust().ToV2()) reqBody.SetTrust(prm.trust.ToV2())
// form request
var req v2reputation.AnnounceIntermediateResultRequest
req := new(v2reputation.AnnounceIntermediateResultRequest)
req.SetBody(reqBody) req.SetBody(reqBody)
req.SetMetaHeader(v2MetaHeaderFromOpts(callOptions))
err := v2signature.SignServiceMessage(callOptions.key, req) // init call context
if err != nil {
return nil, err
}
resp, err := rpcapi.AnnounceIntermediateResult(c.Raw(), req, client.WithContext(ctx))
if err != nil {
return nil, err
}
var ( var (
res = new(AnnounceIntermediateTrustRes) cc contextCall
procPrm processResponseV2Prm res AnnounceIntermediateTrustRes
procRes processResponseV2Res
) )
procPrm.callOpts = callOptions c.initCallContext(&cc)
procPrm.resp = resp cc.req = &req
cc.statusRes = &res
procRes.statusRes = res cc.call = func() (responseV2, error) {
return rpcapi.AnnounceIntermediateResult(c.Raw(), &req, client.WithContext(ctx))
// process response in general
if c.processResponseV2(&procRes, procPrm) {
if procRes.cliErr != nil {
return nil, procRes.cliErr
} }
return res, nil // process call
if !cc.processCall() {
return nil, cc.err
} }
return res, nil return &res, nil
} }

View file

@ -2,18 +2,24 @@ package client
import ( import (
"context" "context"
"errors"
"fmt"
rpcapi "github.com/nspcc-dev/neofs-api-go/v2/rpc" rpcapi "github.com/nspcc-dev/neofs-api-go/v2/rpc"
"github.com/nspcc-dev/neofs-api-go/v2/rpc/client" "github.com/nspcc-dev/neofs-api-go/v2/rpc/client"
v2session "github.com/nspcc-dev/neofs-api-go/v2/session" v2session "github.com/nspcc-dev/neofs-api-go/v2/session"
v2signature "github.com/nspcc-dev/neofs-api-go/v2/signature"
"github.com/nspcc-dev/neofs-sdk-go/owner" "github.com/nspcc-dev/neofs-sdk-go/owner"
) )
var errMalformedResponseBody = errors.New("malformed response body") // CreateSessionPrm groups parameters of CreateSession operation.
type CreateSessionPrm struct {
exp uint64
}
// SetExp sets number of the last NepFS epoch in the lifetime of the session after which it will be expired.
func (x *CreateSessionPrm) SetExp(exp uint64) {
x.exp = exp
}
// CreateSessionRes groups resulting values of CreateSession operation.
type CreateSessionRes struct { type CreateSessionRes struct {
statusRes statusRes
@ -26,6 +32,9 @@ func (x *CreateSessionRes) setID(id []byte) {
x.id = id x.id = id
} }
// ID returns identifier of the opened session in a binary NeoFS API protocol format.
//
// Client doesn't retain value so modification is safe.
func (x CreateSessionRes) ID() []byte { func (x CreateSessionRes) ID() []byte {
return x.id return x.id
} }
@ -34,66 +43,69 @@ func (x *CreateSessionRes) setSessionKey(key []byte) {
x.sessionKey = key x.sessionKey = key
} }
func (x CreateSessionRes) SessionKey() []byte { // PublicKey returns public key of the opened session in a binary NeoFS API protocol format.
func (x CreateSessionRes) PublicKey() []byte {
return x.sessionKey return x.sessionKey
} }
// CreateSession creates session through NeoFS API call. // CreateSession opens a session with the node server on the remote endpoint.
// The session lifetime coincides with the server lifetime. Results can be written
// to session token which can be later attached to the requests.
// //
// Any client's internal or transport errors are returned as error, // Any client's internal or transport errors are returned as `error`.
// NeoFS status codes are included in the returned results. // If WithNeoFSErrorParsing option has been provided, unsuccessful
func (c *Client) CreateSession(ctx context.Context, expiration uint64, opts ...CallOption) (*CreateSessionRes, error) { // NeoFS status codes are returned as `error`, otherwise, are included
// apply all available options // in the returned result structure.
callOptions := c.defaultCallOptions() //
// Immediately panics if parameters are set incorrectly (see CreateSessionPrm docs).
for i := range opts { // Context is required and must not be nil. It is used for network communication.
opts[i](callOptions) //
// Exactly one return value is non-nil. Server status return is returned in CreateSessionRes.
// Reflects all internal errors in second return value (transport problems, response processing, etc.).
func (c *Client) CreateSession(ctx context.Context, prm CreateSessionPrm) (*CreateSessionRes, error) {
// check context
if ctx == nil {
panic(panicMsgMissingContext)
} }
ownerID := owner.NewIDFromPublicKey(&callOptions.key.PublicKey) ownerID := owner.NewIDFromPublicKey(&c.opts.key.PublicKey)
// form request body
reqBody := new(v2session.CreateRequestBody) reqBody := new(v2session.CreateRequestBody)
reqBody.SetOwnerID(ownerID.ToV2()) reqBody.SetOwnerID(ownerID.ToV2())
reqBody.SetExpiration(expiration) reqBody.SetExpiration(prm.exp)
// for request
var req v2session.CreateRequest
req := new(v2session.CreateRequest)
req.SetBody(reqBody) req.SetBody(reqBody)
req.SetMetaHeader(v2MetaHeaderFromOpts(callOptions))
err := v2signature.SignServiceMessage(callOptions.key, req) // init call context
if err != nil {
return nil, err
}
resp, err := rpcapi.CreateSession(c.Raw(), req, client.WithContext(ctx))
if err != nil {
return nil, fmt.Errorf("transport error: %w", err)
}
var ( var (
res = new(CreateSessionRes) cc contextCall
procPrm processResponseV2Prm res CreateSessionRes
procRes processResponseV2Res
) )
procPrm.callOpts = callOptions c.initCallContext(&cc)
procPrm.resp = resp cc.req = &req
cc.statusRes = &res
procRes.statusRes = res cc.call = func() (responseV2, error) {
return rpcapi.CreateSession(c.Raw(), &req, client.WithContext(ctx))
// process response in general
if c.processResponseV2(&procRes, procPrm) {
if procRes.cliErr != nil {
return nil, procRes.cliErr
}
return res, nil
} }
cc.result = func(r responseV2) {
resp := r.(*v2session.CreateResponse)
body := resp.GetBody() body := resp.GetBody()
res.setID(body.GetID()) res.setID(body.GetID())
res.setSessionKey(body.GetSessionKey()) res.setSessionKey(body.GetSessionKey())
}
return res, nil // process call
if !cc.processCall() {
return nil, cc.err
}
return &res, nil
} }

View file

@ -12,10 +12,6 @@ import (
gomock "github.com/golang/mock/gomock" gomock "github.com/golang/mock/gomock"
client "github.com/nspcc-dev/neofs-api-go/v2/rpc/client" client "github.com/nspcc-dev/neofs-api-go/v2/rpc/client"
client0 "github.com/nspcc-dev/neofs-sdk-go/client" client0 "github.com/nspcc-dev/neofs-sdk-go/client"
container "github.com/nspcc-dev/neofs-sdk-go/container"
cid "github.com/nspcc-dev/neofs-sdk-go/container/id"
eacl "github.com/nspcc-dev/neofs-sdk-go/eacl"
owner "github.com/nspcc-dev/neofs-sdk-go/owner"
) )
// MockClient is a mock of Client interface. // MockClient is a mock of Client interface.
@ -42,12 +38,9 @@ func (m *MockClient) EXPECT() *MockClientMockRecorder {
} }
// AnnounceContainerUsedSpace mocks base method. // AnnounceContainerUsedSpace mocks base method.
func (m *MockClient) AnnounceContainerUsedSpace(arg0 context.Context, arg1 []container.UsedSpaceAnnouncement, arg2 ...client0.CallOption) (*client0.AnnounceSpaceRes, error) { func (m *MockClient) AnnounceContainerUsedSpace(arg0 context.Context, arg1 client0.AnnounceSpacePrm) (*client0.AnnounceSpaceRes, error) {
m.ctrl.T.Helper() m.ctrl.T.Helper()
varargs := []interface{}{arg0, arg1} varargs := []interface{}{arg0, arg1}
for _, a := range arg2 {
varargs = append(varargs, a)
}
ret := m.ctrl.Call(m, "AnnounceContainerUsedSpace", varargs...) ret := m.ctrl.Call(m, "AnnounceContainerUsedSpace", varargs...)
ret0, _ := ret[0].(*client0.AnnounceSpaceRes) ret0, _ := ret[0].(*client0.AnnounceSpaceRes)
ret1, _ := ret[1].(error) ret1, _ := ret[1].(error)
@ -55,19 +48,16 @@ func (m *MockClient) AnnounceContainerUsedSpace(arg0 context.Context, arg1 []con
} }
// AnnounceContainerUsedSpace indicates an expected call of AnnounceContainerUsedSpace. // AnnounceContainerUsedSpace indicates an expected call of AnnounceContainerUsedSpace.
func (mr *MockClientMockRecorder) AnnounceContainerUsedSpace(arg0, arg1 interface{}, arg2 ...interface{}) *gomock.Call { func (mr *MockClientMockRecorder) AnnounceContainerUsedSpace(arg0, arg1 interface{}) *gomock.Call {
mr.mock.ctrl.T.Helper() mr.mock.ctrl.T.Helper()
varargs := append([]interface{}{arg0, arg1}, arg2...) varargs := []interface{}{arg0, arg1}
return mr.mock.ctrl.RecordCallWithMethodType(mr.mock, "AnnounceContainerUsedSpace", reflect.TypeOf((*MockClient)(nil).AnnounceContainerUsedSpace), varargs...) return mr.mock.ctrl.RecordCallWithMethodType(mr.mock, "AnnounceContainerUsedSpace", reflect.TypeOf((*MockClient)(nil).AnnounceContainerUsedSpace), varargs...)
} }
// AnnounceIntermediateTrust mocks base method. // AnnounceIntermediateTrust mocks base method.
func (m *MockClient) AnnounceIntermediateTrust(arg0 context.Context, arg1 client0.AnnounceIntermediateTrustPrm, arg2 ...client0.CallOption) (*client0.AnnounceIntermediateTrustRes, error) { func (m *MockClient) AnnounceIntermediateTrust(arg0 context.Context, arg1 client0.AnnounceIntermediateTrustPrm) (*client0.AnnounceIntermediateTrustRes, error) {
m.ctrl.T.Helper() m.ctrl.T.Helper()
varargs := []interface{}{arg0, arg1} varargs := []interface{}{arg0, arg1}
for _, a := range arg2 {
varargs = append(varargs, a)
}
ret := m.ctrl.Call(m, "AnnounceIntermediateTrust", varargs...) ret := m.ctrl.Call(m, "AnnounceIntermediateTrust", varargs...)
ret0, _ := ret[0].(*client0.AnnounceIntermediateTrustRes) ret0, _ := ret[0].(*client0.AnnounceIntermediateTrustRes)
ret1, _ := ret[1].(error) ret1, _ := ret[1].(error)
@ -75,19 +65,16 @@ func (m *MockClient) AnnounceIntermediateTrust(arg0 context.Context, arg1 client
} }
// AnnounceIntermediateTrust indicates an expected call of AnnounceIntermediateTrust. // AnnounceIntermediateTrust indicates an expected call of AnnounceIntermediateTrust.
func (mr *MockClientMockRecorder) AnnounceIntermediateTrust(arg0, arg1 interface{}, arg2 ...interface{}) *gomock.Call { func (mr *MockClientMockRecorder) AnnounceIntermediateTrust(arg0, arg1 interface{}) *gomock.Call {
mr.mock.ctrl.T.Helper() mr.mock.ctrl.T.Helper()
varargs := append([]interface{}{arg0, arg1}, arg2...) varargs := []interface{}{arg0, arg1}
return mr.mock.ctrl.RecordCallWithMethodType(mr.mock, "AnnounceIntermediateTrust", reflect.TypeOf((*MockClient)(nil).AnnounceIntermediateTrust), varargs...) return mr.mock.ctrl.RecordCallWithMethodType(mr.mock, "AnnounceIntermediateTrust", reflect.TypeOf((*MockClient)(nil).AnnounceIntermediateTrust), varargs...)
} }
// AnnounceLocalTrust mocks base method. // AnnounceLocalTrust mocks base method.
func (m *MockClient) AnnounceLocalTrust(arg0 context.Context, arg1 client0.AnnounceLocalTrustPrm, arg2 ...client0.CallOption) (*client0.AnnounceLocalTrustRes, error) { func (m *MockClient) AnnounceLocalTrust(arg0 context.Context, arg1 client0.AnnounceLocalTrustPrm) (*client0.AnnounceLocalTrustRes, error) {
m.ctrl.T.Helper() m.ctrl.T.Helper()
varargs := []interface{}{arg0, arg1} varargs := []interface{}{arg0, arg1}
for _, a := range arg2 {
varargs = append(varargs, a)
}
ret := m.ctrl.Call(m, "AnnounceLocalTrust", varargs...) ret := m.ctrl.Call(m, "AnnounceLocalTrust", varargs...)
ret0, _ := ret[0].(*client0.AnnounceLocalTrustRes) ret0, _ := ret[0].(*client0.AnnounceLocalTrustRes)
ret1, _ := ret[1].(error) ret1, _ := ret[1].(error)
@ -95,9 +82,9 @@ func (m *MockClient) AnnounceLocalTrust(arg0 context.Context, arg1 client0.Annou
} }
// AnnounceLocalTrust indicates an expected call of AnnounceLocalTrust. // AnnounceLocalTrust indicates an expected call of AnnounceLocalTrust.
func (mr *MockClientMockRecorder) AnnounceLocalTrust(arg0, arg1 interface{}, arg2 ...interface{}) *gomock.Call { func (mr *MockClientMockRecorder) AnnounceLocalTrust(arg0, arg1 interface{}) *gomock.Call {
mr.mock.ctrl.T.Helper() mr.mock.ctrl.T.Helper()
varargs := append([]interface{}{arg0, arg1}, arg2...) varargs := []interface{}{arg0, arg1}
return mr.mock.ctrl.RecordCallWithMethodType(mr.mock, "AnnounceLocalTrust", reflect.TypeOf((*MockClient)(nil).AnnounceLocalTrust), varargs...) return mr.mock.ctrl.RecordCallWithMethodType(mr.mock, "AnnounceLocalTrust", reflect.TypeOf((*MockClient)(nil).AnnounceLocalTrust), varargs...)
} }
@ -116,12 +103,9 @@ func (mr *MockClientMockRecorder) Conn() *gomock.Call {
} }
// CreateSession mocks base method. // CreateSession mocks base method.
func (m *MockClient) CreateSession(arg0 context.Context, arg1 uint64, arg2 ...client0.CallOption) (*client0.CreateSessionRes, error) { func (m *MockClient) CreateSession(arg0 context.Context, arg1 client0.CreateSessionPrm) (*client0.CreateSessionRes, error) {
m.ctrl.T.Helper() m.ctrl.T.Helper()
varargs := []interface{}{arg0, arg1} varargs := []interface{}{arg0, arg1}
for _, a := range arg2 {
varargs = append(varargs, a)
}
ret := m.ctrl.Call(m, "CreateSession", varargs...) ret := m.ctrl.Call(m, "CreateSession", varargs...)
ret0, _ := ret[0].(*client0.CreateSessionRes) ret0, _ := ret[0].(*client0.CreateSessionRes)
ret1, _ := ret[1].(error) ret1, _ := ret[1].(error)
@ -129,19 +113,16 @@ func (m *MockClient) CreateSession(arg0 context.Context, arg1 uint64, arg2 ...cl
} }
// CreateSession indicates an expected call of CreateSession. // CreateSession indicates an expected call of CreateSession.
func (mr *MockClientMockRecorder) CreateSession(arg0, arg1 interface{}, arg2 ...interface{}) *gomock.Call { func (mr *MockClientMockRecorder) CreateSession(arg0, arg1 interface{}) *gomock.Call {
mr.mock.ctrl.T.Helper() mr.mock.ctrl.T.Helper()
varargs := append([]interface{}{arg0, arg1}, arg2...) varargs := []interface{}{arg0, arg1}
return mr.mock.ctrl.RecordCallWithMethodType(mr.mock, "CreateSession", reflect.TypeOf((*MockClient)(nil).CreateSession), varargs...) return mr.mock.ctrl.RecordCallWithMethodType(mr.mock, "CreateSession", reflect.TypeOf((*MockClient)(nil).CreateSession), varargs...)
} }
// DeleteContainer mocks base method. // DeleteContainer mocks base method.
func (m *MockClient) DeleteContainer(arg0 context.Context, arg1 *cid.ID, arg2 ...client0.CallOption) (*client0.ContainerDeleteRes, error) { func (m *MockClient) DeleteContainer(arg0 context.Context, arg1 client0.ContainerDeletePrm) (*client0.ContainerDeleteRes, error) {
m.ctrl.T.Helper() m.ctrl.T.Helper()
varargs := []interface{}{arg0, arg1} varargs := []interface{}{arg0, arg1}
for _, a := range arg2 {
varargs = append(varargs, a)
}
ret := m.ctrl.Call(m, "DeleteContainer", varargs...) ret := m.ctrl.Call(m, "DeleteContainer", varargs...)
ret0, _ := ret[0].(*client0.ContainerDeleteRes) ret0, _ := ret[0].(*client0.ContainerDeleteRes)
ret1, _ := ret[1].(error) ret1, _ := ret[1].(error)
@ -149,9 +130,9 @@ func (m *MockClient) DeleteContainer(arg0 context.Context, arg1 *cid.ID, arg2 ..
} }
// DeleteContainer indicates an expected call of DeleteContainer. // DeleteContainer indicates an expected call of DeleteContainer.
func (mr *MockClientMockRecorder) DeleteContainer(arg0, arg1 interface{}, arg2 ...interface{}) *gomock.Call { func (mr *MockClientMockRecorder) DeleteContainer(arg0, arg1 interface{}) *gomock.Call {
mr.mock.ctrl.T.Helper() mr.mock.ctrl.T.Helper()
varargs := append([]interface{}{arg0, arg1}, arg2...) varargs := []interface{}{arg0, arg1}
return mr.mock.ctrl.RecordCallWithMethodType(mr.mock, "DeleteContainer", reflect.TypeOf((*MockClient)(nil).DeleteContainer), varargs...) return mr.mock.ctrl.RecordCallWithMethodType(mr.mock, "DeleteContainer", reflect.TypeOf((*MockClient)(nil).DeleteContainer), varargs...)
} }
@ -176,12 +157,9 @@ func (mr *MockClientMockRecorder) DeleteObject(arg0, arg1 interface{}, arg2 ...i
} }
// EACL mocks base method. // EACL mocks base method.
func (m *MockClient) EACL(arg0 context.Context, arg1 *cid.ID, arg2 ...client0.CallOption) (*client0.EACLRes, error) { func (m *MockClient) EACL(arg0 context.Context, arg1 client0.EACLPrm) (*client0.EACLRes, error) {
m.ctrl.T.Helper() m.ctrl.T.Helper()
varargs := []interface{}{arg0, arg1} varargs := []interface{}{arg0, arg1}
for _, a := range arg2 {
varargs = append(varargs, a)
}
ret := m.ctrl.Call(m, "EACL", varargs...) ret := m.ctrl.Call(m, "EACL", varargs...)
ret0, _ := ret[0].(*client0.EACLRes) ret0, _ := ret[0].(*client0.EACLRes)
ret1, _ := ret[1].(error) ret1, _ := ret[1].(error)
@ -189,19 +167,16 @@ func (m *MockClient) EACL(arg0 context.Context, arg1 *cid.ID, arg2 ...client0.Ca
} }
// EACL indicates an expected call of EACL. // EACL indicates an expected call of EACL.
func (mr *MockClientMockRecorder) EACL(arg0, arg1 interface{}, arg2 ...interface{}) *gomock.Call { func (mr *MockClientMockRecorder) EACL(arg0, arg1 interface{}) *gomock.Call {
mr.mock.ctrl.T.Helper() mr.mock.ctrl.T.Helper()
varargs := append([]interface{}{arg0, arg1}, arg2...) varargs := []interface{}{arg0, arg1}
return mr.mock.ctrl.RecordCallWithMethodType(mr.mock, "EACL", reflect.TypeOf((*MockClient)(nil).EACL), varargs...) return mr.mock.ctrl.RecordCallWithMethodType(mr.mock, "EACL", reflect.TypeOf((*MockClient)(nil).EACL), varargs...)
} }
// EndpointInfo mocks base method. // EndpointInfo mocks base method.
func (m *MockClient) EndpointInfo(arg0 context.Context, arg1 ...client0.CallOption) (*client0.EndpointInfoRes, error) { func (m *MockClient) EndpointInfo(arg0 context.Context, arg1 client0.EndpointInfoPrm) (*client0.EndpointInfoRes, error) {
m.ctrl.T.Helper() m.ctrl.T.Helper()
varargs := []interface{}{arg0} varargs := []interface{}{arg0, arg1}
for _, a := range arg1 {
varargs = append(varargs, a)
}
ret := m.ctrl.Call(m, "EndpointInfo", varargs...) ret := m.ctrl.Call(m, "EndpointInfo", varargs...)
ret0, _ := ret[0].(*client0.EndpointInfoRes) ret0, _ := ret[0].(*client0.EndpointInfoRes)
ret1, _ := ret[1].(error) ret1, _ := ret[1].(error)
@ -209,39 +184,33 @@ func (m *MockClient) EndpointInfo(arg0 context.Context, arg1 ...client0.CallOpti
} }
// EndpointInfo indicates an expected call of EndpointInfo. // EndpointInfo indicates an expected call of EndpointInfo.
func (mr *MockClientMockRecorder) EndpointInfo(arg0 interface{}, arg1 ...interface{}) *gomock.Call { func (mr *MockClientMockRecorder) EndpointInfo(arg0, arg1 interface{}) *gomock.Call {
mr.mock.ctrl.T.Helper() mr.mock.ctrl.T.Helper()
varargs := append([]interface{}{arg0}, arg1...) varargs := []interface{}{arg0, arg1}
return mr.mock.ctrl.RecordCallWithMethodType(mr.mock, "EndpointInfo", reflect.TypeOf((*MockClient)(nil).EndpointInfo), varargs...) return mr.mock.ctrl.RecordCallWithMethodType(mr.mock, "EndpointInfo", reflect.TypeOf((*MockClient)(nil).EndpointInfo), varargs...)
} }
// GetBalance mocks base method. // GetBalance mocks base method.
func (m *MockClient) GetBalance(arg0 context.Context, arg1 *owner.ID, arg2 ...client0.CallOption) (*client0.BalanceOfRes, error) { func (m *MockClient) GetBalance(arg0 context.Context, arg1 client0.GetBalancePrm) (*client0.GetBalanceRes, error) {
m.ctrl.T.Helper() m.ctrl.T.Helper()
varargs := []interface{}{arg0, arg1} varargs := []interface{}{arg0, arg1}
for _, a := range arg2 {
varargs = append(varargs, a)
}
ret := m.ctrl.Call(m, "GetBalance", varargs...) ret := m.ctrl.Call(m, "GetBalance", varargs...)
ret0, _ := ret[0].(*client0.BalanceOfRes) ret0, _ := ret[0].(*client0.GetBalanceRes)
ret1, _ := ret[1].(error) ret1, _ := ret[1].(error)
return ret0, ret1 return ret0, ret1
} }
// GetBalance indicates an expected call of GetBalance. // GetBalance indicates an expected call of GetBalance.
func (mr *MockClientMockRecorder) GetBalance(arg0, arg1 interface{}, arg2 ...interface{}) *gomock.Call { func (mr *MockClientMockRecorder) GetBalance(arg0, arg1 interface{}) *gomock.Call {
mr.mock.ctrl.T.Helper() mr.mock.ctrl.T.Helper()
varargs := append([]interface{}{arg0, arg1}, arg2...) varargs := []interface{}{arg0, arg1}
return mr.mock.ctrl.RecordCallWithMethodType(mr.mock, "GetBalance", reflect.TypeOf((*MockClient)(nil).GetBalance), varargs...) return mr.mock.ctrl.RecordCallWithMethodType(mr.mock, "GetBalance", reflect.TypeOf((*MockClient)(nil).GetBalance), varargs...)
} }
// GetContainer mocks base method. // GetContainer mocks base method.
func (m *MockClient) GetContainer(arg0 context.Context, arg1 *cid.ID, arg2 ...client0.CallOption) (*client0.ContainerGetRes, error) { func (m *MockClient) GetContainer(arg0 context.Context, arg1 client0.ContainerGetPrm) (*client0.ContainerGetRes, error) {
m.ctrl.T.Helper() m.ctrl.T.Helper()
varargs := []interface{}{arg0, arg1} varargs := []interface{}{arg0, arg1}
for _, a := range arg2 {
varargs = append(varargs, a)
}
ret := m.ctrl.Call(m, "GetContainer", varargs...) ret := m.ctrl.Call(m, "GetContainer", varargs...)
ret0, _ := ret[0].(*client0.ContainerGetRes) ret0, _ := ret[0].(*client0.ContainerGetRes)
ret1, _ := ret[1].(error) ret1, _ := ret[1].(error)
@ -249,9 +218,9 @@ func (m *MockClient) GetContainer(arg0 context.Context, arg1 *cid.ID, arg2 ...cl
} }
// GetContainer indicates an expected call of GetContainer. // GetContainer indicates an expected call of GetContainer.
func (mr *MockClientMockRecorder) GetContainer(arg0, arg1 interface{}, arg2 ...interface{}) *gomock.Call { func (mr *MockClientMockRecorder) GetContainer(arg0, arg1 interface{}) *gomock.Call {
mr.mock.ctrl.T.Helper() mr.mock.ctrl.T.Helper()
varargs := append([]interface{}{arg0, arg1}, arg2...) varargs := []interface{}{arg0, arg1}
return mr.mock.ctrl.RecordCallWithMethodType(mr.mock, "GetContainer", reflect.TypeOf((*MockClient)(nil).GetContainer), varargs...) return mr.mock.ctrl.RecordCallWithMethodType(mr.mock, "GetContainer", reflect.TypeOf((*MockClient)(nil).GetContainer), varargs...)
} }
@ -316,12 +285,9 @@ func (mr *MockClientMockRecorder) HeadObject(arg0, arg1 interface{}, arg2 ...int
} }
// ListContainers mocks base method. // ListContainers mocks base method.
func (m *MockClient) ListContainers(arg0 context.Context, arg1 *owner.ID, arg2 ...client0.CallOption) (*client0.ContainerListRes, error) { func (m *MockClient) ListContainers(arg0 context.Context, arg1 client0.ContainerListPrm) (*client0.ContainerListRes, error) {
m.ctrl.T.Helper() m.ctrl.T.Helper()
varargs := []interface{}{arg0, arg1} varargs := []interface{}{arg0, arg1}
for _, a := range arg2 {
varargs = append(varargs, a)
}
ret := m.ctrl.Call(m, "ListContainers", varargs...) ret := m.ctrl.Call(m, "ListContainers", varargs...)
ret0, _ := ret[0].(*client0.ContainerListRes) ret0, _ := ret[0].(*client0.ContainerListRes)
ret1, _ := ret[1].(error) ret1, _ := ret[1].(error)
@ -329,19 +295,16 @@ func (m *MockClient) ListContainers(arg0 context.Context, arg1 *owner.ID, arg2 .
} }
// ListContainers indicates an expected call of ListContainers. // ListContainers indicates an expected call of ListContainers.
func (mr *MockClientMockRecorder) ListContainers(arg0, arg1 interface{}, arg2 ...interface{}) *gomock.Call { func (mr *MockClientMockRecorder) ListContainers(arg0, arg1 interface{}) *gomock.Call {
mr.mock.ctrl.T.Helper() mr.mock.ctrl.T.Helper()
varargs := append([]interface{}{arg0, arg1}, arg2...) varargs := []interface{}{arg0, arg1}
return mr.mock.ctrl.RecordCallWithMethodType(mr.mock, "ListContainers", reflect.TypeOf((*MockClient)(nil).ListContainers), varargs...) return mr.mock.ctrl.RecordCallWithMethodType(mr.mock, "ListContainers", reflect.TypeOf((*MockClient)(nil).ListContainers), varargs...)
} }
// NetworkInfo mocks base method. // NetworkInfo mocks base method.
func (m *MockClient) NetworkInfo(arg0 context.Context, arg1 ...client0.CallOption) (*client0.NetworkInfoRes, error) { func (m *MockClient) NetworkInfo(arg0 context.Context, arg1 client0.NetworkInfoPrm) (*client0.NetworkInfoRes, error) {
m.ctrl.T.Helper() m.ctrl.T.Helper()
varargs := []interface{}{arg0} varargs := []interface{}{arg0, arg1}
for _, a := range arg1 {
varargs = append(varargs, a)
}
ret := m.ctrl.Call(m, "NetworkInfo", varargs...) ret := m.ctrl.Call(m, "NetworkInfo", varargs...)
ret0, _ := ret[0].(*client0.NetworkInfoRes) ret0, _ := ret[0].(*client0.NetworkInfoRes)
ret1, _ := ret[1].(error) ret1, _ := ret[1].(error)
@ -349,9 +312,9 @@ func (m *MockClient) NetworkInfo(arg0 context.Context, arg1 ...client0.CallOptio
} }
// NetworkInfo indicates an expected call of NetworkInfo. // NetworkInfo indicates an expected call of NetworkInfo.
func (mr *MockClientMockRecorder) NetworkInfo(arg0 interface{}, arg1 ...interface{}) *gomock.Call { func (mr *MockClientMockRecorder) NetworkInfo(arg0, arg1 interface{}) *gomock.Call {
mr.mock.ctrl.T.Helper() mr.mock.ctrl.T.Helper()
varargs := append([]interface{}{arg0}, arg1...) varargs := []interface{}{arg0, arg1}
return mr.mock.ctrl.RecordCallWithMethodType(mr.mock, "NetworkInfo", reflect.TypeOf((*MockClient)(nil).NetworkInfo), varargs...) return mr.mock.ctrl.RecordCallWithMethodType(mr.mock, "NetworkInfo", reflect.TypeOf((*MockClient)(nil).NetworkInfo), varargs...)
} }
@ -376,12 +339,9 @@ func (mr *MockClientMockRecorder) ObjectPayloadRangeData(arg0, arg1 interface{},
} }
// PutContainer mocks base method. // PutContainer mocks base method.
func (m *MockClient) PutContainer(arg0 context.Context, arg1 *container.Container, arg2 ...client0.CallOption) (*client0.ContainerPutRes, error) { func (m *MockClient) PutContainer(arg0 context.Context, arg1 client0.ContainerPutPrm) (*client0.ContainerPutRes, error) {
m.ctrl.T.Helper() m.ctrl.T.Helper()
varargs := []interface{}{arg0, arg1} varargs := []interface{}{arg0, arg1}
for _, a := range arg2 {
varargs = append(varargs, a)
}
ret := m.ctrl.Call(m, "PutContainer", varargs...) ret := m.ctrl.Call(m, "PutContainer", varargs...)
ret0, _ := ret[0].(*client0.ContainerPutRes) ret0, _ := ret[0].(*client0.ContainerPutRes)
ret1, _ := ret[1].(error) ret1, _ := ret[1].(error)
@ -389,9 +349,9 @@ func (m *MockClient) PutContainer(arg0 context.Context, arg1 *container.Containe
} }
// PutContainer indicates an expected call of PutContainer. // PutContainer indicates an expected call of PutContainer.
func (mr *MockClientMockRecorder) PutContainer(arg0, arg1 interface{}, arg2 ...interface{}) *gomock.Call { func (mr *MockClientMockRecorder) PutContainer(arg0, arg1 interface{}) *gomock.Call {
mr.mock.ctrl.T.Helper() mr.mock.ctrl.T.Helper()
varargs := append([]interface{}{arg0, arg1}, arg2...) varargs := []interface{}{arg0, arg1}
return mr.mock.ctrl.RecordCallWithMethodType(mr.mock, "PutContainer", reflect.TypeOf((*MockClient)(nil).PutContainer), varargs...) return mr.mock.ctrl.RecordCallWithMethodType(mr.mock, "PutContainer", reflect.TypeOf((*MockClient)(nil).PutContainer), varargs...)
} }
@ -450,12 +410,9 @@ func (mr *MockClientMockRecorder) SearchObjects(arg0, arg1 interface{}, arg2 ...
} }
// SetEACL mocks base method. // SetEACL mocks base method.
func (m *MockClient) SetEACL(arg0 context.Context, arg1 *eacl.Table, arg2 ...client0.CallOption) (*client0.SetEACLRes, error) { func (m *MockClient) SetEACL(arg0 context.Context, arg1 client0.SetEACLPrm) (*client0.SetEACLRes, error) {
m.ctrl.T.Helper() m.ctrl.T.Helper()
varargs := []interface{}{arg0, arg1} varargs := []interface{}{arg0, arg1}
for _, a := range arg2 {
varargs = append(varargs, a)
}
ret := m.ctrl.Call(m, "SetEACL", varargs...) ret := m.ctrl.Call(m, "SetEACL", varargs...)
ret0, _ := ret[0].(*client0.SetEACLRes) ret0, _ := ret[0].(*client0.SetEACLRes)
ret1, _ := ret[1].(error) ret1, _ := ret[1].(error)
@ -463,8 +420,8 @@ func (m *MockClient) SetEACL(arg0 context.Context, arg1 *eacl.Table, arg2 ...cli
} }
// SetEACL indicates an expected call of SetEACL. // SetEACL indicates an expected call of SetEACL.
func (mr *MockClientMockRecorder) SetEACL(arg0, arg1 interface{}, arg2 ...interface{}) *gomock.Call { func (mr *MockClientMockRecorder) SetEACL(arg0, arg1 interface{}) *gomock.Call {
mr.mock.ctrl.T.Helper() mr.mock.ctrl.T.Helper()
varargs := append([]interface{}{arg0, arg1}, arg2...) varargs := []interface{}{arg0, arg1}
return mr.mock.ctrl.RecordCallWithMethodType(mr.mock, "SetEACL", reflect.TypeOf((*MockClient)(nil).SetEACL), varargs...) return mr.mock.ctrl.RecordCallWithMethodType(mr.mock, "SetEACL", reflect.TypeOf((*MockClient)(nil).SetEACL), varargs...)
} }

View file

@ -30,16 +30,16 @@ import (
// Client is a wrapper for client.Client to generate mock. // Client is a wrapper for client.Client to generate mock.
type Client interface { type Client interface {
GetBalance(context.Context, *owner.ID, ...client.CallOption) (*client.BalanceOfRes, error) GetBalance(context.Context, client.GetBalancePrm) (*client.GetBalanceRes, error)
PutContainer(context.Context, *container.Container, ...client.CallOption) (*client.ContainerPutRes, error) PutContainer(context.Context, client.ContainerPutPrm) (*client.ContainerPutRes, error)
GetContainer(context.Context, *cid.ID, ...client.CallOption) (*client.ContainerGetRes, error) GetContainer(context.Context, client.ContainerGetPrm) (*client.ContainerGetRes, error)
ListContainers(context.Context, *owner.ID, ...client.CallOption) (*client.ContainerListRes, error) ListContainers(context.Context, client.ContainerListPrm) (*client.ContainerListRes, error)
DeleteContainer(context.Context, *cid.ID, ...client.CallOption) (*client.ContainerDeleteRes, error) DeleteContainer(context.Context, client.ContainerDeletePrm) (*client.ContainerDeleteRes, error)
EACL(context.Context, *cid.ID, ...client.CallOption) (*client.EACLRes, error) EACL(context.Context, client.EACLPrm) (*client.EACLRes, error)
SetEACL(context.Context, *eacl.Table, ...client.CallOption) (*client.SetEACLRes, error) SetEACL(context.Context, client.SetEACLPrm) (*client.SetEACLRes, error)
AnnounceContainerUsedSpace(context.Context, []container.UsedSpaceAnnouncement, ...client.CallOption) (*client.AnnounceSpaceRes, error) AnnounceContainerUsedSpace(context.Context, client.AnnounceSpacePrm) (*client.AnnounceSpaceRes, error)
EndpointInfo(context.Context, ...client.CallOption) (*client.EndpointInfoRes, error) EndpointInfo(context.Context, client.EndpointInfoPrm) (*client.EndpointInfoRes, error)
NetworkInfo(context.Context, ...client.CallOption) (*client.NetworkInfoRes, error) NetworkInfo(context.Context, client.NetworkInfoPrm) (*client.NetworkInfoRes, error)
PutObject(context.Context, *client.PutObjectParams, ...client.CallOption) (*client.ObjectPutRes, error) PutObject(context.Context, *client.PutObjectParams, ...client.CallOption) (*client.ObjectPutRes, error)
DeleteObject(context.Context, *client.DeleteObjectParams, ...client.CallOption) (*client.ObjectDeleteRes, error) DeleteObject(context.Context, *client.DeleteObjectParams, ...client.CallOption) (*client.ObjectDeleteRes, error)
GetObject(context.Context, *client.GetObjectParams, ...client.CallOption) (*client.ObjectGetRes, error) GetObject(context.Context, *client.GetObjectParams, ...client.CallOption) (*client.ObjectGetRes, error)
@ -47,9 +47,9 @@ type Client interface {
ObjectPayloadRangeData(context.Context, *client.RangeDataParams, ...client.CallOption) (*client.ObjectRangeRes, error) ObjectPayloadRangeData(context.Context, *client.RangeDataParams, ...client.CallOption) (*client.ObjectRangeRes, error)
HashObjectPayloadRanges(context.Context, *client.RangeChecksumParams, ...client.CallOption) (*client.ObjectRangeHashRes, error) HashObjectPayloadRanges(context.Context, *client.RangeChecksumParams, ...client.CallOption) (*client.ObjectRangeHashRes, error)
SearchObjects(context.Context, *client.SearchObjectParams, ...client.CallOption) (*client.ObjectSearchRes, error) SearchObjects(context.Context, *client.SearchObjectParams, ...client.CallOption) (*client.ObjectSearchRes, error)
AnnounceLocalTrust(context.Context, client.AnnounceLocalTrustPrm, ...client.CallOption) (*client.AnnounceLocalTrustRes, error) AnnounceLocalTrust(context.Context, client.AnnounceLocalTrustPrm) (*client.AnnounceLocalTrustRes, error)
AnnounceIntermediateTrust(context.Context, client.AnnounceIntermediateTrustPrm, ...client.CallOption) (*client.AnnounceIntermediateTrustRes, error) AnnounceIntermediateTrust(context.Context, client.AnnounceIntermediateTrustPrm) (*client.AnnounceIntermediateTrustRes, error)
CreateSession(context.Context, uint64, ...client.CallOption) (*client.CreateSessionRes, error) CreateSession(context.Context, client.CreateSessionPrm) (*client.CreateSessionRes, error)
Raw() *apiclient.Client Raw() *apiclient.Client
@ -174,7 +174,6 @@ type Container interface {
DeleteContainer(ctx context.Context, cid *cid.ID, opts ...CallOption) error DeleteContainer(ctx context.Context, cid *cid.ID, opts ...CallOption) error
GetEACL(ctx context.Context, cid *cid.ID, opts ...CallOption) (*eacl.Table, error) GetEACL(ctx context.Context, cid *cid.ID, opts ...CallOption) (*eacl.Table, error)
SetEACL(ctx context.Context, table *eacl.Table, opts ...CallOption) error SetEACL(ctx context.Context, table *eacl.Table, opts ...CallOption) error
AnnounceContainerUsedSpace(ctx context.Context, announce []container.UsedSpaceAnnouncement, opts ...CallOption) error
} }
type Accounting interface { type Accounting interface {
@ -263,6 +262,11 @@ func newPool(ctx context.Context, options *BuilderOptions) (Pool, error) {
inner := make([]*innerPool, len(options.nodesParams)) inner := make([]*innerPool, len(options.nodesParams))
var atLeastOneHealthy bool var atLeastOneHealthy bool
var cliPrm client.CreateSessionPrm
cliPrm.SetExp(options.SessionExpirationEpoch)
for i, params := range options.nodesParams { for i, params := range options.nodesParams {
clientPacks := make([]*clientPack, len(params.weights)) clientPacks := make([]*clientPack, len(params.weights))
for j, address := range params.addresses { for j, address := range params.addresses {
@ -274,7 +278,7 @@ func newPool(ctx context.Context, options *BuilderOptions) (Pool, error) {
return nil, err return nil, err
} }
var healthy bool var healthy bool
cliRes, err := c.CreateSession(ctx, options.SessionExpirationEpoch) cliRes, err := c.CreateSession(ctx, cliPrm)
if err != nil && options.Logger != nil { if err != nil && options.Logger != nil {
options.Logger.Warn("failed to create neofs session token for client", options.Logger.Warn("failed to create neofs session token for client",
zap.String("address", address), zap.String("address", address),
@ -353,14 +357,23 @@ func updateInnerNodesHealth(ctx context.Context, pool *pool, i int, options *Bui
healthyChanged := false healthyChanged := false
wg := sync.WaitGroup{} wg := sync.WaitGroup{}
var (
prmEndpoint client.EndpointInfoPrm
prmSession client.CreateSessionPrm
)
prmSession.SetExp(options.SessionExpirationEpoch)
for j, cPack := range p.clientPacks { for j, cPack := range p.clientPacks {
wg.Add(1) wg.Add(1)
go func(j int, client Client) { go func(j int, cli Client) {
defer wg.Done() defer wg.Done()
ok := true ok := true
tctx, c := context.WithTimeout(ctx, options.NodeRequestTimeout) tctx, c := context.WithTimeout(ctx, options.NodeRequestTimeout)
defer c() defer c()
if _, err := client.EndpointInfo(tctx); err != nil {
if _, err := cli.EndpointInfo(tctx, prmEndpoint); err != nil {
ok = false ok = false
bufferWeights[j] = 0 bufferWeights[j] = 0
} }
@ -371,7 +384,7 @@ func updateInnerNodesHealth(ctx context.Context, pool *pool, i int, options *Bui
if ok { if ok {
bufferWeights[j] = options.nodesParams[i].weights[j] bufferWeights[j] = options.nodesParams[i].weights[j]
if !cp.healthy { if !cp.healthy {
if cliRes, err := client.CreateSession(ctx, options.SessionExpirationEpoch); err != nil { if cliRes, err := cli.CreateSession(ctx, prmSession); err != nil {
ok = false ok = false
bufferWeights[j] = 0 bufferWeights[j] = 0
} else { } else {
@ -488,7 +501,11 @@ func (p *pool) conn(ctx context.Context, cfg *callConfig) (*clientPack, []client
cacheKey := formCacheKey(cp.address, key) cacheKey := formCacheKey(cp.address, key)
sessionToken = p.cache.Get(cacheKey) sessionToken = p.cache.Get(cacheKey)
if sessionToken == nil { if sessionToken == nil {
cliRes, err := cp.client.CreateSession(ctx, math.MaxUint32, clientCallOptions...) var cliPrm client.CreateSessionPrm
cliPrm.SetExp(math.MaxUint32)
cliRes, err := cp.client.CreateSession(ctx, cliPrm)
if err != nil { if err != nil {
return nil, nil, err return nil, nil, err
} }
@ -496,6 +513,8 @@ func (p *pool) conn(ctx context.Context, cfg *callConfig) (*clientPack, []client
ownerID := owner.NewIDFromPublicKey(&key.PublicKey) ownerID := owner.NewIDFromPublicKey(&key.PublicKey)
sessionToken = sessionTokenForOwner(ownerID, cliRes) sessionToken = sessionTokenForOwner(ownerID, cliRes)
cfg.stoken = sessionToken
_ = p.cache.Put(cacheKey, sessionToken) _ = p.cache.Put(cacheKey, sessionToken)
} }
} }
@ -733,12 +752,22 @@ func (p *pool) SearchObject(ctx context.Context, params *client.SearchObjectPara
func (p *pool) PutContainer(ctx context.Context, cnr *container.Container, opts ...CallOption) (*cid.ID, error) { func (p *pool) PutContainer(ctx context.Context, cnr *container.Container, opts ...CallOption) (*cid.ID, error) {
cfg := cfgFromOpts(opts...) cfg := cfgFromOpts(opts...)
cp, options, err := p.conn(ctx, cfg) cp, _, err := p.conn(ctx, cfg)
if err != nil { if err != nil {
return nil, err return nil, err
} }
res, err := cp.client.PutContainer(ctx, cnr, options...) var cliPrm client.ContainerPutPrm
if cnr != nil {
cliPrm.SetContainer(*cnr)
}
if cfg.stoken != nil {
cliPrm.SetSessionToken(*cfg.stoken)
}
res, err := cp.client.PutContainer(ctx, cliPrm)
if p.checkSessionTokenErr(err, cp.address) && !cfg.isRetry { if p.checkSessionTokenErr(err, cp.address) && !cfg.isRetry {
opts = append(opts, retry()) opts = append(opts, retry())
@ -754,12 +783,18 @@ func (p *pool) PutContainer(ctx context.Context, cnr *container.Container, opts
func (p *pool) GetContainer(ctx context.Context, cid *cid.ID, opts ...CallOption) (*container.Container, error) { func (p *pool) GetContainer(ctx context.Context, cid *cid.ID, opts ...CallOption) (*container.Container, error) {
cfg := cfgFromOpts(opts...) cfg := cfgFromOpts(opts...)
cp, options, err := p.conn(ctx, cfg) cp, _, err := p.conn(ctx, cfg)
if err != nil { if err != nil {
return nil, err return nil, err
} }
res, err := cp.client.GetContainer(ctx, cid, options...) var cliPrm client.ContainerGetPrm
if cid != nil {
cliPrm.SetContainer(*cid)
}
res, err := cp.client.GetContainer(ctx, cliPrm)
if p.checkSessionTokenErr(err, cp.address) && !cfg.isRetry { if p.checkSessionTokenErr(err, cp.address) && !cfg.isRetry {
opts = append(opts, retry()) opts = append(opts, retry())
@ -775,12 +810,18 @@ func (p *pool) GetContainer(ctx context.Context, cid *cid.ID, opts ...CallOption
func (p *pool) ListContainers(ctx context.Context, ownerID *owner.ID, opts ...CallOption) ([]*cid.ID, error) { func (p *pool) ListContainers(ctx context.Context, ownerID *owner.ID, opts ...CallOption) ([]*cid.ID, error) {
cfg := cfgFromOpts(opts...) cfg := cfgFromOpts(opts...)
cp, options, err := p.conn(ctx, cfg) cp, _, err := p.conn(ctx, cfg)
if err != nil { if err != nil {
return nil, err return nil, err
} }
res, err := cp.client.ListContainers(ctx, ownerID, options...) var cliPrm client.ContainerListPrm
if ownerID != nil {
cliPrm.SetAccount(*ownerID)
}
res, err := cp.client.ListContainers(ctx, cliPrm)
if p.checkSessionTokenErr(err, cp.address) && !cfg.isRetry { if p.checkSessionTokenErr(err, cp.address) && !cfg.isRetry {
opts = append(opts, retry()) opts = append(opts, retry())
@ -791,17 +832,27 @@ func (p *pool) ListContainers(ctx context.Context, ownerID *owner.ID, opts ...Ca
return nil, err return nil, err
} }
return res.IDList(), nil return res.Containers(), nil
} }
func (p *pool) DeleteContainer(ctx context.Context, cid *cid.ID, opts ...CallOption) error { func (p *pool) DeleteContainer(ctx context.Context, cid *cid.ID, opts ...CallOption) error {
cfg := cfgFromOpts(opts...) cfg := cfgFromOpts(opts...)
cp, options, err := p.conn(ctx, cfg) cp, _, err := p.conn(ctx, cfg)
if err != nil { if err != nil {
return err return err
} }
_, err = cp.client.DeleteContainer(ctx, cid, options...) var cliPrm client.ContainerDeletePrm
if cid != nil {
cliPrm.SetContainer(*cid)
}
if cfg.stoken != nil {
cliPrm.SetSessionToken(*cfg.stoken)
}
_, err = cp.client.DeleteContainer(ctx, cliPrm)
if p.checkSessionTokenErr(err, cp.address) && !cfg.isRetry { if p.checkSessionTokenErr(err, cp.address) && !cfg.isRetry {
opts = append(opts, retry()) opts = append(opts, retry())
@ -815,12 +866,18 @@ func (p *pool) DeleteContainer(ctx context.Context, cid *cid.ID, opts ...CallOpt
func (p *pool) GetEACL(ctx context.Context, cid *cid.ID, opts ...CallOption) (*eacl.Table, error) { func (p *pool) GetEACL(ctx context.Context, cid *cid.ID, opts ...CallOption) (*eacl.Table, error) {
cfg := cfgFromOpts(opts...) cfg := cfgFromOpts(opts...)
cp, options, err := p.conn(ctx, cfg) cp, _, err := p.conn(ctx, cfg)
if err != nil { if err != nil {
return nil, err return nil, err
} }
res, err := cp.client.EACL(ctx, cid, options...) var cliPrm client.EACLPrm
if cid != nil {
cliPrm.SetContainer(*cid)
}
res, err := cp.client.EACL(ctx, cliPrm)
if p.checkSessionTokenErr(err, cp.address) && !cfg.isRetry { if p.checkSessionTokenErr(err, cp.address) && !cfg.isRetry {
opts = append(opts, retry()) opts = append(opts, retry())
@ -836,12 +893,22 @@ func (p *pool) GetEACL(ctx context.Context, cid *cid.ID, opts ...CallOption) (*e
func (p *pool) SetEACL(ctx context.Context, table *eacl.Table, opts ...CallOption) error { func (p *pool) SetEACL(ctx context.Context, table *eacl.Table, opts ...CallOption) error {
cfg := cfgFromOpts(opts...) cfg := cfgFromOpts(opts...)
cp, options, err := p.conn(ctx, cfg) cp, _, err := p.conn(ctx, cfg)
if err != nil { if err != nil {
return err return err
} }
_, err = cp.client.SetEACL(ctx, table, options...) var cliPrm client.SetEACLPrm
if table != nil {
cliPrm.SetTable(*table)
}
if cfg.stoken != nil {
cliPrm.SetSessionToken(*cfg.stoken)
}
_, err = cp.client.SetEACL(ctx, cliPrm)
if p.checkSessionTokenErr(err, cp.address) && !cfg.isRetry { if p.checkSessionTokenErr(err, cp.address) && !cfg.isRetry {
opts = append(opts, retry()) opts = append(opts, retry())
@ -853,33 +920,20 @@ func (p *pool) SetEACL(ctx context.Context, table *eacl.Table, opts ...CallOptio
return err return err
} }
func (p *pool) AnnounceContainerUsedSpace(ctx context.Context, announce []container.UsedSpaceAnnouncement, opts ...CallOption) error {
cfg := cfgFromOpts(opts...)
cp, options, err := p.conn(ctx, cfg)
if err != nil {
return err
}
_, err = cp.client.AnnounceContainerUsedSpace(ctx, announce, options...)
if p.checkSessionTokenErr(err, cp.address) && !cfg.isRetry {
opts = append(opts, retry())
return p.AnnounceContainerUsedSpace(ctx, announce, opts...)
}
// here err already carries both status and client errors
return err
}
func (p *pool) Balance(ctx context.Context, o *owner.ID, opts ...CallOption) (*accounting.Decimal, error) { func (p *pool) Balance(ctx context.Context, o *owner.ID, opts ...CallOption) (*accounting.Decimal, error) {
cfg := cfgFromOpts(opts...) cfg := cfgFromOpts(opts...)
cp, options, err := p.conn(ctx, cfg) cp, _, err := p.conn(ctx, cfg)
if err != nil { if err != nil {
return nil, err return nil, err
} }
res, err := cp.client.GetBalance(ctx, o, options...) var cliPrm client.GetBalancePrm
if o != nil {
cliPrm.SetAccount(*o)
}
res, err := cp.client.GetBalance(ctx, cliPrm)
if err != nil { // here err already carries both status and client errors if err != nil { // here err already carries both status and client errors
return nil, err return nil, err
} }
@ -898,6 +952,13 @@ func (p *pool) WaitForContainerPresence(ctx context.Context, cid *cid.ID, pollPa
defer ticker.Stop() defer ticker.Stop()
wdone := wctx.Done() wdone := wctx.Done()
done := ctx.Done() done := ctx.Done()
var cliPrm client.ContainerGetPrm
if cid != nil {
cliPrm.SetContainer(*cid)
}
for { for {
select { select {
case <-done: case <-done:
@ -905,7 +966,7 @@ func (p *pool) WaitForContainerPresence(ctx context.Context, cid *cid.ID, pollPa
case <-wdone: case <-wdone:
return wctx.Err() return wctx.Err()
case <-ticker.C: case <-ticker.C:
_, err = conn.GetContainer(ctx, cid) _, err = conn.GetContainer(ctx, cliPrm)
if err == nil { if err == nil {
return nil return nil
} }
@ -930,7 +991,7 @@ func sessionTokenForOwner(id *owner.ID, cliRes *client.CreateSessionRes) *sessio
st := session.NewToken() st := session.NewToken()
st.SetOwnerID(id) st.SetOwnerID(id)
st.SetID(cliRes.ID()) st.SetID(cliRes.ID())
st.SetSessionKey(cliRes.SessionKey()) st.SetSessionKey(cliRes.PublicKey())
return st return st
} }

View file

@ -152,7 +152,7 @@ func TestOneNode(t *testing.T) {
clientBuilder := func(opts ...client.Option) (Client, error) { clientBuilder := func(opts ...client.Option) (Client, error) {
mockClient := NewMockClient(ctrl) mockClient := NewMockClient(ctrl)
mockClient.EXPECT().CreateSession(gomock.Any(), gomock.Any()).Return(tok, nil) mockClient.EXPECT().CreateSession(gomock.Any(), gomock.Any()).Return(tok, nil)
mockClient.EXPECT().EndpointInfo(gomock.Any(), gomock.Any()).Return(&client.EndpointInfo{}, nil).AnyTimes() mockClient.EXPECT().EndpointInfo(gomock.Any(), gomock.Any()).Return(&client.EndpointInfoRes{}, nil).AnyTimes()
return mockClient, nil return mockClient, nil
} }
@ -189,7 +189,7 @@ func TestTwoNodes(t *testing.T) {
tokens = append(tokens, tok) tokens = append(tokens, tok)
return tok, err return tok, err
}) })
mockClient.EXPECT().EndpointInfo(gomock.Any(), gomock.Any()).Return(&client.EndpointInfo{}, nil).AnyTimes() mockClient.EXPECT().EndpointInfo(gomock.Any(), gomock.Any()).Return(&client.EndpointInfoRes{}, nil).AnyTimes()
return mockClient, nil return mockClient, nil
} }
@ -222,7 +222,7 @@ func TestOneOfTwoFailed(t *testing.T) {
clientBuilder := func(opts ...client.Option) (Client, error) { clientBuilder := func(opts ...client.Option) (Client, error) {
clientCount++ clientCount++
mockClient := NewMockClient(ctrl) mockClient := NewMockClient(ctrl)
mockClient.EXPECT().CreateSession(gomock.Any(), gomock.Any(), gomock.Any()).DoAndReturn(func(_, _ interface{}, _ ...interface{}) (*session.Token, error) { mockClient.EXPECT().CreateSession(gomock.Any(), gomock.Any()).DoAndReturn(func(_, _ interface{}, _ ...interface{}) (*session.Token, error) {
tok := newToken(t) tok := newToken(t)
tokens = append(tokens, tok) tokens = append(tokens, tok)
return tok, nil return tok, nil
@ -235,7 +235,7 @@ func TestOneOfTwoFailed(t *testing.T) {
tokens = append(tokens, tok) tokens = append(tokens, tok)
return tok, nil return tok, nil
}).AnyTimes() }).AnyTimes()
mockClient2.EXPECT().EndpointInfo(gomock.Any(), gomock.Any()).DoAndReturn(func(_ interface{}, _ ...interface{}) (*client.EndpointInfo, error) { mockClient2.EXPECT().EndpointInfo(gomock.Any(), gomock.Any()).DoAndReturn(func(_ interface{}, _ ...interface{}) (*client.EndpointInfoRes, error) {
return nil, fmt.Errorf("error") return nil, fmt.Errorf("error")
}).AnyTimes() }).AnyTimes()
@ -275,7 +275,7 @@ func TestTwoFailed(t *testing.T) {
clientBuilder := func(opts ...client.Option) (Client, error) { clientBuilder := func(opts ...client.Option) (Client, error) {
mockClient := NewMockClient(ctrl) mockClient := NewMockClient(ctrl)
mockClient.EXPECT().CreateSession(gomock.Any(), gomock.Any(), gomock.Any()).Return(nil, nil).AnyTimes() mockClient.EXPECT().CreateSession(gomock.Any(), gomock.Any()).Return(nil, nil).AnyTimes()
mockClient.EXPECT().EndpointInfo(gomock.Any(), gomock.Any()).Return(nil, fmt.Errorf("error")).AnyTimes() mockClient.EXPECT().EndpointInfo(gomock.Any(), gomock.Any()).Return(nil, fmt.Errorf("error")).AnyTimes()
return mockClient, nil return mockClient, nil
} }
@ -309,7 +309,7 @@ func TestSessionCache(t *testing.T) {
var tokens []*session.Token var tokens []*session.Token
clientBuilder := func(opts ...client.Option) (Client, error) { clientBuilder := func(opts ...client.Option) (Client, error) {
mockClient := NewMockClient(ctrl) mockClient := NewMockClient(ctrl)
mockClient.EXPECT().CreateSession(gomock.Any(), gomock.Any(), gomock.Any()).DoAndReturn(func(_, _ interface{}, _ ...interface{}) (*session.Token, error) { mockClient.EXPECT().CreateSession(gomock.Any(), gomock.Any()).DoAndReturn(func(_, _ interface{}, _ ...interface{}) (*session.Token, error) {
tok := session.NewToken() tok := session.NewToken()
uid, err := uuid.New().MarshalBinary() uid, err := uuid.New().MarshalBinary()
require.NoError(t, err) require.NoError(t, err)
@ -373,7 +373,7 @@ func TestPriority(t *testing.T) {
clientBuilder := func(opts ...client.Option) (Client, error) { clientBuilder := func(opts ...client.Option) (Client, error) {
clientCount++ clientCount++
mockClient := NewMockClient(ctrl) mockClient := NewMockClient(ctrl)
mockClient.EXPECT().CreateSession(gomock.Any(), gomock.Any(), gomock.Any()).DoAndReturn(func(_, _ interface{}, _ ...interface{}) (*session.Token, error) { mockClient.EXPECT().CreateSession(gomock.Any(), gomock.Any()).DoAndReturn(func(_, _ interface{}, _ ...interface{}) (*session.Token, error) {
tok := newToken(t) tok := newToken(t)
tokens = append(tokens, tok) tokens = append(tokens, tok)
return tok, nil return tok, nil
@ -435,7 +435,7 @@ func TestSessionCacheWithKey(t *testing.T) {
var tokens []*session.Token var tokens []*session.Token
clientBuilder := func(opts ...client.Option) (Client, error) { clientBuilder := func(opts ...client.Option) (Client, error) {
mockClient := NewMockClient(ctrl) mockClient := NewMockClient(ctrl)
mockClient.EXPECT().CreateSession(gomock.Any(), gomock.Any(), gomock.Any()).DoAndReturn(func(_, _ interface{}, _ ...interface{}) (*session.Token, error) { mockClient.EXPECT().CreateSession(gomock.Any(), gomock.Any()).DoAndReturn(func(_, _ interface{}, _ ...interface{}) (*session.Token, error) {
tok := session.NewToken() tok := session.NewToken()
uid, err := uuid.New().MarshalBinary() uid, err := uuid.New().MarshalBinary()
require.NoError(t, err) require.NoError(t, err)
@ -487,7 +487,7 @@ func TestSessionTokenOwner(t *testing.T) {
ctrl := gomock.NewController(t) ctrl := gomock.NewController(t)
clientBuilder := func(opts ...client.Option) (Client, error) { clientBuilder := func(opts ...client.Option) (Client, error) {
mockClient := NewMockClient(ctrl) mockClient := NewMockClient(ctrl)
mockClient.EXPECT().CreateSession(gomock.Any(), gomock.Any(), gomock.Any()).Return(&client.CreateSessionRes{}, nil).AnyTimes() mockClient.EXPECT().CreateSession(gomock.Any(), gomock.Any()).Return(&client.CreateSessionRes{}, nil).AnyTimes()
mockClient.EXPECT().EndpointInfo(gomock.Any(), gomock.Any()).Return(&client.EndpointInfoRes{}, nil).AnyTimes() mockClient.EXPECT().EndpointInfo(gomock.Any(), gomock.Any()).Return(&client.EndpointInfoRes{}, nil).AnyTimes()
return mockClient, nil return mockClient, nil
} }
@ -525,9 +525,9 @@ func TestWaitPresence(t *testing.T) {
ctrl := gomock.NewController(t) ctrl := gomock.NewController(t)
mockClient := NewMockClient(ctrl) mockClient := NewMockClient(ctrl)
mockClient.EXPECT().CreateSession(gomock.Any(), gomock.Any(), gomock.Any()).Return(nil, nil).AnyTimes() mockClient.EXPECT().CreateSession(gomock.Any(), gomock.Any()).Return(nil, nil).AnyTimes()
mockClient.EXPECT().EndpointInfo(gomock.Any(), gomock.Any()).Return(nil, nil).AnyTimes() mockClient.EXPECT().EndpointInfo(gomock.Any(), gomock.Any()).Return(nil, nil).AnyTimes()
mockClient.EXPECT().GetContainer(gomock.Any(), gomock.Any(), gomock.Any()).Return(nil, nil).AnyTimes() mockClient.EXPECT().GetContainer(gomock.Any(), gomock.Any()).Return(nil, nil).AnyTimes()
cache, err := NewCache() cache, err := NewCache()
require.NoError(t, err) require.NoError(t, err)

View file

@ -48,11 +48,11 @@ type clientMock struct {
err error err error
} }
func (c *clientMock) EndpointInfo(context.Context, ...client.CallOption) (*client.EndpointInfoRes, error) { func (c *clientMock) EndpointInfo(context.Context, client.EndpointInfoPrm) (*client.EndpointInfoRes, error) {
return nil, nil return nil, nil
} }
func (c *clientMock) NetworkInfo(context.Context, ...client.CallOption) (*client.NetworkInfoRes, error) { func (c *clientMock) NetworkInfo(context.Context, client.NetworkInfoPrm) (*client.NetworkInfoRes, error) {
return nil, nil return nil, nil
} }