forked from TrueCloudLab/frostfs-node
[#85] get-service: Add unit tests
Add unit tests to cover all assemble statements Signed-off-by: Dmitrii Stepanov <d.stepanov@yadro.com>
This commit is contained in:
parent
8b9e40a848
commit
2886b1581b
1 changed files with 498 additions and 0 deletions
|
@ -207,6 +207,40 @@ func generateObject(addr oid.Address, prev *oid.ID, payload []byte, children ...
|
|||
return obj
|
||||
}
|
||||
|
||||
type writeHeaderError struct{}
|
||||
|
||||
func (whe *writeHeaderError) Error() string {
|
||||
return "write header error"
|
||||
}
|
||||
|
||||
type writeHeaderErrorObjectWriter struct {
|
||||
}
|
||||
|
||||
func (w *writeHeaderErrorObjectWriter) WriteHeader(_ *objectSDK.Object) error {
|
||||
return &writeHeaderError{}
|
||||
}
|
||||
|
||||
func (w *writeHeaderErrorObjectWriter) WriteChunk(p []byte) error {
|
||||
return nil
|
||||
}
|
||||
|
||||
type writePayloadError struct{}
|
||||
|
||||
func (whe *writePayloadError) Error() string {
|
||||
return "write payload error"
|
||||
}
|
||||
|
||||
type writePayloadErrorObjectWriter struct {
|
||||
}
|
||||
|
||||
func (w *writePayloadErrorObjectWriter) WriteHeader(_ *objectSDK.Object) error {
|
||||
return nil
|
||||
}
|
||||
|
||||
func (w *writePayloadErrorObjectWriter) WriteChunk(p []byte) error {
|
||||
return &writePayloadError{}
|
||||
}
|
||||
|
||||
func TestGetLocalOnly(t *testing.T) {
|
||||
ctx := context.Background()
|
||||
|
||||
|
@ -902,6 +936,340 @@ func TestGetRemoteSmall(t *testing.T) {
|
|||
require.NoError(t, err)
|
||||
require.Equal(t, payload[off:off+ln], w.Object().Payload())
|
||||
})
|
||||
|
||||
t.Run("write header/payload failure", func(t *testing.T) {
|
||||
addr := oidtest.Address()
|
||||
addr.SetContainer(idCnr)
|
||||
addr.SetObject(oidtest.ID())
|
||||
|
||||
srcObj := generateObject(addr, nil, nil)
|
||||
|
||||
ns, as := testNodeMatrix(t, []int{2})
|
||||
|
||||
splitInfo := objectSDK.NewSplitInfo()
|
||||
splitInfo.SetLink(oidtest.ID())
|
||||
|
||||
children, childIDs, payload := generateChain(2, idCnr)
|
||||
srcObj.SetPayload(payload)
|
||||
srcObj.SetPayloadSize(uint64(len(payload)))
|
||||
children[len(children)-1].SetParent(srcObj)
|
||||
|
||||
var linkAddr oid.Address
|
||||
linkAddr.SetContainer(idCnr)
|
||||
idLink, _ := splitInfo.Link()
|
||||
linkAddr.SetObject(idLink)
|
||||
|
||||
linkingObj := generateObject(linkAddr, nil, nil, childIDs...)
|
||||
linkingObj.SetParentID(addr.Object())
|
||||
linkingObj.SetParent(srcObj)
|
||||
|
||||
var child1Addr oid.Address
|
||||
child1Addr.SetContainer(idCnr)
|
||||
child1Addr.SetObject(childIDs[0])
|
||||
|
||||
var child2Addr oid.Address
|
||||
child2Addr.SetContainer(idCnr)
|
||||
child2Addr.SetObject(childIDs[1])
|
||||
|
||||
c1 := newTestClient()
|
||||
c1.addResult(addr, nil, errors.New("any error"))
|
||||
c1.addResult(linkAddr, nil, errors.New("any error"))
|
||||
c1.addResult(child1Addr, nil, errors.New("any error"))
|
||||
c1.addResult(child2Addr, nil, errors.New("any error"))
|
||||
|
||||
c2 := newTestClient()
|
||||
c2.addResult(addr, nil, objectSDK.NewSplitInfoError(splitInfo))
|
||||
c2.addResult(linkAddr, linkingObj, nil)
|
||||
c2.addResult(child1Addr, children[0], nil)
|
||||
c2.addResult(child2Addr, children[1], nil)
|
||||
|
||||
builder := &testPlacementBuilder{
|
||||
vectors: map[string][][]netmap.NodeInfo{
|
||||
addr.EncodeToString(): ns,
|
||||
linkAddr.EncodeToString(): ns,
|
||||
child1Addr.EncodeToString(): ns,
|
||||
child2Addr.EncodeToString(): ns,
|
||||
},
|
||||
}
|
||||
|
||||
svc := newSvc(builder, &testClientCache{
|
||||
clients: map[string]*testClient{
|
||||
as[0][0]: c1,
|
||||
as[0][1]: c2,
|
||||
},
|
||||
})
|
||||
|
||||
testHeadVirtual(svc, addr, splitInfo)
|
||||
|
||||
wh := &writeHeaderErrorObjectWriter{}
|
||||
|
||||
p := newPrm(false, wh)
|
||||
p.WithAddress(addr)
|
||||
|
||||
err := svc.Get(ctx, p)
|
||||
require.ErrorAs(t, err, new(*writeHeaderError))
|
||||
|
||||
wp := &writePayloadErrorObjectWriter{}
|
||||
|
||||
p = newPrm(false, wp)
|
||||
p.WithAddress(addr)
|
||||
|
||||
err = svc.Get(ctx, p)
|
||||
require.ErrorAs(t, err, new(*writePayloadError))
|
||||
})
|
||||
|
||||
t.Run("linked object not a child of parent", func(t *testing.T) {
|
||||
addr := oidtest.Address()
|
||||
addr.SetContainer(idCnr)
|
||||
addr.SetObject(oidtest.ID())
|
||||
|
||||
srcObj := generateObject(addr, nil, nil)
|
||||
|
||||
ns, as := testNodeMatrix(t, []int{2})
|
||||
|
||||
splitInfo := objectSDK.NewSplitInfo()
|
||||
splitInfo.SetLink(oidtest.ID())
|
||||
|
||||
children, childIDs, payload := generateChain(2, idCnr)
|
||||
srcObj.SetPayload(payload)
|
||||
srcObj.SetPayloadSize(uint64(len(payload)))
|
||||
children[len(children)-1].SetParent(srcObj)
|
||||
|
||||
var linkAddr oid.Address
|
||||
linkAddr.SetContainer(idCnr)
|
||||
idLink, _ := splitInfo.Link()
|
||||
linkAddr.SetObject(idLink)
|
||||
|
||||
wrongParentAddr := oidtest.Address()
|
||||
wrongParentID := oidtest.ID()
|
||||
wrongParentAddr.SetObject(wrongParentID)
|
||||
wrongParentAddr.SetContainer(idCnr)
|
||||
wrongParent := generateObject(wrongParentAddr, nil, nil)
|
||||
|
||||
linkingObj := generateObject(linkAddr, nil, nil, childIDs...)
|
||||
linkingObj.SetParentID(wrongParentID)
|
||||
linkingObj.SetParent(wrongParent)
|
||||
|
||||
var child1Addr oid.Address
|
||||
child1Addr.SetContainer(idCnr)
|
||||
child1Addr.SetObject(childIDs[0])
|
||||
|
||||
var child2Addr oid.Address
|
||||
child2Addr.SetContainer(idCnr)
|
||||
child2Addr.SetObject(childIDs[1])
|
||||
|
||||
c1 := newTestClient()
|
||||
c1.addResult(addr, nil, errors.New("any error"))
|
||||
c1.addResult(linkAddr, nil, errors.New("any error"))
|
||||
c1.addResult(child1Addr, nil, errors.New("any error"))
|
||||
c1.addResult(child2Addr, nil, errors.New("any error"))
|
||||
|
||||
c2 := newTestClient()
|
||||
c2.addResult(addr, nil, objectSDK.NewSplitInfoError(splitInfo))
|
||||
c2.addResult(linkAddr, linkingObj, nil)
|
||||
c2.addResult(child1Addr, children[0], nil)
|
||||
c2.addResult(child2Addr, children[1], nil)
|
||||
|
||||
builder := &testPlacementBuilder{
|
||||
vectors: map[string][][]netmap.NodeInfo{
|
||||
addr.EncodeToString(): ns,
|
||||
linkAddr.EncodeToString(): ns,
|
||||
child1Addr.EncodeToString(): ns,
|
||||
child2Addr.EncodeToString(): ns,
|
||||
},
|
||||
}
|
||||
|
||||
svc := newSvc(builder, &testClientCache{
|
||||
clients: map[string]*testClient{
|
||||
as[0][0]: c1,
|
||||
as[0][1]: c2,
|
||||
},
|
||||
})
|
||||
|
||||
testHeadVirtual(svc, addr, splitInfo)
|
||||
|
||||
w := NewSimpleObjectWriter()
|
||||
|
||||
p := newPrm(false, w)
|
||||
p.WithAddress(addr)
|
||||
|
||||
err := svc.Get(ctx, p)
|
||||
require.NoError(t, err) //TODO fix me
|
||||
//require.Equal(t, err.Error(), "wrong child header")
|
||||
|
||||
w = NewSimpleObjectWriter()
|
||||
payloadSz := srcObj.PayloadSize()
|
||||
|
||||
off := payloadSz / 3
|
||||
ln := payloadSz / 3
|
||||
|
||||
rngPrm := newRngPrm(false, w, off, ln)
|
||||
rngPrm.WithAddress(addr)
|
||||
|
||||
err = svc.GetRange(ctx, rngPrm)
|
||||
require.ErrorAs(t, err, new(*apistatus.ObjectOutOfRange)) //TODO fix me
|
||||
//require.Equal(t, err.Error(), "wrong child header")
|
||||
|
||||
})
|
||||
|
||||
t.Run("linked object with parent udefined", func(t *testing.T) {
|
||||
addr := oidtest.Address()
|
||||
addr.SetContainer(idCnr)
|
||||
addr.SetObject(oidtest.ID())
|
||||
|
||||
srcObj := generateObject(addr, nil, nil)
|
||||
|
||||
ns, as := testNodeMatrix(t, []int{2})
|
||||
|
||||
splitInfo := objectSDK.NewSplitInfo()
|
||||
splitInfo.SetLink(oidtest.ID())
|
||||
|
||||
children, childIDs, payload := generateChain(2, idCnr)
|
||||
srcObj.SetPayload(payload)
|
||||
srcObj.SetPayloadSize(uint64(len(payload)))
|
||||
children[len(children)-1].SetParent(srcObj)
|
||||
|
||||
var linkAddr oid.Address
|
||||
linkAddr.SetContainer(idCnr)
|
||||
idLink, _ := splitInfo.Link()
|
||||
linkAddr.SetObject(idLink)
|
||||
|
||||
linkingObj := generateObject(linkAddr, nil, nil, childIDs...)
|
||||
|
||||
var child1Addr oid.Address
|
||||
child1Addr.SetContainer(idCnr)
|
||||
child1Addr.SetObject(childIDs[0])
|
||||
|
||||
var child2Addr oid.Address
|
||||
child2Addr.SetContainer(idCnr)
|
||||
child2Addr.SetObject(childIDs[1])
|
||||
|
||||
c1 := newTestClient()
|
||||
c1.addResult(addr, nil, errors.New("any error"))
|
||||
c1.addResult(linkAddr, nil, errors.New("any error"))
|
||||
c1.addResult(child1Addr, nil, errors.New("any error"))
|
||||
c1.addResult(child2Addr, nil, errors.New("any error"))
|
||||
|
||||
c2 := newTestClient()
|
||||
c2.addResult(addr, nil, objectSDK.NewSplitInfoError(splitInfo))
|
||||
c2.addResult(linkAddr, linkingObj, nil)
|
||||
c2.addResult(child1Addr, children[0], nil)
|
||||
c2.addResult(child2Addr, children[1], nil)
|
||||
|
||||
builder := &testPlacementBuilder{
|
||||
vectors: map[string][][]netmap.NodeInfo{
|
||||
addr.EncodeToString(): ns,
|
||||
linkAddr.EncodeToString(): ns,
|
||||
child1Addr.EncodeToString(): ns,
|
||||
child2Addr.EncodeToString(): ns,
|
||||
},
|
||||
}
|
||||
|
||||
svc := newSvc(builder, &testClientCache{
|
||||
clients: map[string]*testClient{
|
||||
as[0][0]: c1,
|
||||
as[0][1]: c2,
|
||||
},
|
||||
})
|
||||
|
||||
testHeadVirtual(svc, addr, splitInfo)
|
||||
|
||||
w := NewSimpleObjectWriter()
|
||||
|
||||
p := newPrm(false, w)
|
||||
p.WithAddress(addr)
|
||||
|
||||
err := svc.Get(ctx, p)
|
||||
require.NoError(t, err) //TODO fix me
|
||||
//require.Equal(t, err.Error(), "received child with empty parent")
|
||||
|
||||
w = NewSimpleObjectWriter()
|
||||
payloadSz := srcObj.PayloadSize()
|
||||
|
||||
off := payloadSz / 3
|
||||
ln := payloadSz / 3
|
||||
|
||||
rngPrm := newRngPrm(false, w, off, ln)
|
||||
rngPrm.WithAddress(addr)
|
||||
|
||||
err = svc.GetRange(ctx, rngPrm)
|
||||
require.NoError(t, err) //TODO fix me
|
||||
//require.Equal(t, err.Error(), "received child with empty parent")
|
||||
})
|
||||
|
||||
t.Run("out of range", func(t *testing.T) {
|
||||
addr := oidtest.Address()
|
||||
addr.SetContainer(idCnr)
|
||||
addr.SetObject(oidtest.ID())
|
||||
|
||||
srcObj := generateObject(addr, nil, nil)
|
||||
|
||||
ns, as := testNodeMatrix(t, []int{2})
|
||||
|
||||
splitInfo := objectSDK.NewSplitInfo()
|
||||
splitInfo.SetLink(oidtest.ID())
|
||||
|
||||
children, childIDs, payload := generateChain(2, idCnr)
|
||||
srcObj.SetPayload(payload)
|
||||
srcObj.SetPayloadSize(uint64(len(payload)))
|
||||
children[len(children)-1].SetParent(srcObj)
|
||||
|
||||
var linkAddr oid.Address
|
||||
linkAddr.SetContainer(idCnr)
|
||||
idLink, _ := splitInfo.Link()
|
||||
linkAddr.SetObject(idLink)
|
||||
|
||||
linkingObj := generateObject(linkAddr, nil, nil, childIDs...)
|
||||
linkingObj.SetParentID(addr.Object())
|
||||
linkingObj.SetParent(srcObj)
|
||||
|
||||
var child1Addr oid.Address
|
||||
child1Addr.SetContainer(idCnr)
|
||||
child1Addr.SetObject(childIDs[0])
|
||||
|
||||
var child2Addr oid.Address
|
||||
child2Addr.SetContainer(idCnr)
|
||||
child2Addr.SetObject(childIDs[1])
|
||||
|
||||
c1 := newTestClient()
|
||||
c1.addResult(addr, nil, errors.New("any error"))
|
||||
c1.addResult(linkAddr, nil, errors.New("any error"))
|
||||
c1.addResult(child1Addr, nil, errors.New("any error"))
|
||||
c1.addResult(child2Addr, nil, errors.New("any error"))
|
||||
|
||||
c2 := newTestClient()
|
||||
c2.addResult(addr, nil, objectSDK.NewSplitInfoError(splitInfo))
|
||||
c2.addResult(linkAddr, linkingObj, nil)
|
||||
c2.addResult(child1Addr, children[0], nil)
|
||||
c2.addResult(child2Addr, children[1], nil)
|
||||
|
||||
builder := &testPlacementBuilder{
|
||||
vectors: map[string][][]netmap.NodeInfo{
|
||||
addr.EncodeToString(): ns,
|
||||
linkAddr.EncodeToString(): ns,
|
||||
child1Addr.EncodeToString(): ns,
|
||||
child2Addr.EncodeToString(): ns,
|
||||
},
|
||||
}
|
||||
|
||||
svc := newSvc(builder, &testClientCache{
|
||||
clients: map[string]*testClient{
|
||||
as[0][0]: c1,
|
||||
as[0][1]: c2,
|
||||
},
|
||||
})
|
||||
|
||||
testHeadVirtual(svc, addr, splitInfo)
|
||||
|
||||
w := NewSimpleObjectWriter()
|
||||
|
||||
p := newRngPrm(false, w, uint64(len(payload)), uint64(len(payload)))
|
||||
p.WithAddress(addr)
|
||||
|
||||
err := svc.GetRange(ctx, p)
|
||||
require.ErrorAs(t, err, new(*apistatus.ObjectOutOfRange))
|
||||
})
|
||||
|
||||
})
|
||||
|
||||
t.Run("right child", func(t *testing.T) {
|
||||
|
@ -1025,6 +1393,97 @@ func TestGetRemoteSmall(t *testing.T) {
|
|||
require.ErrorAs(t, err, new(apistatus.ObjectNotFound))
|
||||
})
|
||||
|
||||
t.Run("child has different parent", func(t *testing.T) {
|
||||
addr := oidtest.Address()
|
||||
addr.SetContainer(idCnr)
|
||||
addr.SetObject(oidtest.ID())
|
||||
|
||||
srcObj := generateObject(addr, nil, nil)
|
||||
|
||||
ns, as := testNodeMatrix(t, []int{2})
|
||||
|
||||
splitInfo := objectSDK.NewSplitInfo()
|
||||
splitInfo.SetLastPart(oidtest.ID())
|
||||
|
||||
children, _, payload := generateChain(2, idCnr)
|
||||
srcObj.SetPayloadSize(uint64(len(payload)))
|
||||
srcObj.SetPayload(payload)
|
||||
|
||||
wrongParentAddr := oidtest.Address()
|
||||
wrongParentID := oidtest.ID()
|
||||
wrongParentAddr.SetObject(wrongParentID)
|
||||
wrongParentAddr.SetContainer(idCnr)
|
||||
wrongParent := generateObject(wrongParentAddr, nil, nil)
|
||||
|
||||
rightObj := children[len(children)-1]
|
||||
|
||||
idLast, _ := splitInfo.LastPart()
|
||||
rightObj.SetID(idLast)
|
||||
rightObj.SetParentID(addr.Object())
|
||||
rightObj.SetParent(srcObj)
|
||||
|
||||
firstObj := children[0]
|
||||
firstObj.SetParent(wrongParent)
|
||||
firstObj.SetParentID(wrongParentID)
|
||||
|
||||
c1 := newTestClient()
|
||||
c1.addResult(addr, nil, errors.New("any error"))
|
||||
|
||||
for i := range children {
|
||||
c1.addResult(object.AddressOf(children[i]), nil, errors.New("any error"))
|
||||
}
|
||||
|
||||
c2 := newTestClient()
|
||||
c2.addResult(addr, nil, objectSDK.NewSplitInfoError(splitInfo))
|
||||
|
||||
for i := range children {
|
||||
c2.addResult(object.AddressOf(children[i]), children[i], nil)
|
||||
}
|
||||
|
||||
builder := &testPlacementBuilder{
|
||||
vectors: map[string][][]netmap.NodeInfo{},
|
||||
}
|
||||
|
||||
builder.vectors[addr.EncodeToString()] = ns
|
||||
|
||||
for i := range children {
|
||||
builder.vectors[object.AddressOf(children[i]).EncodeToString()] = ns
|
||||
}
|
||||
|
||||
svc := newSvc(builder, &testClientCache{
|
||||
clients: map[string]*testClient{
|
||||
as[0][0]: c1,
|
||||
as[0][1]: c2,
|
||||
},
|
||||
})
|
||||
|
||||
testHeadVirtual(svc, addr, splitInfo)
|
||||
|
||||
w := NewSimpleObjectWriter()
|
||||
|
||||
p := newPrm(false, w)
|
||||
p.WithAddress(addr)
|
||||
|
||||
err := svc.Get(ctx, p)
|
||||
require.NoError(t, err) //TODO fix me, it must be an error, corrupted chain
|
||||
//require.Equal(t, err.Error(), "parent address in child object differs")
|
||||
require.Equal(t, srcObj, w.Object())
|
||||
|
||||
w = NewSimpleObjectWriter()
|
||||
payloadSz := srcObj.PayloadSize()
|
||||
|
||||
off := payloadSz / 3
|
||||
ln := payloadSz / 3
|
||||
|
||||
rngPrm := newRngPrm(false, w, off, ln)
|
||||
rngPrm.WithAddress(addr)
|
||||
|
||||
err = svc.GetRange(ctx, rngPrm)
|
||||
require.NoError(t, err) //TODO fix me, it must be an error, corrupted chain
|
||||
//require.Equal(t, err.Error(), "parent address in child object differs")
|
||||
require.Equal(t, payload[off:off+ln], w.Object().Payload())
|
||||
})
|
||||
|
||||
t.Run("OK", func(t *testing.T) {
|
||||
addr := oidtest.Address()
|
||||
addr.SetContainer(idCnr)
|
||||
|
@ -1115,6 +1574,45 @@ func TestGetRemoteSmall(t *testing.T) {
|
|||
require.Equal(t, payload[off:off+ln], w.Object().Payload())
|
||||
})
|
||||
})
|
||||
|
||||
t.Run("corrupted source object", func(t *testing.T) {
|
||||
addr := oidtest.Address()
|
||||
addr.SetContainer(idCnr)
|
||||
addr.SetObject(oidtest.ID())
|
||||
|
||||
ns, as := testNodeMatrix(t, []int{2})
|
||||
|
||||
splitInfo := objectSDK.NewSplitInfo()
|
||||
|
||||
c1 := newTestClient()
|
||||
c1.addResult(addr, nil, errors.New("any error"))
|
||||
|
||||
c2 := newTestClient()
|
||||
c2.addResult(addr, nil, objectSDK.NewSplitInfoError(splitInfo))
|
||||
|
||||
builder := &testPlacementBuilder{
|
||||
vectors: map[string][][]netmap.NodeInfo{},
|
||||
}
|
||||
|
||||
builder.vectors[addr.EncodeToString()] = ns
|
||||
|
||||
svc := newSvc(builder, &testClientCache{
|
||||
clients: map[string]*testClient{
|
||||
as[0][0]: c1,
|
||||
as[0][1]: c2,
|
||||
},
|
||||
})
|
||||
|
||||
testHeadVirtual(svc, addr, splitInfo)
|
||||
|
||||
w := NewSimpleObjectWriter()
|
||||
|
||||
p := newPrm(false, w)
|
||||
p.WithAddress(addr)
|
||||
|
||||
err := svc.Get(ctx, p)
|
||||
require.ErrorAs(t, err, new(*objectSDK.SplitInfoError))
|
||||
})
|
||||
})
|
||||
}
|
||||
|
||||
|
|
Loading…
Reference in a new issue