package meta_test import ( "testing" "git.frostfs.info/TrueCloudLab/frostfs-node/pkg/core/object" "git.frostfs.info/TrueCloudLab/frostfs-node/pkg/local_object_storage/internal/testutil" meta "git.frostfs.info/TrueCloudLab/frostfs-node/pkg/local_object_storage/metabase" apistatus "git.frostfs.info/TrueCloudLab/frostfs-sdk-go/client/status" oid "git.frostfs.info/TrueCloudLab/frostfs-sdk-go/object/id" oidtest "git.frostfs.info/TrueCloudLab/frostfs-sdk-go/object/id/test" "github.com/stretchr/testify/require" ) func TestDB_Inhume(t *testing.T) { db := newDB(t) raw := testutil.GenerateObject() testutil.AddAttribute(raw, "foo", "bar") tombstoneID := oidtest.Address() err := putBig(db, raw) require.NoError(t, err) err = metaInhume(db, object.AddressOf(raw), tombstoneID) require.NoError(t, err) _, err = metaExists(db, object.AddressOf(raw)) require.ErrorAs(t, err, new(apistatus.ObjectAlreadyRemoved)) _, err = metaGet(db, object.AddressOf(raw), false) require.ErrorAs(t, err, new(apistatus.ObjectAlreadyRemoved)) } func TestInhumeTombOnTomb(t *testing.T) { db := newDB(t) var ( err error addr1 = oidtest.Address() addr2 = oidtest.Address() addr3 = oidtest.Address() inhumePrm meta.InhumePrm existsPrm meta.ExistsPrm ) inhumePrm.SetAddresses(addr1) inhumePrm.SetTombstoneAddress(addr2) // inhume addr1 via addr2 _, err = db.Inhume(inhumePrm) require.NoError(t, err) existsPrm.SetAddress(addr1) // addr1 should become inhumed {addr1:addr2} _, err = db.Exists(existsPrm) require.ErrorAs(t, err, new(apistatus.ObjectAlreadyRemoved)) inhumePrm.SetAddresses(addr3) inhumePrm.SetTombstoneAddress(addr1) // try to inhume addr3 via addr1 _, err = db.Inhume(inhumePrm) require.NoError(t, err) // record with {addr1:addr2} should be removed from graveyard // as a tomb-on-tomb; metabase should return ObjectNotFound // NOT ObjectAlreadyRemoved since that record has been removed // from graveyard but addr1 is still marked with GC _, err = db.Exists(existsPrm) require.ErrorAs(t, err, new(apistatus.ObjectNotFound)) existsPrm.SetAddress(addr3) // addr3 should be inhumed {addr3: addr1} _, err = db.Exists(existsPrm) require.ErrorAs(t, err, new(apistatus.ObjectAlreadyRemoved)) inhumePrm.SetAddresses(addr1) inhumePrm.SetTombstoneAddress(oidtest.Address()) // try to inhume addr1 (which is already a tombstone in graveyard) _, err = db.Inhume(inhumePrm) require.NoError(t, err) existsPrm.SetAddress(addr1) // record with addr1 key should not appear in graveyard // (tomb can not be inhumed) but should be kept as object // with GC mark _, err = db.Exists(existsPrm) require.ErrorAs(t, err, new(apistatus.ObjectNotFound)) } func TestInhumeLocked(t *testing.T) { db := newDB(t) locked := oidtest.Address() err := db.Lock(locked.Container(), oidtest.ID(), []oid.ID{locked.Object()}) require.NoError(t, err) var prm meta.InhumePrm prm.SetAddresses(locked) _, err = db.Inhume(prm) var e apistatus.ObjectLocked require.ErrorAs(t, err, &e) } func metaInhume(db *meta.DB, target, tomb oid.Address) error { var inhumePrm meta.InhumePrm inhumePrm.SetAddresses(target) inhumePrm.SetTombstoneAddress(tomb) _, err := db.Inhume(inhumePrm) return err }