WIP: Morph: Add unit tests #2

Closed
dstepanov-yadro wants to merge 233 commits from TrueCloudLab/frostfs-node:master into object-3608-morph-unit-tests
5 changed files with 66 additions and 121 deletions
Showing only changes of commit fb708b3a2d - Show all commits

View file

@ -263,9 +263,9 @@ func (s *Server) initContainerProcessor(cfg *viper.Viper, cnrClient *container.C
PoolSize: cfg.GetInt("workers.container"), PoolSize: cfg.GetInt("workers.container"),
AlphabetState: s, AlphabetState: s,
ContainerClient: cnrClient, ContainerClient: cnrClient,
MorphClient: cnrClient.Morph(),
FrostFSIDClient: frostfsIDClient, FrostFSIDClient: frostfsIDClient,
NetworkState: s.netmapClient, NetworkState: s.netmapClient,
NotaryDisabled: s.sideNotaryConfig.disabled,
}) })
if err != nil { if err != nil {
return err return err

View file

@ -7,7 +7,6 @@ import (
"time" "time"
containercore "git.frostfs.info/TrueCloudLab/frostfs-node/pkg/core/container" containercore "git.frostfs.info/TrueCloudLab/frostfs-node/pkg/core/container"
"git.frostfs.info/TrueCloudLab/frostfs-node/pkg/morph/client"
cntClient "git.frostfs.info/TrueCloudLab/frostfs-node/pkg/morph/client/container" cntClient "git.frostfs.info/TrueCloudLab/frostfs-node/pkg/morph/client/container"
"git.frostfs.info/TrueCloudLab/frostfs-node/pkg/morph/client/frostfsid" "git.frostfs.info/TrueCloudLab/frostfs-node/pkg/morph/client/frostfsid"
containerEvent "git.frostfs.info/TrueCloudLab/frostfs-node/pkg/morph/event/container" containerEvent "git.frostfs.info/TrueCloudLab/frostfs-node/pkg/morph/event/container"
@ -22,6 +21,7 @@ import (
"git.frostfs.info/TrueCloudLab/frostfs-sdk-go/netmap" "git.frostfs.info/TrueCloudLab/frostfs-sdk-go/netmap"
"git.frostfs.info/TrueCloudLab/frostfs-sdk-go/user" "git.frostfs.info/TrueCloudLab/frostfs-sdk-go/user"
"git.frostfs.info/TrueCloudLab/frostfs-sdk-go/version" "git.frostfs.info/TrueCloudLab/frostfs-sdk-go/version"
"github.com/nspcc-dev/neo-go/pkg/core/transaction"
"github.com/nspcc-dev/neo-go/pkg/crypto/keys" "github.com/nspcc-dev/neo-go/pkg/crypto/keys"
"github.com/nspcc-dev/neo-go/pkg/network/payload" "github.com/nspcc-dev/neo-go/pkg/network/payload"
"github.com/nspcc-dev/neo-go/pkg/util" "github.com/nspcc-dev/neo-go/pkg/util"
@ -34,18 +34,16 @@ func TestPutEvent(t *testing.T) {
homHashDisabled: true, homHashDisabled: true,
epoch: 100, epoch: 100,
} }
cc := &testContainerClient{ mc := &testMorphClient{}
get: make(map[string]*containercore.Container),
}
proc, err := New(&Params{ proc, err := New(&Params{
Log: test.NewLogger(t, true), Log: test.NewLogger(t, true),
PoolSize: 2, PoolSize: 2,
AlphabetState: &testAlphabetState{isAlphabet: true}, AlphabetState: &testAlphabetState{isAlphabet: true},
FrostFSIDClient: &testIDClient{}, FrostFSIDClient: &testIDClient{},
NotaryDisabled: true,
NetworkState: nst, NetworkState: nst,
ContainerClient: cc, ContainerClient: &testContainerClient{},
MorphClient: mc,
}) })
require.NoError(t, err, "failed to create processor") require.NoError(t, err, "failed to create processor")
@ -64,10 +62,15 @@ func TestPutEvent(t *testing.T) {
cnr.SetBasicACL(acl.Private) cnr.SetBasicACL(acl.Private)
containerSDK.DisableHomomorphicHashing(&cnr) containerSDK.DisableHomomorphicHashing(&cnr)
nr := &payload.P2PNotaryRequest{
MainTransaction: &transaction.Transaction{},
}
event := &testPutEvent{ event := &testPutEvent{
cnr: &cnr, cnr: &cnr,
pk: p, pk: p,
st: nil, st: nil,
nr: nr,
} }
proc.handlePut(event) proc.handlePut(event)
@ -76,13 +79,7 @@ func TestPutEvent(t *testing.T) {
time.Sleep(10 * time.Millisecond) time.Sleep(10 * time.Millisecond)
} }
var expectedPut cntClient.PutPrm require.EqualValues(t, []*transaction.Transaction{nr.MainTransaction}, mc.transactions, "invalid notary requests")
expectedPut.SetContainer(cnr.Marshal())
expectedPut.SetKey(p.PublicKey().Bytes())
expectedPut.SetSignature(p.Sign(cnr.Marshal()))
expectedPut.SetZone("container")
require.EqualValues(t, []cntClient.PutPrm{expectedPut}, cc.put, "invalid put requests")
} }
func TestDeleteEvent(t *testing.T) { func TestDeleteEvent(t *testing.T) {
@ -103,15 +100,16 @@ func TestDeleteEvent(t *testing.T) {
p.PublicKey(), p.PublicKey(),
}, },
} }
mc := &testMorphClient{}
proc, err := New(&Params{ proc, err := New(&Params{
Log: test.NewLogger(t, true), Log: test.NewLogger(t, true),
PoolSize: 2, PoolSize: 2,
AlphabetState: &testAlphabetState{isAlphabet: true}, AlphabetState: &testAlphabetState{isAlphabet: true},
FrostFSIDClient: idc, FrostFSIDClient: idc,
NotaryDisabled: true,
NetworkState: nst, NetworkState: nst,
ContainerClient: cc, ContainerClient: cc,
MorphClient: mc,
}) })
require.NoError(t, err, "failed to create processor") require.NoError(t, err, "failed to create processor")
@ -133,9 +131,14 @@ func TestDeleteEvent(t *testing.T) {
cidBin := make([]byte, 32) cidBin := make([]byte, 32)
cid.Encode(cidBin) cid.Encode(cidBin)
nr := &payload.P2PNotaryRequest{
MainTransaction: &transaction.Transaction{},
}
ev := containerEvent.Delete{ ev := containerEvent.Delete{
ContainerIDValue: cidBin, ContainerIDValue: cidBin,
SignatureValue: p.Sign(cidBin), SignatureValue: p.Sign(cidBin),
NotaryRequestValue: nr,
} }
var signature frostfscrypto.Signature var signature frostfscrypto.Signature
@ -156,7 +159,7 @@ func TestDeleteEvent(t *testing.T) {
expectedDelete.SetCID(ev.ContainerID()) expectedDelete.SetCID(ev.ContainerID())
expectedDelete.SetSignature(ev.Signature()) expectedDelete.SetSignature(ev.Signature())
require.EqualValues(t, []cntClient.DeletePrm{expectedDelete}, cc.delete, "invalid delete requests") require.EqualValues(t, []*transaction.Transaction{nr.MainTransaction}, mc.transactions, "invalid notary requests")
} }
func TestSetEACLEvent(t *testing.T) { func TestSetEACLEvent(t *testing.T) {
@ -168,15 +171,16 @@ func TestSetEACLEvent(t *testing.T) {
cc := &testContainerClient{ cc := &testContainerClient{
get: make(map[string]*containercore.Container), get: make(map[string]*containercore.Container),
} }
mc := &testMorphClient{}
proc, err := New(&Params{ proc, err := New(&Params{
Log: test.NewLogger(t, true), Log: test.NewLogger(t, true),
PoolSize: 2, PoolSize: 2,
AlphabetState: &testAlphabetState{isAlphabet: true}, AlphabetState: &testAlphabetState{isAlphabet: true},
FrostFSIDClient: &testIDClient{}, FrostFSIDClient: &testIDClient{},
NotaryDisabled: true,
NetworkState: nst, NetworkState: nst,
ContainerClient: cc, ContainerClient: cc,
MorphClient: mc,
}) })
require.NoError(t, err, "failed to create processor") require.NoError(t, err, "failed to create processor")
@ -219,10 +223,14 @@ func TestSetEACLEvent(t *testing.T) {
table.AddRecord(r) table.AddRecord(r)
nr := &payload.P2PNotaryRequest{
MainTransaction: &transaction.Transaction{},
}
event := containerEvent.SetEACL{ event := containerEvent.SetEACL{
TableValue: table.ToV2().StableMarshal(nil), TableValue: table.ToV2().StableMarshal(nil),
PublicKeyValue: p.PublicKey().Bytes(), PublicKeyValue: p.PublicKey().Bytes(),
SignatureValue: p.Sign(table.ToV2().StableMarshal(nil)), SignatureValue: p.Sign(table.ToV2().StableMarshal(nil)),
NotaryRequestValue: nr,
} }
proc.handleSetEACL(event) proc.handleSetEACL(event)
@ -236,7 +244,7 @@ func TestSetEACLEvent(t *testing.T) {
expectedPutEACL.SetKey(p.PublicKey().Bytes()) expectedPutEACL.SetKey(p.PublicKey().Bytes())
expectedPutEACL.SetSignature(p.Sign(table.ToV2().StableMarshal(nil))) expectedPutEACL.SetSignature(p.Sign(table.ToV2().StableMarshal(nil)))
require.EqualValues(t, []cntClient.PutEACLPrm{expectedPutEACL}, cc.putEACL, "invalid set EACL requests") require.EqualValues(t, []*transaction.Transaction{nr.MainTransaction}, mc.transactions, "invalid notary requests")
} }
type testAlphabetState struct { type testAlphabetState struct {
@ -262,25 +270,13 @@ func (s *testNetworkState) Epoch() (uint64, error) {
type testContainerClient struct { type testContainerClient struct {
contractAddress util.Uint160 contractAddress util.Uint160
put []cntClient.PutPrm
get map[string]*containercore.Container get map[string]*containercore.Container
delete []cntClient.DeletePrm
putEACL []cntClient.PutEACLPrm
} }
func (c *testContainerClient) ContractAddress() util.Uint160 { func (c *testContainerClient) ContractAddress() util.Uint160 {
return c.contractAddress return c.contractAddress
} }
func (c *testContainerClient) Morph() *client.Client {
return nil
}
func (c *testContainerClient) Put(p cntClient.PutPrm) error {
c.put = append(c.put, p)
return nil
}
func (c *testContainerClient) Get(cid []byte) (*containercore.Container, error) { func (c *testContainerClient) Get(cid []byte) (*containercore.Container, error) {
key := hex.EncodeToString(cid) key := hex.EncodeToString(cid)
if cont, found := c.get[key]; found { if cont, found := c.get[key]; found {
@ -289,16 +285,6 @@ func (c *testContainerClient) Get(cid []byte) (*containercore.Container, error)
return nil, apistatus.ContainerNotFound{} return nil, apistatus.ContainerNotFound{}
} }
func (c *testContainerClient) Delete(p cntClient.DeletePrm) error {
c.delete = append(c.delete, p)
return nil
}
func (c *testContainerClient) PutEACL(p cntClient.PutEACLPrm) error {
c.putEACL = append(c.putEACL, p)
return nil
}
type testIDClient struct { type testIDClient struct {
publicKeys keys.PublicKeys publicKeys keys.PublicKeys
} }
@ -313,6 +299,7 @@ type testPutEvent struct {
cnr *containerSDK.Container cnr *containerSDK.Container
pk *keys.PrivateKey pk *keys.PrivateKey
st []byte st []byte
nr *payload.P2PNotaryRequest
} }
func (e *testPutEvent) MorphEvent() {} func (e *testPutEvent) MorphEvent() {}
@ -333,5 +320,14 @@ func (e *testPutEvent) SessionToken() []byte {
return e.st return e.st
} }
func (e *testPutEvent) NotaryRequest() *payload.P2PNotaryRequest { func (e *testPutEvent) NotaryRequest() *payload.P2PNotaryRequest {
return e.nr
}
type testMorphClient struct {
transactions []*transaction.Transaction
}
func (c *testMorphClient) NotarySignAndInvokeTX(mainTx *transaction.Transaction) error {
c.transactions = append(c.transactions, mainTx)
return nil return nil
} }

View file

@ -4,7 +4,6 @@ import (
"fmt" "fmt"
"git.frostfs.info/TrueCloudLab/frostfs-node/internal/logs" "git.frostfs.info/TrueCloudLab/frostfs-node/internal/logs"
cntClient "git.frostfs.info/TrueCloudLab/frostfs-node/pkg/morph/client/container"
"git.frostfs.info/TrueCloudLab/frostfs-node/pkg/morph/event" "git.frostfs.info/TrueCloudLab/frostfs-node/pkg/morph/event"
containerEvent "git.frostfs.info/TrueCloudLab/frostfs-node/pkg/morph/event/container" containerEvent "git.frostfs.info/TrueCloudLab/frostfs-node/pkg/morph/event/container"
containerSDK "git.frostfs.info/TrueCloudLab/frostfs-sdk-go/container" containerSDK "git.frostfs.info/TrueCloudLab/frostfs-sdk-go/container"
@ -91,27 +90,7 @@ func (cp *Processor) checkPutContainer(ctx *putContainerContext) error {
} }
func (cp *Processor) approvePutContainer(ctx *putContainerContext) { func (cp *Processor) approvePutContainer(ctx *putContainerContext) {
e := ctx.e if err := cp.morphClient.NotarySignAndInvokeTX(ctx.e.NotaryRequest().MainTransaction); err != nil {
var err error
prm := cntClient.PutPrm{}
prm.SetContainer(e.Container())
prm.SetKey(e.PublicKey())
prm.SetSignature(e.Signature())
prm.SetToken(e.SessionToken())
prm.SetName(ctx.d.Name())
prm.SetZone(ctx.d.Zone())
if nr := e.NotaryRequest(); nr != nil {
// put event was received via Notary service
err = cp.cnrClient.Morph().NotarySignAndInvokeTX(nr.MainTransaction)
} else {
// put event was received via notification service
err = cp.cnrClient.Put(prm)
}
if err != nil {
cp.log.Error(logs.ContainerCouldNotApprovePutContainer, cp.log.Error(logs.ContainerCouldNotApprovePutContainer,
zap.String("error", err.Error()), zap.String("error", err.Error()),
) )
@ -171,22 +150,7 @@ func (cp *Processor) checkDeleteContainer(e containerEvent.Delete) error {
} }
func (cp *Processor) approveDeleteContainer(e containerEvent.Delete) { func (cp *Processor) approveDeleteContainer(e containerEvent.Delete) {
var err error if err := cp.morphClient.NotarySignAndInvokeTX(e.NotaryRequest().MainTransaction); err != nil {
prm := cntClient.DeletePrm{}
prm.SetCID(e.ContainerID())
prm.SetSignature(e.Signature())
prm.SetToken(e.SessionToken())
if nr := e.NotaryRequest(); nr != nil {
// delete event was received via Notary service
err = cp.cnrClient.Morph().NotarySignAndInvokeTX(nr.MainTransaction)
} else {
// delete event was received via notification service
err = cp.cnrClient.Delete(prm)
}
if err != nil {
cp.log.Error(logs.ContainerCouldNotApproveDeleteContainer, cp.log.Error(logs.ContainerCouldNotApproveDeleteContainer,
zap.String("error", err.Error()), zap.String("error", err.Error()),
) )

View file

@ -75,23 +75,7 @@ func (cp *Processor) checkSetEACL(e containerEvent.SetEACL) error {
} }
func (cp *Processor) approveSetEACL(e containerEvent.SetEACL) { func (cp *Processor) approveSetEACL(e containerEvent.SetEACL) {
var err error if err := cp.morphClient.NotarySignAndInvokeTX(e.NotaryRequest().MainTransaction); err != nil {
prm := cntClient.PutEACLPrm{}
prm.SetTable(e.Table())
prm.SetKey(e.PublicKey())
prm.SetSignature(e.Signature())
prm.SetToken(e.SessionToken())
if nr := e.NotaryRequest(); nr != nil {
// setEACL event was received via Notary service
err = cp.cnrClient.Morph().NotarySignAndInvokeTX(nr.MainTransaction)
} else {
// setEACL event was received via notification service
err = cp.cnrClient.PutEACL(prm)
}
if err != nil {
cp.log.Error(logs.ContainerCouldNotApproveSetEACL, cp.log.Error(logs.ContainerCouldNotApproveSetEACL,
zap.String("error", err.Error()), zap.String("error", err.Error()),
) )

View file

@ -6,13 +6,12 @@ import (
"git.frostfs.info/TrueCloudLab/frostfs-node/internal/logs" "git.frostfs.info/TrueCloudLab/frostfs-node/internal/logs"
containercore "git.frostfs.info/TrueCloudLab/frostfs-node/pkg/core/container" containercore "git.frostfs.info/TrueCloudLab/frostfs-node/pkg/core/container"
"git.frostfs.info/TrueCloudLab/frostfs-node/pkg/morph/client"
cntClient "git.frostfs.info/TrueCloudLab/frostfs-node/pkg/morph/client/container"
"git.frostfs.info/TrueCloudLab/frostfs-node/pkg/morph/client/frostfsid" "git.frostfs.info/TrueCloudLab/frostfs-node/pkg/morph/client/frostfsid"
"git.frostfs.info/TrueCloudLab/frostfs-node/pkg/morph/event" "git.frostfs.info/TrueCloudLab/frostfs-node/pkg/morph/event"
containerEvent "git.frostfs.info/TrueCloudLab/frostfs-node/pkg/morph/event/container" containerEvent "git.frostfs.info/TrueCloudLab/frostfs-node/pkg/morph/event/container"
"git.frostfs.info/TrueCloudLab/frostfs-node/pkg/util/logger" "git.frostfs.info/TrueCloudLab/frostfs-node/pkg/util/logger"
"github.com/nspcc-dev/neo-go/pkg/core/mempoolevent" "github.com/nspcc-dev/neo-go/pkg/core/mempoolevent"
"github.com/nspcc-dev/neo-go/pkg/core/transaction"
"github.com/nspcc-dev/neo-go/pkg/crypto/keys" "github.com/nspcc-dev/neo-go/pkg/crypto/keys"
"github.com/nspcc-dev/neo-go/pkg/util" "github.com/nspcc-dev/neo-go/pkg/util"
"github.com/panjf2000/ants/v2" "github.com/panjf2000/ants/v2"
@ -27,11 +26,11 @@ type (
ContClient interface { ContClient interface {
ContractAddress() util.Uint160 ContractAddress() util.Uint160
Morph() *client.Client
Put(p cntClient.PutPrm) error
Get(cid []byte) (*containercore.Container, error) Get(cid []byte) (*containercore.Container, error)
Delete(p cntClient.DeletePrm) error }
PutEACL(p cntClient.PutEACLPrm) error
MorphClient interface {
NotarySignAndInvokeTX(mainTx *transaction.Transaction) error
} }
IDClient interface { IDClient interface {
@ -44,9 +43,9 @@ type (
pool *ants.Pool pool *ants.Pool
alphabetState AlphabetState alphabetState AlphabetState
cnrClient ContClient // notary must be enabled cnrClient ContClient // notary must be enabled
morphClient MorphClient
idClient IDClient idClient IDClient
netState NetworkState netState NetworkState
notaryDisabled bool
} }
// Params of the processor constructor. // Params of the processor constructor.
@ -55,9 +54,9 @@ type (
PoolSize int PoolSize int
AlphabetState AlphabetState AlphabetState AlphabetState
ContainerClient ContClient ContainerClient ContClient
MorphClient MorphClient
FrostFSIDClient IDClient FrostFSIDClient IDClient
NetworkState NetworkState NetworkState NetworkState
NotaryDisabled bool
} }
) )
@ -88,6 +87,8 @@ func New(p *Params) (*Processor, error) {
return nil, errors.New("ir/container: global state is not set") return nil, errors.New("ir/container: global state is not set")
case p.ContainerClient == nil: case p.ContainerClient == nil:
return nil, errors.New("ir/container: Container client is not set") return nil, errors.New("ir/container: Container client is not set")
case p.MorphClient == nil:
return nil, errors.New("ir/container: Morph client is not set")
case p.FrostFSIDClient == nil: case p.FrostFSIDClient == nil:
return nil, errors.New("ir/container: FrostFS ID client is not set") return nil, errors.New("ir/container: FrostFS ID client is not set")
case p.NetworkState == nil: case p.NetworkState == nil:
@ -108,7 +109,7 @@ func New(p *Params) (*Processor, error) {
cnrClient: p.ContainerClient, cnrClient: p.ContainerClient,
idClient: p.FrostFSIDClient, idClient: p.FrostFSIDClient,
netState: p.NetworkState, netState: p.NetworkState,
notaryDisabled: p.NotaryDisabled, morphClient: p.MorphClient,
}, nil }, nil
} }