Skip to content

Commit 296e072

Browse files
authored
refactor(meta): extract utilities from monolithic util.rs (#18678)
Transform the large util.rs file (561 lines) into 8 focused utility modules to improve code organization, maintainability, and developer experience. PROBLEM: - Monolithic util.rs with 561 lines and 16 scattered functions - Inconsistent import patterns across 39 API files - 165+ occurrences of duplicated transaction utilities - Poor discoverability and maintainability SOLUTION: Applied incremental refactoring with backward compatibility: EXTRACTED MODULES: - txn_condition_util.rs - Transaction condition builders (txn_cond_eq_seq, txn_cond_seq) - txn_retry_util.rs - Transaction retry patterns (txn_backoff re-export) - serialization_util.rs - Data serialization (serialize_struct, deserialize_struct, etc.) - error_util.rs - Error construction (6 functions from util.rs, database_util.rs, schema_api.rs) - kv_fetch_util.rs - KV operations (get_u64_value, fetch_id, 4 others) - txn_op_builder_util.rs - Transaction builders (txn_put_pb, txn_op_del, 3 others) - txn_core_util.rs - Core transactions (send_txn, txn_delete_exact, txn_replace_exact) - data_retention_util.rs - Retention logic (is_drop_time_retainable, get_retention_boundary)
1 parent f64aedd commit 296e072

27 files changed

+681
-518
lines changed

src/meta/api/src/data_mask_api_impl.rs

Lines changed: 5 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -36,12 +36,12 @@ use crate::data_mask_api::DatamaskApi;
3636
use crate::fetch_id;
3737
use crate::kv_app_error::KVAppError;
3838
use crate::kv_pb_api::KVPbApi;
39-
use crate::send_txn;
4039
use crate::txn_backoff::txn_backoff;
41-
use crate::txn_cond_eq_seq;
42-
use crate::util::txn_delete_exact;
43-
use crate::util::txn_op_put_pb;
44-
use crate::util::txn_replace_exact;
40+
use crate::txn_condition_util::txn_cond_eq_seq;
41+
use crate::txn_core_util::send_txn;
42+
use crate::txn_core_util::txn_delete_exact;
43+
use crate::txn_core_util::txn_replace_exact;
44+
use crate::txn_op_builder_util::txn_op_put_pb;
4545

4646
/// DatamaskApi is implemented upon kvapi::KVApi.
4747
/// Thus every type that impl kvapi::KVApi impls DatamaskApi.
Lines changed: 43 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,43 @@
1+
// Copyright 2021 Datafuse Labs
2+
//
3+
// Licensed under the Apache License, Version 2.0 (the "License");
4+
// you may not use this file except in compliance with the License.
5+
// You may obtain a copy of the License at
6+
//
7+
// http://www.apache.org/licenses/LICENSE-2.0
8+
//
9+
// Unless required by applicable law or agreed to in writing, software
10+
// distributed under the License is distributed on an "AS IS" BASIS,
11+
// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
12+
// See the License for the specific language governing permissions and
13+
// limitations under the License.
14+
15+
//! Data retention utilities extracted from util.rs
16+
17+
use std::time::Duration;
18+
19+
use chrono::DateTime;
20+
use chrono::Utc;
21+
22+
const DEFAULT_DATA_RETENTION_SECONDS: i64 = 24 * 60 * 60;
23+
24+
/// Determines if an item is within the retention period based on its drop time.
25+
///
26+
/// # Arguments
27+
/// * `drop_on` - The optional timestamp when the item was marked for deletion.
28+
/// * `now` - The current timestamp used as a reference point.
29+
///
30+
/// Items without a drop time (`None`) are always considered retainable.
31+
/// The retention period is defined by `DEFAULT_DATA_RETENTION_SECONDS`.
32+
pub fn is_drop_time_retainable(drop_on: Option<DateTime<Utc>>, now: DateTime<Utc>) -> bool {
33+
let retention_boundary = get_retention_boundary(now);
34+
35+
// If it is None, fill it with a very big time.
36+
let drop_on = drop_on.unwrap_or(DateTime::<Utc>::MAX_UTC);
37+
drop_on > retention_boundary
38+
}
39+
40+
/// Get the retention boundary time before which the data can be permanently removed.
41+
pub fn get_retention_boundary(now: DateTime<Utc>) -> DateTime<Utc> {
42+
now - Duration::from_secs(DEFAULT_DATA_RETENTION_SECONDS as u64)
43+
}

src/meta/api/src/database_api.rs

Lines changed: 4 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -55,21 +55,21 @@ use log::error;
5555
use log::warn;
5656
use seq_marked::SeqValue;
5757

58-
use crate::database_util::db_has_to_not_exist;
58+
use crate::data_retention_util::is_drop_time_retainable;
5959
use crate::database_util::drop_database_meta;
6060
use crate::database_util::get_db_or_err;
6161
use crate::db_has_to_exist;
62+
use crate::error_util::db_has_to_not_exist;
6263
use crate::fetch_id;
6364
use crate::kv_app_error::KVAppError;
6465
use crate::kv_pb_api::KVPbApi;
65-
use crate::send_txn;
6666
use crate::serialize_struct;
6767
use crate::serialize_u64;
6868
use crate::txn_backoff::txn_backoff;
69-
use crate::txn_cond_seq;
69+
use crate::txn_condition_util::txn_cond_seq;
70+
use crate::txn_core_util::send_txn;
7071
use crate::txn_op_del;
7172
use crate::txn_op_put;
72-
use crate::util::is_drop_time_retainable;
7373

7474
impl<KV> DatabaseApi for KV
7575
where

src/meta/api/src/database_util.rs

Lines changed: 2 additions & 25 deletions
Original file line numberDiff line numberDiff line change
@@ -16,7 +16,6 @@ use std::fmt::Display;
1616

1717
use chrono::Utc;
1818
use databend_common_meta_app::app_error::AppError;
19-
use databend_common_meta_app::app_error::DatabaseAlreadyExists;
2019
use databend_common_meta_app::app_error::DropDbWithDropTime;
2120
use databend_common_meta_app::schema::database_name_ident::DatabaseNameIdent;
2221
use databend_common_meta_app::schema::DatabaseId;
@@ -32,35 +31,13 @@ use databend_common_meta_types::TxnRequest;
3231
use log::debug;
3332
use log::warn;
3433

34+
use crate::error_util::unknown_database_error;
3535
use crate::kv_app_error::KVAppError;
3636
use crate::kv_pb_api::KVPbApi;
3737
use crate::serialize_struct;
38-
use crate::txn_cond_seq;
38+
use crate::txn_condition_util::txn_cond_seq;
3939
use crate::txn_op_del;
4040
use crate::txn_op_put;
41-
use crate::util::unknown_database_error;
42-
43-
/// Return OK if a db_id or db_meta does not exist by checking the seq.
44-
///
45-
/// Otherwise returns DatabaseAlreadyExists error
46-
pub(crate) fn db_has_to_not_exist(
47-
seq: u64,
48-
name_ident: &DatabaseNameIdent,
49-
ctx: impl Display,
50-
) -> Result<(), KVAppError> {
51-
if seq == 0 {
52-
Ok(())
53-
} else {
54-
debug!(seq = seq, name_ident :? =(name_ident); "exist");
55-
56-
Err(KVAppError::AppError(AppError::DatabaseAlreadyExists(
57-
DatabaseAlreadyExists::new(
58-
name_ident.database_name(),
59-
format!("{}: {}", ctx, name_ident.display()),
60-
),
61-
)))
62-
}
63-
}
6441

6542
pub(crate) async fn drop_database_meta(
6643
kv_api: &(impl kvapi::KVApi<Error = MetaError> + ?Sized),

src/meta/api/src/dictionary_api.rs

Lines changed: 3 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -38,11 +38,11 @@ use crate::kv_app_error::KVAppError;
3838
use crate::kv_pb_api::KVPbApi;
3939
use crate::meta_txn_error::MetaTxnError;
4040
use crate::name_id_value_api::NameIdValueApi;
41-
use crate::send_txn;
4241
use crate::txn_backoff::txn_backoff;
43-
use crate::txn_cond_seq;
42+
use crate::txn_condition_util::txn_cond_seq;
43+
use crate::txn_core_util::send_txn;
44+
use crate::txn_op_builder_util::txn_op_put_pb;
4445
use crate::txn_op_del;
45-
use crate::util::txn_op_put_pb;
4646

4747
/// DictionaryApi defines APIs for dictionary management.
4848
///

src/meta/api/src/error_util.rs

Lines changed: 108 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,108 @@
1+
// Copyright 2021 Datafuse Labs
2+
//
3+
// Licensed under the Apache License, Version 2.0 (the "License");
4+
// you may not use this file except in compliance with the License.
5+
// You may obtain a copy of the License at
6+
//
7+
// http://www.apache.org/licenses/LICENSE-2.0
8+
//
9+
// Unless required by applicable law or agreed to in writing, software
10+
// distributed under the License is distributed on an "AS IS" BASIS,
11+
// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
12+
// See the License for the specific language governing permissions and
13+
// limitations under the License.
14+
15+
//! Error construction utilities extracted from util.rs and other modules
16+
17+
use std::fmt::Display;
18+
19+
use databend_common_meta_app::app_error::AppError;
20+
use databend_common_meta_app::app_error::DatabaseAlreadyExists;
21+
use databend_common_meta_app::app_error::TableAlreadyExists;
22+
use databend_common_meta_app::app_error::UnknownDatabase;
23+
use databend_common_meta_app::app_error::UnknownDatabaseId;
24+
use databend_common_meta_app::app_error::UnknownTable;
25+
use databend_common_meta_app::schema::database_name_ident::DatabaseNameIdent;
26+
use databend_common_meta_app::schema::TableNameIdent;
27+
28+
use crate::kv_app_error::KVAppError;
29+
30+
pub fn unknown_database_error(db_name_ident: &DatabaseNameIdent, msg: impl Display) -> AppError {
31+
let e = UnknownDatabase::new(
32+
db_name_ident.database_name(),
33+
format!("{}: {}", msg, db_name_ident.display()),
34+
);
35+
AppError::UnknownDatabase(e)
36+
}
37+
38+
pub fn db_has_to_exist(
39+
seq: u64,
40+
db_name_ident: &DatabaseNameIdent,
41+
msg: impl Display,
42+
) -> Result<(), KVAppError> {
43+
if seq == 0 {
44+
Err(KVAppError::AppError(unknown_database_error(
45+
db_name_ident,
46+
msg,
47+
)))
48+
} else {
49+
Ok(())
50+
}
51+
}
52+
53+
pub fn db_id_has_to_exist(seq: u64, db_id: u64, msg: impl Display) -> Result<(), KVAppError> {
54+
if seq == 0 {
55+
let app_err = AppError::UnknownDatabaseId(UnknownDatabaseId::new(
56+
db_id,
57+
format!("{}: {}", msg, db_id),
58+
));
59+
Err(KVAppError::AppError(app_err))
60+
} else {
61+
Ok(())
62+
}
63+
}
64+
65+
pub fn assert_table_exist(
66+
seq: u64,
67+
name_ident: &TableNameIdent,
68+
ctx: impl Display,
69+
) -> Result<(), AppError> {
70+
if seq > 0 {
71+
return Ok(());
72+
}
73+
Err(AppError::UnknownTable(UnknownTable::new(
74+
&name_ident.table_name,
75+
format!("{}: {}", ctx, name_ident),
76+
)))
77+
}
78+
79+
pub fn db_has_to_not_exist(
80+
seq: u64,
81+
name_ident: &DatabaseNameIdent,
82+
ctx: impl Display,
83+
) -> Result<(), KVAppError> {
84+
if seq == 0 {
85+
Ok(())
86+
} else {
87+
Err(KVAppError::AppError(AppError::DatabaseAlreadyExists(
88+
DatabaseAlreadyExists::new(
89+
name_ident.database_name(),
90+
format!("{}: {}", ctx, name_ident.display()),
91+
),
92+
)))
93+
}
94+
}
95+
96+
pub fn table_has_to_not_exist(
97+
seq: u64,
98+
name_ident: &TableNameIdent,
99+
ctx: impl Display,
100+
) -> Result<(), KVAppError> {
101+
if seq == 0 {
102+
Ok(())
103+
} else {
104+
Err(KVAppError::AppError(AppError::TableAlreadyExists(
105+
TableAlreadyExists::new(&name_ident.table_name, format!("{}: {}", ctx, name_ident)),
106+
)))
107+
}
108+
}

src/meta/api/src/garbage_collection_api.rs

Lines changed: 6 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -54,15 +54,15 @@ use log::info;
5454
use crate::index_api::IndexApi;
5555
use crate::kv_app_error::KVAppError;
5656
use crate::kv_pb_api::KVPbApi;
57-
use crate::send_txn;
5857
use crate::txn_backoff::txn_backoff;
59-
use crate::txn_cond_eq_seq;
58+
use crate::txn_condition_util::txn_cond_eq_seq;
59+
use crate::txn_core_util::send_txn;
60+
use crate::txn_core_util::txn_delete_exact;
61+
use crate::txn_core_util::txn_replace_exact;
62+
use crate::txn_op_builder_util::txn_op_put_pb;
63+
use crate::txn_op_builder_util::txn_put_pb;
6064
use crate::txn_op_del;
6165
use crate::txn_op_get;
62-
use crate::util::txn_delete_exact;
63-
use crate::util::txn_op_put_pb;
64-
use crate::util::txn_put_pb;
65-
use crate::util::txn_replace_exact;
6666

6767
/// GarbageCollectionApi defines APIs for garbage collection operations.
6868
///

src/meta/api/src/index_api.rs

Lines changed: 5 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -62,15 +62,15 @@ use crate::meta_txn_error::MetaTxnError;
6262
use crate::name_id_value_api::NameIdValueApi;
6363
use crate::schema_api::mark_index_as_deleted;
6464
use crate::schema_api::mark_table_index_as_deleted;
65-
use crate::send_txn;
6665
use crate::serialize_struct;
6766
use crate::txn_backoff::txn_backoff;
68-
use crate::txn_cond_eq_seq;
69-
use crate::txn_cond_seq;
67+
use crate::txn_condition_util::txn_cond_eq_seq;
68+
use crate::txn_condition_util::txn_cond_seq;
69+
use crate::txn_core_util::send_txn;
70+
use crate::txn_core_util::txn_delete_exact;
71+
use crate::txn_op_builder_util::txn_op_put_pb;
7072
use crate::txn_op_del;
7173
use crate::txn_op_put;
72-
use crate::util::txn_delete_exact;
73-
use crate::util::txn_op_put_pb;
7474

7575
/// IndexApi defines APIs for index management and metadata.
7676
///

0 commit comments

Comments
 (0)