Skip to content

EC DELETE#3549

Merged
roman-khimov merged 7 commits intomasterfrom
ec-delete
Sep 18, 2025
Merged

EC DELETE#3549
roman-khimov merged 7 commits intomasterfrom
ec-delete

Conversation

@cthulhu-rider
Copy link
Contributor

No description provided.

@codecov
Copy link

codecov bot commented Aug 28, 2025

Codecov Report

❌ Patch coverage is 78.57143% with 27 lines in your changes missing coverage. Please review.
✅ Project coverage is 26.67%. Comparing base (e8348a9) to head (a7c2a54).
⚠️ Report is 12 commits behind head on master.

Files with missing lines Patch % Lines
pkg/local_object_storage/shard/head.go 56.52% 10 Missing ⚠️
cmd/neofs-lens/internal/meta/get.go 0.00% 7 Missing ⚠️
pkg/local_object_storage/metabase/ec.go 90.32% 2 Missing and 1 partial ⚠️
pkg/local_object_storage/metabase/exists.go 85.00% 3 Missing ⚠️
pkg/local_object_storage/metabase/inhume.go 84.21% 2 Missing and 1 partial ⚠️
pkg/local_object_storage/engine/exists.go 0.00% 1 Missing ⚠️
Additional details and impacted files
@@            Coverage Diff             @@
##           master    #3549      +/-   ##
==========================================
+ Coverage   26.51%   26.67%   +0.15%     
==========================================
  Files         653      654       +1     
  Lines       49290    49373      +83     
==========================================
+ Hits        13071    13169      +98     
+ Misses      35181    35158      -23     
- Partials     1038     1046       +8     

☔ View full report in Codecov by Sentry.
📢 Have feedback on the report? Share it here.

🚀 New features to boost your workflow:
  • ❄️ Test Analytics: Detect flaky tests, report on failures, and find test suite problems.

childAddr := objAddr
childAddr.SetObject(child.GetID())

// TODO: check why Get returns different header
Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

i'll leave an issue for this

Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Because there are limits to what Get can restore from the metabase, it's OK.

@cthulhu-rider cthulhu-rider force-pushed the ec-delete branch 2 times, most recently from 870dd1b to 89b58f0 Compare August 29, 2025 10:56
@cthulhu-rider cthulhu-rider marked this pull request as ready for review August 29, 2025 11:16
Copy link
Member

@roman-khimov roman-khimov left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

This makes a different choice compared to regular big objects, we don't mark children as deleted immediately there, but we handle relations during GC cycle (related to #3551). We need some unified approach.

childAddr := objAddr
childAddr.SetObject(child.GetID())

// TODO: check why Get returns different header
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Because there are limits to what Get can restore from the metabase, it's OK.

@cthulhu-rider
Copy link
Contributor Author

cthulhu-rider commented Sep 10, 2025

This makes a different choice compared to regular big objects, we don't mark children as deleted immediately there, but we handle relations during GC cycle (related to #3551). We need some unified approach.

generally speaking, i expected that i wouldnt need any additional actions and DELETE would work out of the box. All EC parts refer to the parent. And split DELETE works as expected, also building logic around the parent ref. Surprise to me. I'll review again what's missing in the general approach

@cthulhu-rider
Copy link
Contributor Author

cthulhu-rider commented Sep 10, 2025

ok, all parent-child magic when happens in

func (e *StorageEngine) inhumeAddr(addr oid.Address, force bool, tombstone *oid.Address, tombExpiration uint64) (bool, error) {

and collecting of child objects is hardly tied to the split scheme. I see two ways:

  1. Unify the obtaining of child objects, making it independent of the root object's encoding (split, EC, etc.). Object ID is input, a full list of child IDs is output. When deleting, only fact of the relationship itself is important, not how it is obtained.
  2. process EC specifically

finally, i'd like to have 1. Maybe @roman-khimov meant this by

We need some unified approach.

but it'd be a quite shaking change, risky. I suggest to start from 2, and generalize to 1 separately. For example, postpone to #3500 where it almost definitely will be needed

@roman-khimov
Copy link
Member

Think of expired objects,

func (e *StorageEngine) processExpiredObjects(addrs []oid.Address) {
err := e.inhume(addrs, false, nil, 0)
if err != nil {
e.log.Warn("handling expired objects", zap.Error(err))
}
}

Maybe if we're to fix inhumeAddr() for EC it'd be sufficient.

@cthulhu-rider
Copy link
Contributor Author

cthulhu-rider commented Sep 15, 2025

reworked closer to split case

@cthulhu-rider cthulhu-rider force-pushed the ec-delete branch 3 times, most recently from 9b6b39b to 687f621 Compare September 16, 2025 11:52
Signed-off-by: Leonard Lyubich <leonard@morphbits.io>
One less function. One less usage of `getSplitInfo()`.

Signed-off-by: Leonard Lyubich <leonard@morphbits.io>
One less error to worry about.

Signed-off-by: Leonard Lyubich <leonard@morphbits.io>
Previous text was outdated.

Signed-off-by: Leonard Lyubich <leonard@morphbits.io>
Signed-off-by: Leonard Lyubich <leonard@morphbits.io>
@cthulhu-rider cthulhu-rider force-pushed the ec-delete branch 2 times, most recently from 428e719 to 9135b7f Compare September 16, 2025 12:27

var tombPartAddrs []oid.Address
for i := range partNum {
tombPart, err := iec.FormObjectForECPart(signer, tomb, testutil.RandByteSlice(32), iec.PartInfo{
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Why are we splitting tombstones?

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

i havent made any exceptions yet. But given the lack of benefit in ECing them, better to exclude. Their payload is empty anyway

Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Exactly. It's header only and splitting it doesn't make much sense to me. Same goes for locks.

Copy link
Contributor Author

@cthulhu-rider cthulhu-rider Sep 18, 2025

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

fixed this in test. How about excluding tombstones in a separate PR?

Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Works for me.

oid.NewAddress(addr.Container(), si.GetLink())}
case errors.As(err, &errECParts):
if len(errECParts) == 0 {
panic(errors.New("empty EC part set"))
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Worth a panic?

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

yeah, to prevent code mistakes. Subsequent logic assumes that it is non-empty

In general, the mechanism is inherited from split scheme. Key changes:
 - all GET methods return newly added error if EC parent is requested.
   At the moment, only physically stored EC parts are requested. This
   will protect against collision with split case and will reveal
   unadapted places if any.
 - If some EC parts are stored in the metabase along with the object
   being removed, they are also marked. This automates their closure and
   subsequent GC.

Closes #3502.

Signed-off-by: Leonard Lyubich <leonard@morphbits.io>
It is the parent objects that are expiring and deleting in practice.
Reading is also performed at their address.

Previously, the method checked child status instead. In particular, this
led to 404 child status return when parent object was removed. This
collided with the part absence on SN: triggered requests from backup
SN and resulted in 404 final status.

Refs #3502.

Signed-off-by: Leonard Lyubich <leonard@morphbits.io>
@roman-khimov roman-khimov merged commit 231cb3d into master Sep 18, 2025
21 of 22 checks passed
@roman-khimov roman-khimov deleted the ec-delete branch September 18, 2025 13:13
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

2 participants