mirror of
https://github.com/rustfs/rustfs.git
synced 2026-07-28 17:18:58 +00:00
refactor(replication): isolate object decision contracts (#4219)
This commit is contained in:
@@ -12,10 +12,11 @@ paths.
|
||||
|---|---|---|
|
||||
| `config.rs` | Replication config helpers, rule matching, and tag filtering. | Uses replication-local filemeta/tagging boundaries and S3 DTOs directly. |
|
||||
| `datatypes.rs` | ECStore compatibility re-export for resync status enums. | Re-exports `rustfs-replication` contracts while downstream facade consumers migrate. |
|
||||
| `replication_object_decision_boundary.rs` | Object replication option DTOs, resync target projection, delete replication decisions, and multipart planning helpers. | Keeps ECStore runtime modules from importing object decision contracts directly from `rustfs-replication`. |
|
||||
| `replication_pool.rs` | Replication queue, worker pool, MRF persistence, bucket stats, and delete/object scheduling. | Depends on bucket target sys, bucket metadata sys, metadata paths, queue contracts through the queue boundary, file metadata replication contracts through local boundaries, config storage, storage contracts through the replication storage boundary, runtime sources, and notification state. |
|
||||
| `replication_queue_boundary.rs` | Queue/admission DTOs, heal queue DTOs, worker sizing, and backpressure helpers. | Keeps ECStore runtime modules from importing queue/backpressure contracts directly from `rustfs-replication`. |
|
||||
| `replication_resync_boundary.rs` | Resync DTOs, status classifiers, persisted resync/MRF codec wrappers, and ECStore error mapping. | Keeps ECStore runtime modules from importing resync contract helpers directly from `rustfs-replication`. |
|
||||
| `replication_resyncer.rs` | Object replication, delete replication, resync execution, target calls, and multipart target upload paths. | Depends on target calls and target config types through the replication target boundary, metadata paths and metadata systems through the replication metadata boundary, file metadata replication contracts through the filemeta boundary, resync contracts through the resync boundary, error contracts through the error boundary, versioning systems, storage contracts through the replication storage boundary, config-derived storage class labels through the config store, runtime sources, notification events and local event host selection through the event sink, bandwidth reader wrapping, and SetDisks lock timing. |
|
||||
| `replication_resyncer.rs` | Object replication, delete replication, resync execution, target calls, and multipart target upload paths. | Depends on target calls and target config types through the replication target boundary, metadata paths and metadata systems through the replication metadata boundary, file metadata replication contracts through the filemeta boundary, object decisions and multipart planning through the object decision boundary, resync contracts through the resync boundary, queue DTOs through the queue boundary, error contracts through the error boundary, versioning systems, storage contracts through the replication storage boundary, config-derived storage class labels through the config store, runtime sources, notification events and local event host selection through the event sink, bandwidth reader wrapping, and SetDisks lock timing. |
|
||||
| `replication_state.rs` | Replication queue/stat state and worker accounting. | Reads runtime sources, file metadata replication contracts, error contracts, and bucket monitor handles through local boundaries, and owns shared replication pool/stat state. |
|
||||
| `replication_lifecycle_bridge.rs` | Lifecycle-originated delete replication admission and version-purge state construction. | Depends on replication config/rule matching, delete-replication decisions, and replication delete scheduling through a local contract type. |
|
||||
| `replication_migration_bridge.rs` | Bucket migration access to persisted replication resync codec helpers. | Keeps migration normalization behind a bridge instead of re-exporting resyncer codec helpers. |
|
||||
@@ -35,6 +36,7 @@ paths.
|
||||
| `ReplicationResyncContracts` | Resync options, target status, bucket status, status classifiers, and persisted resync/MRF status wire format. | Owned by `crates/replication`; ECStore imports them through `replication_resync_boundary.rs`, which maps crate errors to ECStore errors. |
|
||||
| `ReplicationConfigStore` | Replication config persistence and config-derived labels used by target options. | Config read/save helpers and storage class labels are exposed through the contract type in `replication_config_store.rs`. |
|
||||
| `ReplicationFileMeta` | Replication status, decisions, MRF entries, resync decisions, and target reset helpers. | `rustfs_filemeta` replication contracts are concentrated in `replication_filemeta_boundary.rs`; `FileInfo` remains in the storage boundary for storage trait bindings and walk options. |
|
||||
| `ReplicationObjectDecisionContracts` | Object replication options, delete replication decisions, resync target projection, multipart planning, and delete-marker retry classifiers. | Owned by `crates/replication`; ECStore imports them through `replication_object_decision_boundary.rs`. |
|
||||
| `ReplicationQueueContracts` | Queue admission, heal queue results/actions, worker operations, worker sizing, and backpressure decisions. | Owned by `crates/replication`; ECStore imports them through `replication_queue_boundary.rs`. |
|
||||
| `ReplicationErrorBoundary` | ECStore error/result contracts and replication-specific error classifiers. | `crate::error` imports are concentrated in `replication_error_boundary.rs`. |
|
||||
| `ReplicationTargetStore` | Bucket target listing, target client lookup, target offline checks, target config types, target operation option types, and target HeadObject comparison adapters. | Bucket target sys access, `BucketTargets`, target operation types, and HeadObject-to-replication DTO adapters are exposed through the contract type in `replication_target_boundary.rs`. |
|
||||
|
||||
@@ -27,6 +27,7 @@ mod replication_migration_bridge;
|
||||
mod replication_msgp_boundary;
|
||||
mod replication_object_bridge;
|
||||
mod replication_object_config;
|
||||
mod replication_object_decision_boundary;
|
||||
pub(crate) mod replication_pool;
|
||||
mod replication_queue_boundary;
|
||||
mod replication_resync_boundary;
|
||||
@@ -46,6 +47,7 @@ pub(crate) use replication_lifecycle_bridge::{ReplicationLifecycleBridge, Replic
|
||||
pub(crate) use replication_migration_bridge::ReplicationMigrationBridge;
|
||||
pub use replication_object_bridge::ReplicationObjectBridge;
|
||||
pub use replication_object_config::ReplicationConfig;
|
||||
pub use replication_object_decision_boundary::MustReplicateOptions;
|
||||
pub use replication_pool::{
|
||||
DynReplicationPool, ReplicationPoolTrait, get_global_replication_pool, get_global_replication_stats,
|
||||
init_background_replication,
|
||||
@@ -59,4 +61,4 @@ pub use replication_scanner_bridge::ReplicationScannerBridge;
|
||||
pub use replication_state::ReplicationStats;
|
||||
pub use replication_storage_boundary::{ReplicationObjectIO, ReplicationStorage};
|
||||
pub(crate) use replication_target_config_bridge::ReplicationTargetConfigBridge;
|
||||
pub use rustfs_replication::{BucketStats, MustReplicateOptions};
|
||||
pub use rustfs_replication::BucketStats;
|
||||
|
||||
@@ -16,10 +16,10 @@ use std::{collections::HashMap, sync::Arc};
|
||||
|
||||
use super::replication_filemeta_boundary::{ReplicateDecision, ReplicationStatusType, ReplicationType};
|
||||
use super::replication_object_config::{check_replicate_delete, get_must_replicate_options, must_replicate};
|
||||
use super::replication_object_decision_boundary::MustReplicateOptions;
|
||||
use super::replication_pool::{schedule_replication, schedule_replication_delete};
|
||||
use super::replication_queue_boundary::DeletedObjectReplicationInfo;
|
||||
use super::replication_storage_boundary::{ObjectInfo, ObjectOptions, ObjectToDelete, ReplicationStorage};
|
||||
use rustfs_replication::MustReplicateOptions;
|
||||
|
||||
pub struct ReplicationObjectBridge;
|
||||
|
||||
|
||||
@@ -14,10 +14,6 @@
|
||||
|
||||
use std::collections::HashMap;
|
||||
|
||||
use rustfs_replication::{
|
||||
MustReplicateOptions, ReplicationDeleteSource, ReplicationResyncTargetObject, delete_replication_missing_source_decision,
|
||||
delete_replication_object_opts, resync_target_for_object,
|
||||
};
|
||||
use rustfs_utils::http::AMZ_BUCKET_REPLICATION_STATUS;
|
||||
use s3s::dto::ReplicationConfiguration;
|
||||
use serde::{Deserialize, Serialize};
|
||||
@@ -30,6 +26,10 @@ use super::replication_filemeta_boundary::{
|
||||
};
|
||||
use super::replication_logging::{EVENT_RESYNC_CONFIG_LOOKUP_SKIPPED, LOG_COMPONENT_ECSTORE, LOG_SUBSYSTEM_REPLICATION_RESYNC};
|
||||
use super::replication_metadata_boundary::ReplicationMetadataStore;
|
||||
use super::replication_object_decision_boundary::{
|
||||
MustReplicateOptions, ReplicationDeleteSource, ReplicationResyncTargetObject, delete_replication_missing_source_decision,
|
||||
delete_replication_object_opts, resync_target_for_object,
|
||||
};
|
||||
use super::replication_storage_boundary::{ObjectInfo, ObjectOptions, ObjectToDelete};
|
||||
use super::replication_target_boundary::{BucketTargets, ReplicationTargetStore};
|
||||
use super::replication_versioning_boundary::ReplicationVersioningStore;
|
||||
|
||||
@@ -0,0 +1,22 @@
|
||||
// Copyright 2024 RustFS Team
|
||||
//
|
||||
// Licensed under the Apache License, Version 2.0 (the "License");
|
||||
// you may not use this file except in compliance with the License.
|
||||
// You may obtain a copy of the License at
|
||||
//
|
||||
// http://www.apache.org/licenses/LICENSE-2.0
|
||||
//
|
||||
// Unless required by applicable law or agreed to in writing, software
|
||||
// distributed under the License is distributed on an "AS IS" BASIS,
|
||||
// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
// See the License for the specific language governing permissions and
|
||||
// limitations under the License.
|
||||
|
||||
pub use rustfs_replication::MustReplicateOptions;
|
||||
pub(crate) use rustfs_replication::{
|
||||
ReplicationDeleteSource, ReplicationMultipartPartInput, ReplicationResyncTargetObject,
|
||||
delete_replication_missing_source_decision, delete_replication_object_opts, heal_uses_delete_replication_path,
|
||||
is_retryable_delete_replication_head_error, is_version_delete_replication, replication_etags_match,
|
||||
replication_multipart_complete_actual_size, replication_multipart_part_plan, resync_target_for_object,
|
||||
should_retry_delete_marker_purge,
|
||||
};
|
||||
@@ -29,6 +29,11 @@ use super::replication_metadata_boundary::ReplicationMetadataStore;
|
||||
#[cfg(test)]
|
||||
use super::replication_msgp_boundary::ReplicationMsgpCodec;
|
||||
use super::replication_object_config::{ReplicationConfig, check_replicate_delete, get_replication_config, must_replicate};
|
||||
use super::replication_object_decision_boundary::{
|
||||
MustReplicateOptions, ReplicationMultipartPartInput, heal_uses_delete_replication_path,
|
||||
is_retryable_delete_replication_head_error, is_version_delete_replication, replication_etags_match,
|
||||
replication_multipart_complete_actual_size, replication_multipart_part_plan, should_retry_delete_marker_purge,
|
||||
};
|
||||
use super::replication_queue_boundary::DeletedObjectReplicationInfo;
|
||||
use super::replication_resync_boundary::{
|
||||
BucketReplicationResyncStatus, ResyncOpts, TargetReplicationResyncStatus, encode_resync_file, is_version_id_mismatch,
|
||||
@@ -60,11 +65,6 @@ use http_body::Frame;
|
||||
use http_body_util::StreamBody;
|
||||
#[cfg(test)]
|
||||
use rmp_serde;
|
||||
use rustfs_replication::{
|
||||
MustReplicateOptions, ReplicationMultipartPartInput, heal_uses_delete_replication_path,
|
||||
is_retryable_delete_replication_head_error, is_version_delete_replication, replication_etags_match,
|
||||
replication_multipart_complete_actual_size, replication_multipart_part_plan, should_retry_delete_marker_purge,
|
||||
};
|
||||
use rustfs_s3_types::EventName;
|
||||
use rustfs_utils::http::{
|
||||
AMZ_TAGGING_DIRECTIVE, SUFFIX_REPLICATION_RESET, SUFFIX_REPLICATION_STATUS, has_internal_suffix, insert_str,
|
||||
|
||||
@@ -208,6 +208,7 @@ REPLICATION_STATS_CONTRACT_BACKSLIDE_HITS_FILE="${TMP_DIR}/replication_stats_con
|
||||
REPLICATION_RUNTIME_CONTRACT_BACKSLIDE_HITS_FILE="${TMP_DIR}/replication_runtime_contract_backslide_hits.txt"
|
||||
REPLICATION_RESYNC_CONTRACT_BACKSLIDE_HITS_FILE="${TMP_DIR}/replication_resync_contract_backslide_hits.txt"
|
||||
REPLICATION_RESYNC_BOUNDARY_BYPASS_HITS_FILE="${TMP_DIR}/replication_resync_boundary_bypass_hits.txt"
|
||||
REPLICATION_OBJECT_DECISION_BOUNDARY_BYPASS_HITS_FILE="${TMP_DIR}/replication_object_decision_boundary_bypass_hits.txt"
|
||||
REPLICATION_OBJECT_COMPARE_CONTRACT_BACKSLIDE_HITS_FILE="${TMP_DIR}/replication_object_compare_contract_backslide_hits.txt"
|
||||
REPLICATION_MRF_WIRE_FORMAT_BACKSLIDE_HITS_FILE="${TMP_DIR}/replication_mrf_wire_format_backslide_hits.txt"
|
||||
STORAGE_REPLICATION_HANDLE_BOUNDARY_BYPASS_HITS_FILE="${TMP_DIR}/storage_replication_handle_boundary_bypass_hits.txt"
|
||||
@@ -2614,16 +2615,24 @@ fi
|
||||
|
||||
(
|
||||
cd "$ROOT_DIR"
|
||||
{
|
||||
rg -n --with-filename 'rustfs_replication::(DeletedObjectReplicationInfo|LARGE_WORKER_COUNT|ReplicationBackpressureRecommendation|ReplicationBackpressureState|ReplicationHealQueueAction|ReplicationHealQueueResult|ReplicationHealResyncDeletes|ReplicationOperation|ReplicationPoolOpts|ReplicationPriority|ReplicationQueueAdmission|ReplicationWorkerQueue|WORKER_MAX_LIMIT|initial_worker_counts|large_worker_backpressure_resize|mrf_worker_size_to_count|replication_backpressure_recommendation|replication_heal_queue_action|resized_worker_counts|should_queue_large_object|worker_queue_for_replication_type)\b' \
|
||||
crates/ecstore/src/bucket/replication \
|
||||
--glob '*.rs'
|
||||
rg -n -U --with-filename 'use\s+rustfs_replication::\{[^}]*\b(DeletedObjectReplicationInfo|LARGE_WORKER_COUNT|ReplicationBackpressureRecommendation|ReplicationBackpressureState|ReplicationHealQueueAction|ReplicationHealQueueResult|ReplicationHealResyncDeletes|ReplicationOperation|ReplicationPoolOpts|ReplicationPriority|ReplicationQueueAdmission|ReplicationWorkerQueue|WORKER_MAX_LIMIT|initial_worker_counts|large_worker_backpressure_resize|mrf_worker_size_to_count|replication_backpressure_recommendation|replication_heal_queue_action|resized_worker_counts|should_queue_large_object|worker_queue_for_replication_type)\b' \
|
||||
crates/ecstore/src/bucket/replication \
|
||||
--glob '*.rs'
|
||||
} |
|
||||
rg -v '^crates/ecstore/src/bucket/replication/replication_queue_boundary\.rs:' || true
|
||||
) >"$REPLICATION_QUEUE_BOUNDARY_BYPASS_HITS_FILE"
|
||||
replication_queue_boundary_status=0
|
||||
rg -n --with-filename 'rustfs_replication::(DeletedObjectReplicationInfo|LARGE_WORKER_COUNT|ReplicationBackpressureRecommendation|ReplicationBackpressureState|ReplicationHealQueueAction|ReplicationHealQueueResult|ReplicationHealResyncDeletes|ReplicationOperation|ReplicationPoolOpts|ReplicationPriority|ReplicationQueueAdmission|ReplicationWorkerQueue|WORKER_MAX_LIMIT|initial_worker_counts|large_worker_backpressure_resize|mrf_worker_size_to_count|replication_backpressure_recommendation|replication_heal_queue_action|resized_worker_counts|should_queue_large_object|worker_queue_for_replication_type)\b' \
|
||||
crates/ecstore/src/bucket/replication \
|
||||
--glob '*.rs' \
|
||||
--glob '!replication_queue_boundary.rs' >"$REPLICATION_QUEUE_BOUNDARY_BYPASS_HITS_FILE" || replication_queue_boundary_status=$?
|
||||
if [[ "$replication_queue_boundary_status" -ne 0 && "$replication_queue_boundary_status" -ne 1 ]]; then
|
||||
exit "$replication_queue_boundary_status"
|
||||
fi
|
||||
|
||||
replication_queue_boundary_grouped_status=0
|
||||
rg -n -U --with-filename 'use\s+rustfs_replication::\{[^}]*\b(DeletedObjectReplicationInfo|LARGE_WORKER_COUNT|ReplicationBackpressureRecommendation|ReplicationBackpressureState|ReplicationHealQueueAction|ReplicationHealQueueResult|ReplicationHealResyncDeletes|ReplicationOperation|ReplicationPoolOpts|ReplicationPriority|ReplicationQueueAdmission|ReplicationWorkerQueue|WORKER_MAX_LIMIT|initial_worker_counts|large_worker_backpressure_resize|mrf_worker_size_to_count|replication_backpressure_recommendation|replication_heal_queue_action|resized_worker_counts|should_queue_large_object|worker_queue_for_replication_type)\b' \
|
||||
crates/ecstore/src/bucket/replication \
|
||||
--glob '*.rs' \
|
||||
--glob '!replication_queue_boundary.rs' >>"$REPLICATION_QUEUE_BOUNDARY_BYPASS_HITS_FILE" || replication_queue_boundary_grouped_status=$?
|
||||
if [[ "$replication_queue_boundary_grouped_status" -ne 0 && "$replication_queue_boundary_grouped_status" -ne 1 ]]; then
|
||||
exit "$replication_queue_boundary_grouped_status"
|
||||
fi
|
||||
)
|
||||
|
||||
if [[ -s "$REPLICATION_QUEUE_BOUNDARY_BYPASS_HITS_FILE" ]]; then
|
||||
report_failure "replication queue contracts must stay behind replication_queue_boundary: $(paste -sd '; ' "$REPLICATION_QUEUE_BOUNDARY_BYPASS_HITS_FILE")"
|
||||
@@ -2676,21 +2685,54 @@ fi
|
||||
|
||||
(
|
||||
cd "$ROOT_DIR"
|
||||
{
|
||||
rg -n --with-filename 'rustfs_replication::(resync::(RESYNC_META_FORMAT|RESYNC_META_VERSION|WIRE_ZERO_TIME_UNIX)|mrf::(MRF_META_FORMAT|MRF_META_VERSION)|(encode_resync_file|decode_resync_file|encode_mrf_file|decode_mrf_file|BucketReplicationResyncStatus|ResyncOpts|TargetReplicationResyncStatus|resync_state_accepts_update|should_count_head_proxy_failure|should_auto_resume_resync|is_version_id_mismatch)\b)' \
|
||||
crates/ecstore/src/bucket/replication \
|
||||
--glob '*.rs'
|
||||
rg -n -U --with-filename 'use\s+rustfs_replication::\{[^}]*\b(encode_resync_file|decode_resync_file|encode_mrf_file|decode_mrf_file|BucketReplicationResyncStatus|ResyncOpts|TargetReplicationResyncStatus|resync_state_accepts_update|should_count_head_proxy_failure|should_auto_resume_resync|is_version_id_mismatch)\b' \
|
||||
crates/ecstore/src/bucket/replication \
|
||||
--glob '*.rs'
|
||||
} |
|
||||
rg -v '^crates/ecstore/src/bucket/replication/replication_resync_boundary\.rs:' || true
|
||||
) >"$REPLICATION_RESYNC_BOUNDARY_BYPASS_HITS_FILE"
|
||||
replication_resync_boundary_status=0
|
||||
rg -n --with-filename 'rustfs_replication::(resync::(RESYNC_META_FORMAT|RESYNC_META_VERSION|WIRE_ZERO_TIME_UNIX)|mrf::(MRF_META_FORMAT|MRF_META_VERSION)|(encode_resync_file|decode_resync_file|encode_mrf_file|decode_mrf_file|BucketReplicationResyncStatus|ResyncOpts|TargetReplicationResyncStatus|resync_state_accepts_update|should_count_head_proxy_failure|should_auto_resume_resync|is_version_id_mismatch)\b)' \
|
||||
crates/ecstore/src/bucket/replication \
|
||||
--glob '*.rs' \
|
||||
--glob '!replication_resync_boundary.rs' >"$REPLICATION_RESYNC_BOUNDARY_BYPASS_HITS_FILE" || replication_resync_boundary_status=$?
|
||||
if [[ "$replication_resync_boundary_status" -ne 0 && "$replication_resync_boundary_status" -ne 1 ]]; then
|
||||
exit "$replication_resync_boundary_status"
|
||||
fi
|
||||
|
||||
replication_resync_boundary_grouped_status=0
|
||||
rg -n -U --with-filename 'use\s+rustfs_replication::\{[^}]*\b(encode_resync_file|decode_resync_file|encode_mrf_file|decode_mrf_file|BucketReplicationResyncStatus|ResyncOpts|TargetReplicationResyncStatus|resync_state_accepts_update|should_count_head_proxy_failure|should_auto_resume_resync|is_version_id_mismatch)\b' \
|
||||
crates/ecstore/src/bucket/replication \
|
||||
--glob '*.rs' \
|
||||
--glob '!replication_resync_boundary.rs' >>"$REPLICATION_RESYNC_BOUNDARY_BYPASS_HITS_FILE" || replication_resync_boundary_grouped_status=$?
|
||||
if [[ "$replication_resync_boundary_grouped_status" -ne 0 && "$replication_resync_boundary_grouped_status" -ne 1 ]]; then
|
||||
exit "$replication_resync_boundary_grouped_status"
|
||||
fi
|
||||
)
|
||||
|
||||
if [[ -s "$REPLICATION_RESYNC_BOUNDARY_BYPASS_HITS_FILE" ]]; then
|
||||
report_failure "replication resync contracts must stay behind replication_resync_boundary: $(paste -sd '; ' "$REPLICATION_RESYNC_BOUNDARY_BYPASS_HITS_FILE")"
|
||||
fi
|
||||
|
||||
(
|
||||
cd "$ROOT_DIR"
|
||||
replication_object_decision_boundary_status=0
|
||||
rg -n --with-filename 'rustfs_replication::(MustReplicateOptions|ReplicationDeleteSource|ReplicationMultipartPartInput|ReplicationResyncTargetObject|delete_replication_missing_source_decision|delete_replication_object_opts|heal_uses_delete_replication_path|is_retryable_delete_replication_head_error|is_version_delete_replication|replication_etags_match|replication_multipart_complete_actual_size|replication_multipart_part_plan|resync_target_for_object|should_retry_delete_marker_purge)\b' \
|
||||
crates/ecstore/src/bucket/replication \
|
||||
--glob '*.rs' \
|
||||
--glob '!replication_object_decision_boundary.rs' >"$REPLICATION_OBJECT_DECISION_BOUNDARY_BYPASS_HITS_FILE" || replication_object_decision_boundary_status=$?
|
||||
if [[ "$replication_object_decision_boundary_status" -ne 0 && "$replication_object_decision_boundary_status" -ne 1 ]]; then
|
||||
exit "$replication_object_decision_boundary_status"
|
||||
fi
|
||||
|
||||
replication_object_decision_boundary_grouped_status=0
|
||||
rg -n -U --with-filename 'use\s+rustfs_replication::\{[^}]*\b(MustReplicateOptions|ReplicationDeleteSource|ReplicationMultipartPartInput|ReplicationResyncTargetObject|delete_replication_missing_source_decision|delete_replication_object_opts|heal_uses_delete_replication_path|is_retryable_delete_replication_head_error|is_version_delete_replication|replication_etags_match|replication_multipart_complete_actual_size|replication_multipart_part_plan|resync_target_for_object|should_retry_delete_marker_purge)\b' \
|
||||
crates/ecstore/src/bucket/replication \
|
||||
--glob '*.rs' \
|
||||
--glob '!replication_object_decision_boundary.rs' >>"$REPLICATION_OBJECT_DECISION_BOUNDARY_BYPASS_HITS_FILE" || replication_object_decision_boundary_grouped_status=$?
|
||||
if [[ "$replication_object_decision_boundary_grouped_status" -ne 0 && "$replication_object_decision_boundary_grouped_status" -ne 1 ]]; then
|
||||
exit "$replication_object_decision_boundary_grouped_status"
|
||||
fi
|
||||
)
|
||||
|
||||
if [[ -s "$REPLICATION_OBJECT_DECISION_BOUNDARY_BYPASS_HITS_FILE" ]]; then
|
||||
report_failure "replication object decision contracts must stay behind replication_object_decision_boundary: $(paste -sd '; ' "$REPLICATION_OBJECT_DECISION_BOUNDARY_BYPASS_HITS_FILE")"
|
||||
fi
|
||||
|
||||
(
|
||||
cd "$ROOT_DIR"
|
||||
replication_object_compare_status=0
|
||||
|
||||
Reference in New Issue
Block a user