Skip to content

Commit

Permalink
Optimize some code.
Browse files Browse the repository at this point in the history
  • Loading branch information
gudaoxuri committed Apr 9, 2024
1 parent 8330638 commit 123a721
Show file tree
Hide file tree
Showing 8 changed files with 86 additions and 10 deletions.
13 changes: 11 additions & 2 deletions backend/basic/src/dto.rs
Original file line number Diff line number Diff line change
@@ -1,3 +1,4 @@
//! Basic DTOs
use std::collections::HashMap;

use serde::{Deserialize, Serialize};
Expand All @@ -7,17 +8,25 @@ use crate::enumeration::BasicQueryOpKind;
#[cfg(feature = "default")]
use tardis::web::poem_openapi;

/// Basic query condition object
/// 基础的查询条件对象
#[derive(Serialize, Deserialize, Debug, Clone)]
#[cfg_attr(feature = "default", derive(poem_openapi::Object))]
pub struct BasicQueryCondInfo {
/// Query field
#[oai(validator(min_length = "1"))]
pub field: String,
/// Query operator
pub op: BasicQueryOpKind,
/// Query value
pub value: Value,
}

impl BasicQueryCondInfo {
// The outer level is the `OR` relationship, the inner level is the `AND` relationship
/// Check if the ``check_vars`` passed in meet the conditions in ``conds``
/// 检查传入的 ``check_vars`` 是否满足 ``conds`` 中的条件
///
/// The outer level is the `OR` relationship, the inner level is the `AND` relationship
pub fn check_or_and_conds(conds: &Vec<Vec<BasicQueryCondInfo>>, check_vars: &HashMap<String, Value>) -> TardisResult<bool> {
let is_match = conds.iter().any(|and_conds| {
and_conds.iter().all(|cond| match check_vars.get(&cond.field) {
Expand Down Expand Up @@ -93,7 +102,7 @@ mod tests {

use tardis::{basic::result::TardisResult, serde_json::json};

use crate::{enumeration::BasicQueryOpKind, dto::BasicQueryCondInfo};
use crate::{dto::BasicQueryCondInfo, enumeration::BasicQueryOpKind};

#[test]
fn test_check_or_and_conds() -> TardisResult<()> {
Expand Down
17 changes: 17 additions & 0 deletions backend/basic/src/enumeration.rs
Original file line number Diff line number Diff line change
@@ -1,25 +1,42 @@
//! Basic enumerations
use serde::{Deserialize, Serialize};
use tardis::derive_more::Display;
#[cfg(feature = "default")]
use tardis::web::poem_openapi;

/// API classification
/// API分类
#[derive(Display, Debug)]
#[cfg_attr(feature = "default", derive(poem_openapi::Tags))]
pub enum ApiTag {
/// Common Console, mostly starting with ``cc``, generally do not require authentication.
/// 公共类型, 多使用 ``cc`` 开头,一般不需要认证
#[oai(rename = "Common Console")]
Common,
/// Tenant Console, mostly starting with ``ct``
/// 租户类型, 多使用 ``ct`` 开头
#[oai(rename = "Tenant Console")]
Tenant,
/// App Console, mostly starting with ``ca``
/// 应用类型, 多使用 ``ca`` 开头
#[oai(rename = "App Console")]
App,
/// System Console, mostly starting with ``cs``
/// 系统类型, 多使用 ``cs`` 开头
#[oai(rename = "System Console")]
System,
/// Passport Console, mostly starting with ``cp``
/// 通行证类型, 多使用 ``cp`` 开头
#[oai(rename = "Passport Console")]
Passport,
/// Interface Console, mostly starting with ``ci``, used for system-to-system calls, this type of interface generally uses ak/sk authentication
/// 接口类型, 多使用 ``ci`` 开头, 用于系统间调用, 此类型接口一般使用ak/sk认证
#[oai(rename = "Interface Console")]
Interface,
}

/// Basic query operator
/// 基础查询操作符
#[derive(Display, Clone, Debug, PartialEq, Eq, Deserialize, Serialize)]
#[cfg_attr(feature = "default", derive(poem_openapi::Enum))]
pub enum BasicQueryOpKind {
Expand Down
27 changes: 26 additions & 1 deletion backend/basic/src/lib.rs
Original file line number Diff line number Diff line change
@@ -1,7 +1,23 @@
//! Basic library for BIOS
//! BIOS的基础库
//!
//! This library provides the following functions:
//! 1. RBUM (Resource-Based Unified Model) model and implementation of common operations.
//! 1. SPI (Service Provider Interface) model and implementation of common operations.
//! 1. Common enumeration types.
//! 1. Common utility functions.
//! 1. Basic test support.
//!
//! 此类库提供了下功能:
//! 1. RBUM(基于资源的统一模型)模型及公共操作的实现
//! 1. SPI(服务提供接口)模型及公共操作的实现
//! 1. 通用枚举类型
//! 1. 通用工具函数
//! 1. 基础的测试支持
extern crate lazy_static;

pub mod enumeration;
pub mod dto;
pub mod enumeration;
pub mod helper;
pub mod process;
pub mod rbum;
Expand All @@ -12,10 +28,19 @@ pub mod test;
pub use enumeration::ApiTag;
use tardis::{TardisFuns, TardisFunsInst};

/// Extractor for ``TardisFunInst``
/// 提取 ``TardisFunsInst``
pub trait TardisFunInstExtractor {
fn tardis_fun_inst(&self) -> TardisFunsInst;
}

/// Extract ``TardisFunInst`` from request path
/// 从请求路径中自动提取 ``TardisFunInst``
///
/// Get the first path segment from the request path as the service domain.
/// If there is a configuration parameter ``csm.X`` with the same name as the service domain, use this configuration parameter,
/// otherwise use the default configuration parameter.
/// 从请求路径中找到第一个路径段作为服务域名,如果存在与该服务域名同名的配置参数 ``csm.X``, 则使用该配置参数,否则使用默认配置参数.
#[cfg(feature = "default")]
impl TardisFunInstExtractor for tardis::web::poem::Request {
fn tardis_fun_inst(&self) -> TardisFunsInst {
Expand Down
9 changes: 8 additions & 1 deletion backend/basic/src/process/ci_processor.rs
Original file line number Diff line number Diff line change
@@ -1,8 +1,13 @@
//! CI (Interface Console) Processor
//!
//! The CI type interface is mostly used for calls between systems, and the interface is authenticated by Ak/Sk to ensure the security of the interface.
//! CI类型的接口多用于系统之间的调用,通过Ak/Sk进行签名认证,保证接口的安全性。
use serde::{Deserialize, Serialize};
use tardis::{basic::result::TardisResult, chrono::Utc, TardisFuns};

use crate::helper::request_helper::sort_query;

/// Application key configuration
#[derive(Debug, Serialize, Deserialize, Clone)]
#[serde(default)]
pub struct AppKeyConfig {
Expand All @@ -21,7 +26,9 @@ impl Default for AppKeyConfig {
}
}

// signature ak
/// Generate signature
///
/// Generate a signature for the request and return the request header with the signature
pub fn signature(app_key_config: &AppKeyConfig, method: &str, path: &str, query: &str, mut header: Vec<(String, String)>) -> TardisResult<Vec<(String, String)>> {
let sorted_req_query = sort_query(query);
let date = Utc::now().format("%a, %d %b %Y %T GMT").to_string();
Expand Down
22 changes: 19 additions & 3 deletions backend/basic/src/process/task_processor.rs
Original file line number Diff line number Diff line change
@@ -1,5 +1,4 @@
//! # 异步任务处理器
//! Async task processor
use std::{collections::HashMap, future::Future, sync::Arc};

use lazy_static::lazy_static;
Expand All @@ -21,16 +20,20 @@ lazy_static! {
const TASK_PROCESSOR_DATA_EX_SEC: u64 = 60 * 60 * 24;
const TASK_IN_CTX_FLAG: &str = "task_id";

/// Set task status event flag
/// 设置任务状态事件标识
pub const EVENT_SET_TASK_STATUS_FLAG: &str = "set_task_status";
/// Set task process data event flag
/// 设置任务处理数据事件标识
pub const EVENT_SET_TASK_PROCESS_DATA_FLAG: &str = "set_task_process";
/// Execute task event flag
/// 执行任务事件标识
pub const EVENT_EXECUTE_TASK_FLAG: &str = "execute_task";

pub struct TaskProcessor;

impl TaskProcessor {
/// Initialize the asynchronous task status
/// 初始化异步任务状态
pub async fn init_status(cache_key: &str, task_id: Option<u64>, cache_client: &TardisCacheClient) -> TardisResult<u64> {
let task_id = task_id.unwrap_or(Local::now().timestamp_nanos_opt().expect("maybe in 23rd century") as u64);
Expand All @@ -44,20 +47,23 @@ impl TaskProcessor {
Ok(task_id)
}

/// Check the status of the asynchronous task (whether it is completed)
/// 检查异步任务状态(是否完成)
pub async fn check_status(cache_key: &str, task_id: u64, cache_client: &TardisCacheClient) -> TardisResult<bool> {
let result1 = cache_client.getbit(&format!("{cache_key}:1"), (task_id / u32::MAX as u64) as usize).await?;
let result2 = cache_client.getbit(&format!("{cache_key}:2"), (task_id % u32::MAX as u64) as usize).await?;
Ok(result1 && result2)
}

/// Set the status of the asynchronous task (whether it is completed)
/// 设置异步任务状态(是否完成)
pub async fn set_status(cache_key: &str, task_id: u64, status: bool, cache_client: &TardisCacheClient) -> TardisResult<()> {
cache_client.setbit(&format!("{cache_key}:1"), (task_id / u32::MAX as u64) as usize, status).await?;
cache_client.setbit(&format!("{cache_key}:2"), (task_id % u32::MAX as u64) as usize, status).await?;
Ok(())
}

/// Set the status of the asynchronous task (whether it is completed) and send an event
/// 设置异步任务状态(是否完成)并发送事件
pub async fn set_status_with_event(
cache_key: &str,
Expand All @@ -83,12 +89,14 @@ impl TaskProcessor {
.await
}

/// Set the processing data of the asynchronous task
/// 设置异步任务处理数据
pub async fn set_process_data(cache_key: &str, task_id: u64, data: Value, cache_client: &TardisCacheClient) -> TardisResult<()> {
cache_client.set_ex(&format!("{cache_key}:{task_id}"), &TardisFuns::json.json_to_string(data)?, TASK_PROCESSOR_DATA_EX_SEC).await?;
Ok(())
}

/// Set the processing data of the asynchronous task and send an event
/// 设置异步任务处理数据并发送事件
pub async fn set_process_data_with_event(
cache_key: &str,
Expand All @@ -115,6 +123,7 @@ impl TaskProcessor {
Ok(())
}

/// Fetch the processing data of the asynchronous task
/// 获取异步任务处理数据
pub async fn get_process_data(cache_key: &str, task_id: u64, cache_client: &TardisCacheClient) -> TardisResult<Value> {
if let Some(result) = cache_client.get(&format!("{cache_key}:{task_id}")).await? {
Expand All @@ -124,6 +133,7 @@ impl TaskProcessor {
}
}

/// Execute asynchronous task
/// 执行异步任务
pub async fn execute_task<P, T>(cache_key: &str, process_fun: P, cache_client: &Arc<TardisCacheClient>) -> TardisResult<u64>
where
Expand All @@ -133,6 +143,7 @@ impl TaskProcessor {
Self::do_execute_task_with_ctx(cache_key, process_fun, cache_client, None, "".to_string(), None, None).await
}

/// Execute asynchronous task and send event
/// 执行异步任务并发送事件
pub async fn execute_task_with_ctx<P, T>(
cache_key: &str,
Expand Down Expand Up @@ -204,6 +215,7 @@ impl TaskProcessor {
Ok(task_id)
}

/// Execute asynchronous task (without asynchronous function, only used to mark the start of the task)
/// 执行异步任务(不带异步函数,仅用于标记任务开始执行)
pub async fn execute_task_without_fun(
cache_key: &str,
Expand All @@ -229,11 +241,13 @@ impl TaskProcessor {
Ok(task_id)
}

/// Stop asynchronous task
/// 停止异步任务
pub async fn stop_task(cache_key: &str, task_id: u64, cache_client: &TardisCacheClient) -> TardisResult<()> {
Self::stop_task_with_event(cache_key, task_id, cache_client, None, "".to_string(), None).await
}

/// Stop asynchronous task and send event
/// 停止异步任务并发送事件
pub async fn stop_task_with_event(
cache_key: &str,
Expand Down Expand Up @@ -262,8 +276,10 @@ impl TaskProcessor {
Ok(())
}

/// Fetch the asynchronous task IDs in the context
/// 获取异步任务IDs
///
/// Use ``,`` to separate multiple tasks
/// 多个任务使用``,``分隔
pub async fn get_task_id_with_ctx(ctx: &TardisContext) -> TardisResult<Option<String>> {
ctx.get_ext(TASK_IN_CTX_FLAG).await
Expand All @@ -285,7 +301,7 @@ impl TaskProcessor {
}

#[derive(Clone, Debug, Deserialize, Serialize)]
pub struct TaskWsEventReq {
struct TaskWsEventReq {
pub task_id: u64,
pub data: Value,
pub msg: String,
Expand Down
1 change: 1 addition & 0 deletions backend/basic/src/test.rs
Original file line number Diff line number Diff line change
@@ -1,3 +1,4 @@
#[cfg(feature = "default")]
pub mod init_rbum_test_container;
#[cfg(feature = "default")]
pub mod test_http_client;
4 changes: 1 addition & 3 deletions backend/basic/src/test/init_rbum_test_container.rs
Original file line number Diff line number Diff line change
@@ -1,3 +1,4 @@
//! Init test container
use std::env;

use tardis::basic::result::TardisResult;
Expand All @@ -15,9 +16,6 @@ pub struct LifeHold<'a> {
}

pub async fn init(docker: &Cli, sql_init_path: Option<String>) -> TardisResult<LifeHold<'_>> {
// let reldb_container = TardisTestContainer::mysql_custom(None, docker);
// let port = reldb_container.get_host_port_ipv4(3306);
// let url = format!("mysql://root:123456@127.0.0.1:{}/test", port);
let reldb_container = TardisTestContainer::postgres_custom(sql_init_path.as_deref(), docker);
let port = reldb_container.get_host_port_ipv4(5432);
let url = format!("postgres://postgres:123456@127.0.0.1:{port}/test");
Expand Down
3 changes: 3 additions & 0 deletions backend/basic/src/test/test_http_client.rs
Original file line number Diff line number Diff line change
@@ -1,3 +1,4 @@
//! Http client for testing
use std::fmt::Debug;

use serde::de::DeserializeOwned;
Expand Down Expand Up @@ -30,6 +31,8 @@ impl TestHttpClient {
}
}

/// Build a request with authentication information
/// 构造一个带有认证信息的请求
pub fn set_auth(&mut self, ctx: &TardisContext) -> TardisResult<()> {
let ctx_base64 = &TardisFuns::crypto.base64.encode(TardisFuns::json.obj_to_string(&ctx)?);
let fw_config = TardisFuns::fw_config();
Expand Down

0 comments on commit 123a721

Please sign in to comment.