feat(pool): add bulk key configuration management

This commit is contained in:
MMEXA
2026-07-14 04:57:05 +08:00
parent 7f61bb43c7
commit a25fab371a
37 changed files with 2510 additions and 379 deletions
@@ -0,0 +1,60 @@
use super::{
admin_pool_provider_id_from_path, build_admin_pool_error_response,
ADMIN_POOL_PROVIDER_CATALOG_READER_UNAVAILABLE_DETAIL,
ADMIN_POOL_PROVIDER_CATALOG_WRITER_UNAVAILABLE_DETAIL,
};
use crate::handlers::admin::provider::shared::payloads::AdminProviderKeyBatchUpdateRequest;
use crate::handlers::admin::request::{AdminAppState, AdminRequestContext};
use crate::GatewayError;
use axum::{
body::{Body, Bytes},
http,
response::Response,
};
pub(super) async fn build_admin_pool_batch_update_response(
state: &AdminAppState<'_>,
request_context: &AdminRequestContext<'_>,
request_body: Option<&Bytes>,
) -> Result<Response<Body>, GatewayError> {
if !state.has_provider_catalog_data_reader() {
return Ok(build_admin_pool_error_response(
http::StatusCode::SERVICE_UNAVAILABLE,
ADMIN_POOL_PROVIDER_CATALOG_READER_UNAVAILABLE_DETAIL,
));
}
if !state.has_provider_catalog_data_writer() {
return Ok(build_admin_pool_error_response(
http::StatusCode::SERVICE_UNAVAILABLE,
ADMIN_POOL_PROVIDER_CATALOG_WRITER_UNAVAILABLE_DETAIL,
));
}
let Some(provider_id) = admin_pool_provider_id_from_path(request_context.path()) else {
return Ok(build_admin_pool_error_response(
http::StatusCode::NOT_FOUND,
"Provider 不存在",
));
};
let payload = match request_body.filter(|body| !body.is_empty()) {
Some(body) => match serde_json::from_slice::<AdminProviderKeyBatchUpdateRequest>(body) {
Ok(value) => value,
Err(_) => {
return Ok(build_admin_pool_error_response(
http::StatusCode::BAD_REQUEST,
"请求体必须包含 key_ids 与 patch",
));
}
},
None => {
return Ok(build_admin_pool_error_response(
http::StatusCode::BAD_REQUEST,
"请求体必须包含 key_ids 与 patch",
));
}
};
state
.build_admin_pool_batch_update_response(&provider_id, payload)
.await
}
@@ -15,6 +15,8 @@ mod batch_import;
mod batch_shared;
#[path = "batch_routes/task_status.rs"]
mod batch_task_status;
#[path = "batch_routes/update.rs"]
mod batch_update;
pub(crate) mod payloads;
#[path = "read_routes/keys.rs"]
mod read_keys;
@@ -152,6 +154,16 @@ pub(crate) async fn maybe_build_local_admin_pool_response(
.await?,
));
}
Some("batch_update_keys") => {
return Ok(Some(
batch_update::build_admin_pool_batch_update_response(
state,
request_context,
request_body,
)
.await?,
));
}
Some("batch_delete_task_status") => {
return Ok(Some(
batch_task_status::build_admin_pool_batch_delete_task_status_response(
@@ -213,6 +213,10 @@ pub(crate) fn is_admin_pool_route(request_context: &AdminRequestContext<'_>) ->
&& path.starts_with("/api/admin/pool/")
&& path.ends_with("/keys/batch-action")
&& path.matches('/').count() == 6)
|| (request_context.method() == http::Method::PATCH
&& path.starts_with("/api/admin/pool/")
&& path.ends_with("/keys/batch-update")
&& path.matches('/').count() == 6)
|| (request_context.method() == http::Method::POST
&& path.starts_with("/api/admin/pool/")
&& path.ends_with("/keys/resolve-selection")