pub mod api;
pub mod cluster_api;
pub mod config_api;
pub mod connection_api;
pub mod login_api;
pub mod model;
pub mod naming_api;
pub mod user_api;
pub mod middle;
pub mod transfer_api;
pub mod v2;
use std::sync::Arc;
use self::model::NamespaceInfo;
use crate::namespace::model::{
NamespaceFromFlags, NamespaceQueryReq, NamespaceQueryResult, NamespaceRaftReq,
};
use crate::{
common::appdata::AppShareData,
config::core::{ConfigActor, ConfigCmd, ConfigKey, ConfigResult},
raft::cluster::model::SetConfigReq,
};
use actix::prelude::*;
pub struct NamespaceUtilsOld;
pub const DEFAULT_NAMESPACE: &str = "public";
pub const SYSCONFIG_NAMESPACE: &str = "__INNER_SYSTEM__";
pub const SYSCONFIG_GROUP: &str = "sys";
pub const SYSCONFIG_NAMESPACE_KEY: &str = "namespaces";
lazy_static::lazy_static! {
static ref DEFAULT_NAMESPACE_INFO:Arc<NamespaceInfo> = Arc::new(NamespaceInfo {
namespace_id: Some(Arc::new("".to_owned())),
namespace_name: Some(DEFAULT_NAMESPACE.to_owned()),
r#type: Some("0".to_owned()),
});
}
impl NamespaceUtilsOld {
pub async fn get_namespace_source(config_addr: &Addr<ConfigActor>) -> Arc<String> {
let cmd = ConfigCmd::GET(ConfigKey::new(
SYSCONFIG_NAMESPACE_KEY,
SYSCONFIG_GROUP,
SYSCONFIG_NAMESPACE,
));
match config_addr.send(cmd).await {
Ok(res) => {
let r: ConfigResult = res.unwrap();
match r {
ConfigResult::Data { value: v, .. } => v,
_ => Arc::new("".to_string()),
}
}
Err(_) => Arc::new("".to_string()),
}
}
pub fn get_namespaces_from_source(namespace_str: Arc<String>) -> Vec<Arc<NamespaceInfo>> {
if namespace_str.is_empty() {
return vec![DEFAULT_NAMESPACE_INFO.clone()];
}
if let Ok(mut namespaces) = serde_json::from_str::<Vec<Arc<NamespaceInfo>>>(&namespace_str)
{
let mut list = Vec::with_capacity(namespaces.len() + 1);
list.push(DEFAULT_NAMESPACE_INFO.clone());
list.append(&mut namespaces);
list
} else {
vec![DEFAULT_NAMESPACE_INFO.clone()]
}
}
pub async fn get_namespaces(config_addr: &Addr<ConfigActor>) -> Vec<Arc<NamespaceInfo>> {
let namespace_str = Self::get_namespace_source(config_addr).await;
Self::get_namespaces_from_source(namespace_str)
}
pub async fn load_namespace_from_config(config_addr: &Addr<ConfigActor>) -> Vec<NamespaceInfo> {
let namespace_str = Self::get_namespace_source(config_addr).await;
if namespace_str.is_empty() {
return vec![];
}
serde_json::from_str::<Vec<NamespaceInfo>>(&namespace_str).unwrap_or_default()
}
pub async fn save_namespace(
app_data: &Arc<AppShareData>,
value: &Vec<NamespaceInfo>,
) -> anyhow::Result<()> {
let value_str = serde_json::to_string(value)?;
let req = SetConfigReq::new(
ConfigKey::new(
SYSCONFIG_NAMESPACE_KEY,
SYSCONFIG_GROUP,
SYSCONFIG_NAMESPACE,
),
Arc::new(value_str),
);
match app_data.config_route.set_config(req).await {
Ok(_) => Ok(()),
Err(err) => Err(anyhow::anyhow!(err)),
}
}
pub async fn add_namespace(
app_data: &Arc<AppShareData>,
info: NamespaceInfo,
) -> anyhow::Result<()> {
if let (Some(namespace_id), Some(namespace_name)) = (info.namespace_id, info.namespace_name)
{
if namespace_id.is_empty() || namespace_id.as_ref().eq(DEFAULT_NAMESPACE) {
return Err(anyhow::anyhow!("namespace is exist"));
}
let mut infos = Self::load_namespace_from_config(&app_data.config_addr).await;
for item in &infos {
if namespace_id.eq(item.namespace_id.as_ref().unwrap()) {
return Err(anyhow::anyhow!("namespace is exist"));
}
}
let new_info = NamespaceInfo {
namespace_id: Some(namespace_id),
namespace_name: Some(namespace_name),
r#type: Some("2".to_owned()),
};
infos.push(new_info);
Self::save_namespace(app_data, &infos).await
} else {
Err(anyhow::anyhow!("params is empty"))
}
}
pub async fn update_namespace(
app_data: &Arc<AppShareData>,
info: NamespaceInfo,
) -> anyhow::Result<()> {
if let (Some(namespace_id), Some(namespace_name)) = (info.namespace_id, info.namespace_name)
{
if namespace_id.is_empty() || namespace_id.as_ref().eq(DEFAULT_NAMESPACE) {
return Err(anyhow::anyhow!("namespace can't update"));
}
let infos = Self::load_namespace_from_config(&app_data.config_addr).await;
let mut new_infos = Vec::with_capacity(infos.len());
let mut update_mark = false;
for mut item in infos {
if namespace_id.eq(item.namespace_id.as_ref().unwrap()) {
item.namespace_name = Some(namespace_name.clone());
update_mark = true;
}
new_infos.push(item);
}
if !update_mark {
return Err(anyhow::anyhow!("namespace is not exist"));
}
Self::save_namespace(app_data, &new_infos).await
} else {
Err(anyhow::anyhow!("params is empty"))
}
}
pub async fn remove_namespace(
app_data: &Arc<AppShareData>,
namespace_id: Option<String>,
) -> anyhow::Result<()> {
if let Some(namespace_id) = namespace_id {
if namespace_id.is_empty() || namespace_id.eq(DEFAULT_NAMESPACE) {
return Err(anyhow::anyhow!("namespace can't delete"));
}
let infos = Self::load_namespace_from_config(&app_data.config_addr).await;
let infos_len = infos.len();
let mut new_infos = Vec::with_capacity(infos.len());
for item in infos {
if namespace_id.eq(item.namespace_id.as_ref().unwrap() as &str) {
continue;
}
new_infos.push(item);
}
if new_infos.len() == infos_len {
return Err(anyhow::anyhow!("namespace is not exist"));
}
Self::save_namespace(app_data, &new_infos).await
} else {
Err(anyhow::anyhow!("params is empty"))
}
}
}
pub struct NamespaceUtils;
impl NamespaceUtils {
pub async fn get_namespaces(
app_share_data: &Arc<AppShareData>,
) -> anyhow::Result<Vec<NamespaceInfo>> {
let res = app_share_data
.namespace_addr
.send(NamespaceQueryReq::List)
.await??;
if let NamespaceQueryResult::List(list) = res {
Ok(list
.into_iter()
.map(|e| e.as_ref().to_owned().into())
.collect())
} else {
Err(anyhow::anyhow!("NamespaceQueryResult is error"))
}
}
pub async fn get_namespace(
app_share_data: &Arc<AppShareData>,
namespace_id: Option<Arc<String>>,
) -> anyhow::Result<NamespaceInfo> {
let namespace_id = namespace_id.unwrap_or_default();
let res = app_share_data
.namespace_addr
.send(NamespaceQueryReq::Info(namespace_id.clone()))
.await??;
if let NamespaceQueryResult::Info(info) = res {
Ok(info.as_ref().to_owned().into())
} else {
Err(anyhow::anyhow!("NamespaceQueryResult is error"))
}
}
pub async fn add_namespace(
app_data: &Arc<AppShareData>,
info: NamespaceInfo,
) -> anyhow::Result<()> {
app_data
.raft_request_route
.request_namespace(NamespaceRaftReq::Set(info.into()))
.await?;
Ok(())
}
pub async fn update_namespace(
app_data: &Arc<AppShareData>,
info: NamespaceInfo,
) -> anyhow::Result<()> {
app_data
.raft_request_route
.request_namespace(NamespaceRaftReq::Update(info.into()))
.await?;
Ok(())
}
pub async fn remove_namespace(
app_data: &Arc<AppShareData>,
namespace_id: Option<Arc<String>>,
) -> anyhow::Result<()> {
let namespace_id = namespace_id.unwrap_or_default();
let res = app_data
.namespace_addr
.send(NamespaceQueryReq::Info(namespace_id.clone()))
.await??;
if let NamespaceQueryResult::Info(v) = res {
if v.flag != NamespaceFromFlags::USER.bits() {
return Err(anyhow::anyhow!("The namespace can't be deleted,because config or service data exists in the namespace"));
}
}
app_data
.raft_request_route
.request_namespace(NamespaceRaftReq::Delete { id: namespace_id })
.await?;
Ok(())
}
}