refactor(storage): narrow resync metadata bounds (#3345)

This commit is contained in:
安正超
2026-06-11 12:41:15 +08:00
committed by GitHub
parent ee96e194a3
commit 2f7cc7cb9e
3 changed files with 62 additions and 53 deletions
@@ -27,7 +27,7 @@ use crate::bucket::replication::replication_state::ReplicationStats;
use crate::config::com::read_config;
use crate::disk::BUCKET_META_PREFIX;
use crate::error::Error as EcstoreError;
use crate::store_api::ObjectInfo;
use crate::store_api::{ObjectIO, ObjectInfo};
use lazy_static::lazy_static;
use rustfs_filemeta::MrfReplicateEntry;
use rustfs_filemeta::ReplicateDecision;
@@ -976,7 +976,7 @@ impl<S: StorageAPI> ReplicationPool<S> {
}
/// Load bucket resync metadata from disk
async fn load_bucket_resync_metadata<S: StorageAPI>(
async fn load_bucket_resync_metadata<S: ObjectIO>(
bucket: &str,
obj_api: Arc<S>,
) -> Result<BucketReplicationResyncStatus, EcstoreError> {
@@ -32,7 +32,7 @@ use crate::event_notification::{EventArgs, send_event};
use crate::global::GLOBAL_LocalNodeName;
use crate::global::get_global_bucket_monitor;
use crate::set_disk::get_lock_acquire_timeout;
use crate::store_api::{DeletedObject, HTTPRangeSpec, ObjectInfo, ObjectOptions, ObjectToDelete, WalkOptions};
use crate::store_api::{DeletedObject, HTTPRangeSpec, ObjectIO, ObjectInfo, ObjectOptions, ObjectToDelete, WalkOptions};
use crate::{StorageAPI, new_object_layer_fn};
use aws_sdk_s3::error::{ProvideErrorMetadata, SdkError};
use aws_sdk_s3::operation::head_object::{HeadObjectError, HeadObjectOutput};
@@ -485,7 +485,7 @@ impl ReplicationResyncer {
}
}
pub async fn mark_status<S: StorageAPI>(&self, status: ResyncStatusType, opts: ResyncOpts, obj_layer: Arc<S>) -> Result<()> {
pub async fn mark_status<S: ObjectIO>(&self, status: ResyncStatusType, opts: ResyncOpts, obj_layer: Arc<S>) -> Result<()> {
let bucket_status = {
let mut status_map = self.status_map.write().await;
let now = OffsetDateTime::now_utc();
@@ -590,7 +590,7 @@ impl ReplicationResyncer {
bucket_status.last_update = Some(now);
}
pub async fn persist_to_disk<S: StorageAPI>(&self, cancel_token: CancellationToken, api: Arc<S>) {
pub async fn persist_to_disk<S: ObjectIO>(&self, cancel_token: CancellationToken, api: Arc<S>) {
let mut interval = tokio::time::interval(RESYNC_TIME_INTERVAL);
let mut last_update_times = HashMap::new();
@@ -635,7 +635,7 @@ impl ReplicationResyncer {
}
}
async fn resync_bucket_mark_status<S: StorageAPI>(&self, status: ResyncStatusType, opts: ResyncOpts, storage: Arc<S>) {
async fn resync_bucket_mark_status<S: ObjectIO>(&self, status: ResyncStatusType, opts: ResyncOpts, storage: Arc<S>) {
if let Err(err) = self.mark_status(status, opts.clone(), storage.clone()).await {
error!("Failed to mark resync status: {}", err);
}
@@ -1026,7 +1026,7 @@ pub async fn get_heal_replicate_object_info(oi: &ObjectInfo, rcfg: &ReplicationC
}
}
pub(crate) async fn save_resync_status<S: StorageAPI>(
pub(crate) async fn save_resync_status<S: ObjectIO>(
bucket: &str,
status: &BucketReplicationResyncStatus,
api: Arc<S>,
+55 -46
View File
@@ -5,16 +5,16 @@ Status values: `[ ]` not started, `[~]` in progress, `[x]` complete, `[!]` block
## Current Context
- Issue: [`rustfs/backlog#660`](https://github.com/rustfs/backlog/issues/660)
- Branch: `overtrue/arch-storage-api-bound-narrowing`
- Baseline: `origin/main` at `6b86e3875c4912f3a7c27915b0bbd43399402847`
- Branch: `overtrue/arch-replication-resync-bounds`
- Baseline: `origin/main` at `7191a3abae08918eedb117955280dc81e65450de`
- PR type for this branch: `dependency-migration`
- Runtime behavior changes: none.
- Rust code changes: narrow metadata helper generic bounds away from full
`StorageAPI` where helpers only need object I/O, object metadata/delete,
bucket listing, object listing, or `StorageAdminApi`.
- Rust code changes: narrow replication resync metadata helper generic bounds
away from full `StorageAPI` where helpers only need object I/O.
- CI/script changes: none.
- Docs changes: record API-008 completion and the current bound-narrowing
context, verification evidence, and expert review outcomes.
- Docs changes: record API-009 completion and the current replication resync
metadata bound-narrowing context, verification evidence, and expert review
outcomes.
## Phase 0 Tasks
@@ -226,25 +226,35 @@ Status values: `[ ]` not started, `[~]` in progress, `[x]` complete, `[!]` block
`new_ns_lock`, while admin inventory surfaces live only on
`StorageAdminApi`.
- [~] `API-009` Narrow metadata helper storage bounds.
- Current branch slice: narrow server config, tier config, rebalance
metadata, and startup metadata migration helper bounds away from full
`StorageAPI` when the helper only needs `ObjectIO`, `ObjectOperations`,
`BucketOperations`, `ListOperations`, or `StorageAdminApi`.
- [x] `API-009` Narrow metadata helper storage bounds.
- Completed slice: `rustfs/rustfs#3343` narrowed server config, tier config,
rebalance metadata, and startup metadata migration helper bounds away from
full `StorageAPI` when the helper only needs `ObjectIO`,
`ObjectOperations`, `BucketOperations`, `ListOperations`, or
`StorageAdminApi`.
- Acceptance: metadata helper contracts express the actual operation group
they need, while callers and persistence behavior remain unchanged.
- Must preserve: config/tier/rebalance serialized byte shapes, read/write
object names, legacy bucket/IAM migration normalization and skip behavior,
lock behavior around rebalance metadata merge, dynamic storage-class lookup,
object APIs, scanner cache persistence, heal repair, replication
persistence, and storage hot paths.
- [~] `API-010` Narrow replication resync metadata bounds.
- Current branch slice: narrow replication resync status load/save/mark/persist
helper bounds away from full `StorageAPI` when the helper only needs
`ObjectIO`.
- Acceptance: resync metadata helpers express object-I/O-only persistence
requirements, while replication execution, delete replication, multipart
replication, object lookups, and scheduling behavior remain on full
`StorageAPI` where needed.
- Must preserve: resync status serialization, resync metadata object paths,
in-memory status-map mutation order, stale-update rejection, periodic
persistence cadence, worker-token behavior, target replication decisions,
object replication, delete replication, multipart replication, scanner,
heal, and storage hot paths.
- Risk defense: do not move traits to `rustfs-storage-api`, do not remove
`StorageAPI`, do not alter helper bodies or storage options, and keep
`save_rebalance_meta_with_merge` on full `StorageAPI` because it still needs
`new_ns_lock`.
- Verification: focused compile/tests, migration guards, Rust risk scan, and
required quality/architecture, migration-preservation, and
testing/verification review passed before push.
`StorageAPI`, do not alter helper bodies or storage options, and do not
narrow replication execution paths that use object/list/multipart/delete
operations beyond metadata persistence.
- Verification: focused compile/tests, migration guards, and Rust risk scan
passed; required quality/architecture, migration-preservation, and
testing/verification review is pending before push.
## Phase 8 Background Controller Tasks
@@ -269,8 +279,8 @@ Status values: `[ ]` not started, `[~]` in progress, `[x]` complete, `[!]` block
## Next PRs
1. `dependency-migration`: narrow metadata/helper bounds away from full
`StorageAPI` where the helper only needs a specific operation trait.
1. `dependency-migration`: narrow replication resync metadata helper bounds
away from full `StorageAPI` where the helper only needs `ObjectIO`.
2. `api-extraction`: move only the pure server-config model into
rustfs-config as CFG-003.
3. `api-extraction`: keep the old rustfs_ecstore::config::* path with
@@ -286,9 +296,9 @@ Status values: `[ ]` not started, `[~]` in progress, `[x]` complete, `[!]` block
| Expert | Status | Notes |
|---|---|---|
| Quality/architecture | pass | Confirmed the Rust diff only changes imports/generic bounds, the new operation-group bounds match actual calls, `StorageAPI` and `new_ns_lock` remain where needed, and no over-abstraction, naming regression, dependency reversal, or hot-path intrusion was found. |
| Migration preservation | pass | Confirmed config/tier/rebalance byte shapes, object names, buckets, options, bucket/IAM normalization and skip behavior, dynamic storage-class lookup, and rebalance metadata merge locking remain unchanged. |
| Testing/verification | pass | Confirmed the focused compile, config/tier/rebalance/bucket migration tests, migration guards, diff hygiene, and added-line Rust risk scan are sufficient; full pre-commit can be skipped under the current larger-granularity instruction. |
| Quality/architecture | pass | Confirmed the Rust diff only adds the `ObjectIO` import and narrows resync metadata load/save/mark/persist helper bounds; helper bodies are unchanged, broader replication execution paths remain on `StorageAPI`, and no new abstraction or crate split was added. |
| Migration preservation | pass | Confirmed `read_config`/`save_config` already use the `ObjectIO` contract, while resync metadata serialization, object paths, storage options, status-map flow, and object/delete/multipart replication paths remain unchanged. |
| Testing/verification | pass | Confirmed the focused compile, replication/resync tests, migration guards, diff hygiene, and added-line risk scan are sufficient for this generic-bound-only slice, so full pre-commit can be skipped under the current larger-granularity instruction. |
## Verification Notes
@@ -297,41 +307,40 @@ Passed:
- `cargo check -p rustfs-ecstore`.
- `cargo fmt --all --check`.
- `cargo check -p rustfs-storage-api -p rustfs-ecstore -p rustfs --lib`.
- `cargo test -p rustfs-ecstore config --lib`; 59 passed.
- `cargo test -p rustfs-ecstore tier --lib`; 27 passed.
- `cargo test -p rustfs-ecstore rebalance --lib`; 198 passed.
- `cargo test -p rustfs-ecstore bucket::migration --lib`; 2 passed.
- `cargo test -p rustfs-ecstore replication --lib`; 58 passed.
- `cargo test -p rustfs-ecstore resync --lib`; 31 passed.
- `./scripts/check_architecture_migration_rules.sh`.
- `./scripts/check_layer_dependencies.sh`.
- `./scripts/check_metrics_migration_refs.sh`.
- `./scripts/check_unsafe_code_allowances.sh`.
- `git diff --check`.
- Rust code-quality scan on changed `.rs` files: broad full-file matches are
pre-existing test/business-code patterns; added-line scan found no new
unwrap/expect, numeric cast, `Result<_, String>`, `Box<dyn Error>`,
println/eprintln, or `Ordering::Relaxed`.
- Rust code-quality scan on changed `.rs` files, plus added-line scan for
unwrap/expect, numeric casts, `Result<_, String>`, `Box<dyn Error>`,
println/eprintln, and `Ordering::Relaxed`; broad full-file matches are
pre-existing touched-file patterns, and the added-line scan found no new
risky code patterns.
Notes:
- Full pre-commit is intentionally skipped when the focused tests and guards
pass, per the current instruction to increase PR granularity.
- This slice changes generic bounds and imports only; helper bodies, storage
options, object names, and metadata normalization logic are unchanged.
- `save_rebalance_meta_with_merge` intentionally still requires full
`StorageAPI` because it uses `new_ns_lock`.
options, object paths, and resync serialization logic are unchanged.
- Replication execution paths intentionally still require full `StorageAPI`
where they use object/list/multipart/delete operations.
- No temporary compatibility shim was added.
## Handoff Notes
- Keep this API-009 slice as a `dependency-migration` PR that only narrows
metadata/helper generic bounds for config, tier, rebalance, and startup
metadata migration helpers.
- Keep this API-010 slice as a `dependency-migration` PR that only narrows
replication resync metadata helper generic bounds.
- Do not remove `StorageAPI` itself, object operation traits, or
`new_ns_lock` in this PR.
- Do not move traits into `rustfs-storage-api` or introduce new compatibility
shims in this PR.
- Do not alter config/tier/rebalance serialized byte shapes, legacy bucket/IAM
migration normalization, object names, storage options, scanner cache writes,
heal object repair, object APIs, replication persistence, or storage hot-path
consumers in this PR.
- Do not alter resync status serialization, metadata object paths, stale-update
rejection, status-map mutation order, periodic persistence cadence, worker
token behavior, replication execution, delete replication, multipart
replication, scanner cache writes, heal object repair, object APIs, or storage
hot-path consumers in this PR.
- Do not add temporary compatibility code unless a matching
`RUSTFS_COMPAT_TODO(<task-id>)` marker and cleanup-register entry are added.