添加发布数据的几个接口 删除发布数据版本表的版本字段
This commit is contained in:
parent
b64200284a
commit
ed45a08ad7
53
crates/rtss_api/src/apis/common.rs
Normal file
53
crates/rtss_api/src/apis/common.rs
Normal file
@ -0,0 +1,53 @@
|
||||
use async_graphql::{InputObject, InputType, OutputType, SimpleObject};
|
||||
use rtss_db::{common::TableColumn, model::DraftDataColumn};
|
||||
use rtss_dto::common::IscsStyle;
|
||||
use serde::{de::DeserializeOwned, Deserialize, Serialize};
|
||||
|
||||
pub trait DataOptions: InputType + OutputType + Serialize + DeserializeOwned {
|
||||
fn to_data_options_filter_clause(&self) -> String;
|
||||
}
|
||||
|
||||
#[derive(Debug, InputObject, SimpleObject, Serialize, Deserialize)]
|
||||
#[graphql(input_name = "IscsDataOptionsInput")]
|
||||
pub struct IscsDataOptions {
|
||||
pub style: IscsStyle,
|
||||
}
|
||||
|
||||
impl DataOptions for IscsDataOptions {
|
||||
fn to_data_options_filter_clause(&self) -> String {
|
||||
let options_column = DraftDataColumn::Options.name();
|
||||
format!(
|
||||
"{options_column} @> '{}'",
|
||||
serde_json::to_string(self).unwrap()
|
||||
)
|
||||
}
|
||||
}
|
||||
|
||||
#[cfg(test)]
|
||||
mod tests {
|
||||
use super::*;
|
||||
|
||||
#[test]
|
||||
fn test_iscs_data_options_serialize() {
|
||||
rtss_log::Logging::default().init();
|
||||
let options = IscsDataOptions {
|
||||
style: IscsStyle::DaShiZhiNeng,
|
||||
};
|
||||
let json = serde_json::to_string(&options).unwrap();
|
||||
println!("{}", json);
|
||||
println!("{}", options.style.as_str_name());
|
||||
assert_eq!(json, r#"{"style":"DaShiZhiNeng"}"#);
|
||||
let options: IscsDataOptions = serde_json::from_str(&json).unwrap();
|
||||
assert_eq!(options.style, IscsStyle::DaShiZhiNeng);
|
||||
}
|
||||
|
||||
#[test]
|
||||
fn test_iscs_data_options_into_data_options_filter_clause() {
|
||||
let options = IscsDataOptions {
|
||||
style: IscsStyle::DaShiZhiNeng,
|
||||
};
|
||||
let clause = options.to_data_options_filter_clause();
|
||||
println!("{clause}");
|
||||
assert_eq!(clause, r#"options @> '{"style":"DaShiZhiNeng"}'"#);
|
||||
}
|
||||
}
|
@ -1,16 +1,16 @@
|
||||
use async_graphql::{Context, InputObject, Object, SimpleObject};
|
||||
use async_graphql::{InputType, OutputType};
|
||||
use base64::prelude::*;
|
||||
use base64::Engine;
|
||||
use chrono::NaiveDateTime;
|
||||
use rtss_db::common::TableColumn;
|
||||
use rtss_db::model::DraftDataColumn;
|
||||
use rtss_db::DraftDataAccessor;
|
||||
use rtss_db::RtssDbAccessor;
|
||||
use rtss_dto::common::{DataType, IscsStyle};
|
||||
use serde::de::DeserializeOwned;
|
||||
use serde::{Deserialize, Serialize};
|
||||
use rtss_dto::common::DataType;
|
||||
use serde_json::Value;
|
||||
|
||||
use crate::pagination::PageQueryDto;
|
||||
use crate::apis::PageQueryDto;
|
||||
|
||||
use super::common::{DataOptions, IscsDataOptions};
|
||||
use super::PageDto;
|
||||
|
||||
#[derive(Default)]
|
||||
pub struct DraftDataQuery;
|
||||
@ -20,39 +20,39 @@ pub struct DraftDataMutation;
|
||||
|
||||
#[Object]
|
||||
impl DraftDataQuery {
|
||||
/// 分页查询全部草稿数据(系统管理用)
|
||||
/// 分页查询所有草稿数据(系统管理用)
|
||||
async fn draft_data_paging<'ctx>(
|
||||
&self,
|
||||
ctx: &Context<'ctx>,
|
||||
paging: PageQueryDto,
|
||||
query: DraftDataFilterDto,
|
||||
) -> async_graphql::Result<DraftDataPage> {
|
||||
) -> async_graphql::Result<PageDto<DraftDataDto>> {
|
||||
let db_accessor = ctx.data::<RtssDbAccessor>()?;
|
||||
let paging_result = db_accessor
|
||||
.query_draft_data(query.into(), paging.into())
|
||||
.await?;
|
||||
Ok(paging_result.into())
|
||||
}
|
||||
/// 分页查询用户的草稿数据
|
||||
/// 分页查询用户的草稿ISCS数据
|
||||
async fn user_draft_iscs_data_paging<'ctx>(
|
||||
&self,
|
||||
ctx: &Context<'ctx>,
|
||||
paging: PageQueryDto,
|
||||
query: UserDraftDataFilterDto<IscsDataOptions>,
|
||||
) -> async_graphql::Result<DraftIscsDataPage> {
|
||||
) -> async_graphql::Result<PageDto<DraftIscsDataDto>> {
|
||||
let db_accessor = ctx.data::<RtssDbAccessor>()?;
|
||||
let paging_result = db_accessor
|
||||
.query_draft_data(query.into(), paging.into())
|
||||
.await?;
|
||||
Ok(paging_result.into())
|
||||
}
|
||||
/// 分页查询共享的草稿数据
|
||||
/// 分页查询共享的草稿ISCS数据
|
||||
async fn shared_draft_iscs_data_paging<'ctx>(
|
||||
&self,
|
||||
ctx: &Context<'ctx>,
|
||||
paging: PageQueryDto,
|
||||
query: SharedDraftDataFilterDto<IscsDataOptions>,
|
||||
) -> async_graphql::Result<DraftIscsDataPage> {
|
||||
) -> async_graphql::Result<PageDto<DraftIscsDataDto>> {
|
||||
let db_accessor = ctx.data::<RtssDbAccessor>()?;
|
||||
let paging_result = db_accessor
|
||||
.query_draft_data(query.into(), paging.into())
|
||||
@ -60,11 +60,7 @@ impl DraftDataQuery {
|
||||
Ok(paging_result.into())
|
||||
}
|
||||
/// 根据id获取草稿数据
|
||||
async fn draft_data(
|
||||
&self,
|
||||
ctx: &Context<'_>,
|
||||
id: i32,
|
||||
) -> async_graphql::Result<DraftDataWithStringOptions> {
|
||||
async fn draft_data(&self, ctx: &Context<'_>, id: i32) -> async_graphql::Result<DraftDataDto> {
|
||||
let db_accessor = ctx.data::<RtssDbAccessor>()?;
|
||||
let draft_data = db_accessor.query_draft_data_by_id(id).await?;
|
||||
Ok(draft_data.into())
|
||||
@ -89,7 +85,7 @@ impl DraftDataMutation {
|
||||
&self,
|
||||
ctx: &Context<'_>,
|
||||
input: CreateDraftDataDto<IscsDataOptions>,
|
||||
) -> async_graphql::Result<DraftData<IscsDataOptions>> {
|
||||
) -> async_graphql::Result<DraftIscsDataDto> {
|
||||
let db_accessor = ctx.data::<RtssDbAccessor>()?;
|
||||
let draft_data = db_accessor.create_draft_data(input.into()).await?;
|
||||
Ok(draft_data.into())
|
||||
@ -100,22 +96,22 @@ impl DraftDataMutation {
|
||||
ctx: &Context<'_>,
|
||||
id: i32,
|
||||
name: String,
|
||||
) -> async_graphql::Result<DraftDataWithStringOptions> {
|
||||
) -> async_graphql::Result<DraftDataDto> {
|
||||
let db_accessor = ctx.data::<RtssDbAccessor>()?;
|
||||
let draft_data = db_accessor.update_draft_data_name(id, &name).await?;
|
||||
Ok(draft_data.into())
|
||||
}
|
||||
/// 更新草稿数据data
|
||||
/// data为base64编码的字符串
|
||||
async fn update_draft_data_data(
|
||||
&self,
|
||||
ctx: &Context<'_>,
|
||||
id: i32,
|
||||
data: Vec<u8>,
|
||||
) -> async_graphql::Result<DraftDataWithStringOptions> {
|
||||
data: String, // base64编码的数据
|
||||
) -> async_graphql::Result<DraftDataDto> {
|
||||
let db_accessor = ctx.data::<RtssDbAccessor>()?;
|
||||
let draft_data = db_accessor
|
||||
.update_draft_data_data(id, data.as_slice())
|
||||
.await?;
|
||||
let bytes = BASE64_STANDARD.decode(data).expect("base64 decode error");
|
||||
let draft_data = db_accessor.update_draft_data_data(id, &bytes).await?;
|
||||
Ok(draft_data.into())
|
||||
}
|
||||
/// 更新草稿数据共享状态
|
||||
@ -124,7 +120,7 @@ impl DraftDataMutation {
|
||||
ctx: &Context<'_>,
|
||||
id: i32,
|
||||
is_shared: bool,
|
||||
) -> async_graphql::Result<DraftDataWithStringOptions> {
|
||||
) -> async_graphql::Result<DraftDataDto> {
|
||||
let db_accessor = ctx.data::<RtssDbAccessor>()?;
|
||||
let draft_data = db_accessor.set_draft_data_shared(id, is_shared).await?;
|
||||
Ok(draft_data.into())
|
||||
@ -145,7 +141,7 @@ impl DraftDataMutation {
|
||||
ctx: &Context<'_>,
|
||||
id: i32,
|
||||
release_data_id: i32,
|
||||
) -> async_graphql::Result<DraftDataWithStringOptions> {
|
||||
) -> async_graphql::Result<DraftDataDto> {
|
||||
let db_accessor = ctx.data::<RtssDbAccessor>()?;
|
||||
let draft_data = db_accessor
|
||||
.set_default_release_data_id(id, release_data_id)
|
||||
@ -159,7 +155,7 @@ impl DraftDataMutation {
|
||||
id: i32,
|
||||
name: String,
|
||||
user_id: i32,
|
||||
) -> async_graphql::Result<DraftDataWithStringOptions> {
|
||||
) -> async_graphql::Result<DraftDataDto> {
|
||||
let db_accessor = ctx.data::<RtssDbAccessor>()?;
|
||||
let draft_data = db_accessor.save_as_new_draft(id, &name, user_id).await?;
|
||||
Ok(draft_data.into())
|
||||
@ -208,27 +204,6 @@ impl<T: DataOptions> From<UserDraftDataFilterDto<T>> for rtss_db::DraftDataQuery
|
||||
}
|
||||
}
|
||||
|
||||
pub trait DataOptions: InputType + OutputType + Serialize + DeserializeOwned {
|
||||
fn to_data_options_filter_clause(&self) -> String;
|
||||
}
|
||||
|
||||
#[derive(Debug, InputObject, SimpleObject, Serialize, Deserialize)]
|
||||
#[graphql(input_name = "IscsDataOptionsInput")]
|
||||
pub struct IscsDataOptions {
|
||||
pub style: IscsStyle,
|
||||
}
|
||||
|
||||
impl DataOptions for IscsDataOptions {
|
||||
fn to_data_options_filter_clause(&self) -> String {
|
||||
let options_column = DraftDataColumn::Options.name();
|
||||
// format!("{options_column}['style'] = '\"{}\"'", self.style.as_str_name())
|
||||
format!(
|
||||
"{options_column} @> '{}'",
|
||||
serde_json::to_string(self).unwrap()
|
||||
)
|
||||
}
|
||||
}
|
||||
|
||||
/// 共享的草稿数据查询条件
|
||||
#[derive(Debug, InputObject)]
|
||||
#[graphql(concrete(name = "SharedDraftIscsDataFilterDto", params(IscsDataOptions)))]
|
||||
@ -274,27 +249,32 @@ impl From<DraftDataFilterDto> for rtss_db::DraftDataQuery {
|
||||
}
|
||||
|
||||
#[derive(Debug, SimpleObject)]
|
||||
pub struct DraftDataWithStringOptions {
|
||||
pub struct DraftDataDto {
|
||||
pub id: i32,
|
||||
pub name: String,
|
||||
pub data_type: rtss_dto::common::DataType,
|
||||
pub options: Option<Value>,
|
||||
pub data: Option<Vec<u8>>,
|
||||
/// base64编码的数据
|
||||
pub data: Option<String>,
|
||||
pub user_id: i32,
|
||||
pub default_release_data_id: Option<i32>,
|
||||
pub is_shared: bool,
|
||||
pub created_at: NaiveDateTime,
|
||||
pub updated_at: NaiveDateTime,
|
||||
}
|
||||
|
||||
impl From<rtss_db::model::DraftDataModel> for DraftDataWithStringOptions {
|
||||
impl From<rtss_db::model::DraftDataModel> for DraftDataDto {
|
||||
fn from(value: rtss_db::model::DraftDataModel) -> Self {
|
||||
Self {
|
||||
id: value.id,
|
||||
name: value.name,
|
||||
data_type: DataType::try_from(value.data_type).unwrap(),
|
||||
options: value.options,
|
||||
data: value.data,
|
||||
data: value
|
||||
.data
|
||||
.map(|d| base64::prelude::BASE64_STANDARD.encode(d)),
|
||||
user_id: value.user_id,
|
||||
default_release_data_id: value.default_release_data_id,
|
||||
is_shared: value.is_shared,
|
||||
created_at: value.created_at.naive_local(),
|
||||
updated_at: value.updated_at.naive_local(),
|
||||
@ -303,90 +283,19 @@ impl From<rtss_db::model::DraftDataModel> for DraftDataWithStringOptions {
|
||||
}
|
||||
|
||||
#[derive(Debug, SimpleObject)]
|
||||
#[graphql(concrete(name = "DraftIscsData", params(IscsDataOptions)))]
|
||||
pub struct DraftData<T: OutputType> {
|
||||
pub id: i32,
|
||||
pub name: String,
|
||||
pub data_type: rtss_dto::common::DataType,
|
||||
pub options: Option<T>,
|
||||
pub data: Option<Vec<u8>>,
|
||||
pub user_id: i32,
|
||||
pub is_shared: bool,
|
||||
pub created_at: NaiveDateTime,
|
||||
pub updated_at: NaiveDateTime,
|
||||
pub struct DraftIscsDataDto {
|
||||
pub draft_data: DraftDataDto,
|
||||
pub options: Option<IscsDataOptions>,
|
||||
}
|
||||
|
||||
impl<T: DataOptions> From<rtss_db::model::DraftDataModel> for DraftData<T> {
|
||||
impl From<rtss_db::model::DraftDataModel> for DraftIscsDataDto {
|
||||
fn from(value: rtss_db::model::DraftDataModel) -> Self {
|
||||
Self {
|
||||
id: value.id,
|
||||
name: value.name,
|
||||
data_type: DataType::try_from(value.data_type).unwrap(),
|
||||
options: value.options.map(|o| serde_json::from_value(o).unwrap()),
|
||||
data: value.data,
|
||||
user_id: value.user_id,
|
||||
is_shared: value.is_shared,
|
||||
created_at: value.created_at.naive_local(),
|
||||
updated_at: value.updated_at.naive_local(),
|
||||
options: value
|
||||
.options
|
||||
.clone()
|
||||
.map(|o| serde_json::from_value(o).unwrap()),
|
||||
draft_data: value.into(),
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
#[derive(Debug, SimpleObject)]
|
||||
pub struct DraftDataPage {
|
||||
pub total: i64,
|
||||
pub data: Vec<DraftDataWithStringOptions>,
|
||||
}
|
||||
|
||||
impl From<rtss_db::common::PageResult<rtss_db::model::DraftDataModel>> for DraftDataPage {
|
||||
fn from(value: rtss_db::common::PageResult<rtss_db::model::DraftDataModel>) -> Self {
|
||||
Self {
|
||||
total: value.total,
|
||||
data: value.data.into_iter().map(|m| m.into()).collect(),
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
#[derive(Debug, SimpleObject)]
|
||||
pub struct DraftIscsDataPage {
|
||||
pub total: i64,
|
||||
pub data: Vec<DraftData<IscsDataOptions>>,
|
||||
}
|
||||
|
||||
impl From<rtss_db::common::PageResult<rtss_db::model::DraftDataModel>> for DraftIscsDataPage {
|
||||
fn from(value: rtss_db::common::PageResult<rtss_db::model::DraftDataModel>) -> Self {
|
||||
Self {
|
||||
total: value.total,
|
||||
data: value.data.into_iter().map(|m| m.into()).collect(),
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
#[cfg(test)]
|
||||
mod tests {
|
||||
use super::*;
|
||||
|
||||
#[test]
|
||||
fn test_iscs_data_options_serialize() {
|
||||
rtss_log::Logging::default().init();
|
||||
let options = IscsDataOptions {
|
||||
style: IscsStyle::DaShiZhiNeng,
|
||||
};
|
||||
let json = serde_json::to_string(&options).unwrap();
|
||||
println!("{}", json);
|
||||
println!("{}", options.style.as_str_name());
|
||||
assert_eq!(json, r#"{"style":"DaShiZhiNeng"}"#);
|
||||
let options: IscsDataOptions = serde_json::from_str(&json).unwrap();
|
||||
assert_eq!(options.style, IscsStyle::DaShiZhiNeng);
|
||||
}
|
||||
|
||||
#[test]
|
||||
fn test_iscs_data_options_into_data_options_filter_clause() {
|
||||
let options = IscsDataOptions {
|
||||
style: IscsStyle::DaShiZhiNeng,
|
||||
};
|
||||
let clause = options.to_data_options_filter_clause();
|
||||
println!("{clause}");
|
||||
assert_eq!(clause, r#"options @> '{"style":"DaShiZhiNeng"}'"#);
|
||||
}
|
||||
}
|
68
crates/rtss_api/src/apis/mod.rs
Normal file
68
crates/rtss_api/src/apis/mod.rs
Normal file
@ -0,0 +1,68 @@
|
||||
use async_graphql::MergedObject;
|
||||
use async_graphql::{Enum, InputObject, OutputType, SimpleObject};
|
||||
use draft_data::{DraftDataMutation, DraftDataQuery};
|
||||
use release_data::{ReleaseDataMutation, ReleaseDataQuery};
|
||||
|
||||
mod common;
|
||||
mod draft_data;
|
||||
mod release_data;
|
||||
mod simulation;
|
||||
|
||||
#[derive(Default, MergedObject)]
|
||||
pub struct Query(DraftDataQuery, ReleaseDataQuery);
|
||||
|
||||
#[derive(Default, MergedObject)]
|
||||
pub struct Mutation(DraftDataMutation, ReleaseDataMutation);
|
||||
|
||||
#[derive(Enum, Copy, Clone, Default, Eq, PartialEq, Debug)]
|
||||
#[graphql(remote = "rtss_db::common::SortOrder")]
|
||||
pub enum SortOrder {
|
||||
#[default]
|
||||
Asc,
|
||||
Desc,
|
||||
}
|
||||
|
||||
#[derive(InputObject, Debug)]
|
||||
pub struct PageQueryDto {
|
||||
#[graphql(default = 1)]
|
||||
pub page: i32,
|
||||
#[graphql(default = 10)]
|
||||
pub items_per_page: i32,
|
||||
}
|
||||
|
||||
impl From<PageQueryDto> for rtss_db::common::PageQuery {
|
||||
fn from(value: PageQueryDto) -> Self {
|
||||
Self {
|
||||
page: value.page,
|
||||
items_per_page: value.items_per_page,
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
#[derive(Debug, SimpleObject)]
|
||||
#[graphql(concrete(name = "DraftDataPageDto", params(draft_data::DraftDataDto)))]
|
||||
#[graphql(concrete(name = "DraftIscsDataPageDto", params(draft_data::DraftIscsDataDto)))]
|
||||
#[graphql(concrete(name = "ReleaseDataPageDto", params(release_data::ReleaseDataDto)))]
|
||||
#[graphql(concrete(
|
||||
name = "ReleaseIscsDataPageDto",
|
||||
params(release_data::ReleaseIscsDataWithoutVersionDto)
|
||||
))]
|
||||
pub struct PageDto<T: OutputType> {
|
||||
pub total: i64,
|
||||
pub items: Vec<T>,
|
||||
}
|
||||
|
||||
impl<T: OutputType> PageDto<T> {
|
||||
pub fn new(total: i64, items: Vec<T>) -> Self {
|
||||
Self { total, items }
|
||||
}
|
||||
}
|
||||
|
||||
impl<T: OutputType, M: Into<T>> From<rtss_db::common::PageResult<M>> for PageDto<T> {
|
||||
fn from(value: rtss_db::common::PageResult<M>) -> Self {
|
||||
Self::new(
|
||||
value.total,
|
||||
value.data.into_iter().map(|m| m.into()).collect(),
|
||||
)
|
||||
}
|
||||
}
|
214
crates/rtss_api/src/apis/release_data.rs
Normal file
214
crates/rtss_api/src/apis/release_data.rs
Normal file
@ -0,0 +1,214 @@
|
||||
use async_graphql::{Context, InputObject, Object, SimpleObject};
|
||||
use base64::prelude::*;
|
||||
use chrono::NaiveDateTime;
|
||||
use rtss_db::model::*;
|
||||
use rtss_db::{model::ReleaseDataModel, ReleaseDataAccessor, RtssDbAccessor};
|
||||
use rtss_dto::common::DataType;
|
||||
use serde_json::Value;
|
||||
|
||||
use super::common::IscsDataOptions;
|
||||
use super::{PageDto, PageQueryDto};
|
||||
|
||||
#[derive(Default)]
|
||||
pub struct ReleaseDataQuery;
|
||||
|
||||
#[derive(Default)]
|
||||
pub struct ReleaseDataMutation;
|
||||
|
||||
#[Object]
|
||||
impl ReleaseDataQuery {
|
||||
/// 分页查询所有发布数据(系统管理用)
|
||||
async fn release_data_paging(
|
||||
&self,
|
||||
ctx: &Context<'_>,
|
||||
page: PageQueryDto,
|
||||
query: ReleaseDataFilterDto,
|
||||
) -> async_graphql::Result<PageDto<ReleaseDataDto>> {
|
||||
let db_accessor = ctx.data::<RtssDbAccessor>()?;
|
||||
let paging = db_accessor
|
||||
.query_release_data_list(query.into(), page.into())
|
||||
.await?;
|
||||
Ok(paging.into())
|
||||
}
|
||||
|
||||
/// 分页查询用户发布的ISCS数据
|
||||
async fn user_release_iscs_data_paging(
|
||||
&self,
|
||||
ctx: &Context<'_>,
|
||||
page: PageQueryDto,
|
||||
query: UserReleaseDataFilterDto,
|
||||
) -> async_graphql::Result<PageDto<ReleaseIscsDataWithoutVersionDto>> {
|
||||
let db_accessor = ctx.data::<RtssDbAccessor>()?;
|
||||
let paging = db_accessor
|
||||
.query_release_data_list(query.into(), page.into())
|
||||
.await?;
|
||||
Ok(paging.into())
|
||||
}
|
||||
|
||||
/// id查询发布数据
|
||||
async fn release_data(
|
||||
&self,
|
||||
ctx: &Context<'_>,
|
||||
id: i32,
|
||||
) -> async_graphql::Result<ReleaseDataWithUsedVersionDto> {
|
||||
let db_accessor = ctx.data::<RtssDbAccessor>()?;
|
||||
let model = db_accessor.query_release_data_with_used_version(id).await?;
|
||||
Ok(model.into())
|
||||
}
|
||||
}
|
||||
|
||||
#[Object]
|
||||
impl ReleaseDataMutation {
|
||||
/// 发布到新的发布数据
|
||||
async fn release_new_from_draft(
|
||||
&self,
|
||||
ctx: &Context<'_>,
|
||||
draft_id: i32,
|
||||
name: String,
|
||||
description: String,
|
||||
) -> async_graphql::Result<ReleaseDataWithUsedVersionDto> {
|
||||
let db_accessor = ctx.data::<RtssDbAccessor>()?;
|
||||
let result = db_accessor
|
||||
.release_new_from_draft(draft_id, &name, &description)
|
||||
.await?;
|
||||
Ok(result.into())
|
||||
}
|
||||
|
||||
/// 发布到默认发布数据,需要草稿数据发布过或设置了默认发布数据id
|
||||
async fn release_to_default_release_data(
|
||||
&self,
|
||||
ctx: &Context<'_>,
|
||||
draft_id: i32,
|
||||
description: String,
|
||||
) -> async_graphql::Result<ReleaseDataWithUsedVersionDto> {
|
||||
let db_accessor = ctx.data::<RtssDbAccessor>()?;
|
||||
let result = db_accessor
|
||||
.release_to_existing(draft_id, &description)
|
||||
.await?;
|
||||
Ok(result.into())
|
||||
}
|
||||
}
|
||||
|
||||
#[derive(Debug, InputObject)]
|
||||
pub struct ReleaseDataFilterDto {
|
||||
pub name: Option<String>,
|
||||
pub user_id: Option<i32>,
|
||||
pub data_type: Option<DataType>,
|
||||
pub is_published: Option<bool>,
|
||||
}
|
||||
|
||||
#[derive(Debug, InputObject)]
|
||||
pub struct UserReleaseDataFilterDto {
|
||||
pub user_id: i32,
|
||||
pub name: Option<String>,
|
||||
pub data_type: Option<DataType>,
|
||||
pub is_published: Option<bool>,
|
||||
}
|
||||
|
||||
impl From<UserReleaseDataFilterDto> for rtss_db::ReleaseDataQuery {
|
||||
fn from(value: UserReleaseDataFilterDto) -> Self {
|
||||
Self {
|
||||
name: value.name,
|
||||
user_id: Some(value.user_id),
|
||||
data_type: value.data_type,
|
||||
is_published: value.is_published,
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
impl From<ReleaseDataFilterDto> for rtss_db::ReleaseDataQuery {
|
||||
fn from(value: ReleaseDataFilterDto) -> Self {
|
||||
Self {
|
||||
name: value.name,
|
||||
user_id: value.user_id,
|
||||
data_type: value.data_type,
|
||||
is_published: value.is_published,
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
#[derive(Debug, SimpleObject)]
|
||||
pub struct ReleaseDataDto {
|
||||
pub id: i32,
|
||||
pub name: String,
|
||||
pub data_type: String,
|
||||
pub options: Option<Value>,
|
||||
pub used_version_id: Option<i32>,
|
||||
pub user_id: i32,
|
||||
pub is_published: bool,
|
||||
pub created_at: NaiveDateTime,
|
||||
pub updated_at: NaiveDateTime,
|
||||
}
|
||||
|
||||
#[derive(Debug, SimpleObject)]
|
||||
pub struct ReleaseIscsDataWithoutVersionDto {
|
||||
pub release_data: ReleaseDataDto,
|
||||
pub options: Option<IscsDataOptions>,
|
||||
}
|
||||
|
||||
impl From<ReleaseDataModel> for ReleaseIscsDataWithoutVersionDto {
|
||||
fn from(model: ReleaseDataModel) -> Self {
|
||||
Self {
|
||||
options: model
|
||||
.options
|
||||
.clone()
|
||||
.map(|o| serde_json::from_value(o).unwrap()),
|
||||
release_data: model.into(),
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
#[derive(Debug, SimpleObject)]
|
||||
pub struct ReleaseDataWithUsedVersionDto {
|
||||
pub release_data: ReleaseDataDto,
|
||||
pub used_version: Option<ReleaseDataVersionDto>,
|
||||
}
|
||||
|
||||
#[derive(Debug, SimpleObject)]
|
||||
pub struct ReleaseDataVersionDto {
|
||||
pub id: i32,
|
||||
pub release_data_id: i32,
|
||||
pub description: String,
|
||||
/// base64编码的数据
|
||||
pub data: String,
|
||||
pub user_id: i32,
|
||||
pub created_at: NaiveDateTime,
|
||||
}
|
||||
|
||||
impl From<(ReleaseDataModel, ReleaseDataVersionModel)> for ReleaseDataWithUsedVersionDto {
|
||||
fn from((data, version): (ReleaseDataModel, ReleaseDataVersionModel)) -> Self {
|
||||
Self {
|
||||
release_data: data.into(),
|
||||
used_version: Some(version.into()),
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
impl From<ReleaseDataVersionModel> for ReleaseDataVersionDto {
|
||||
fn from(model: ReleaseDataVersionModel) -> Self {
|
||||
Self {
|
||||
id: model.id,
|
||||
release_data_id: model.release_data_id,
|
||||
description: model.description,
|
||||
data: BASE64_STANDARD.encode(model.data),
|
||||
user_id: model.user_id,
|
||||
created_at: model.created_at.naive_local(),
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
impl From<ReleaseDataModel> for ReleaseDataDto {
|
||||
fn from(model: ReleaseDataModel) -> Self {
|
||||
Self {
|
||||
id: model.id,
|
||||
name: model.name,
|
||||
data_type: model.data_type.to_string(),
|
||||
options: model.options,
|
||||
used_version_id: model.used_version_id,
|
||||
user_id: model.user_id,
|
||||
is_published: model.is_published,
|
||||
created_at: model.created_at.naive_local(),
|
||||
updated_at: model.updated_at.naive_local(),
|
||||
}
|
||||
}
|
||||
}
|
@ -1,8 +1,6 @@
|
||||
mod draft_data;
|
||||
// mod jwt_auth;
|
||||
mod pagination;
|
||||
mod apis;
|
||||
mod server;
|
||||
mod simulation;
|
||||
mod simulation_definition;
|
||||
mod sys_info;
|
||||
|
||||
|
@ -1,29 +0,0 @@
|
||||
use async_graphql::{Enum, InputObject, SimpleObject};
|
||||
|
||||
#[derive(Enum, Copy, Clone, Default, Eq, PartialEq, Debug)]
|
||||
#[graphql(remote = "rtss_db::common::SortOrder")]
|
||||
pub enum SortOrder {
|
||||
#[default]
|
||||
Asc,
|
||||
Desc,
|
||||
}
|
||||
|
||||
#[derive(InputObject, Debug)]
|
||||
pub struct PageQueryDto {
|
||||
pub page: i32,
|
||||
pub items_per_page: i32,
|
||||
}
|
||||
|
||||
impl From<PageQueryDto> for rtss_db::common::PageQuery {
|
||||
fn from(value: PageQueryDto) -> Self {
|
||||
Self {
|
||||
page: value.page,
|
||||
items_per_page: value.items_per_page,
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
#[derive(SimpleObject)]
|
||||
pub struct PageDto {
|
||||
pub total: i64,
|
||||
}
|
@ -14,7 +14,7 @@ use rtss_log::tracing::{debug, info};
|
||||
use tokio::net::TcpListener;
|
||||
use tower_http::cors::CorsLayer;
|
||||
|
||||
use crate::draft_data;
|
||||
use crate::apis::{Mutation, Query};
|
||||
use crate::simulation_definition::MutexSimulationManager;
|
||||
|
||||
pub struct ServerConfig {
|
||||
@ -83,12 +83,6 @@ async fn graphiql() -> impl IntoResponse {
|
||||
|
||||
pub type SimulationSchema = Schema<Query, Mutation, EmptySubscription>;
|
||||
|
||||
#[derive(Default, MergedObject)]
|
||||
pub struct Query(draft_data::DraftDataQuery);
|
||||
|
||||
#[derive(Default, MergedObject)]
|
||||
pub struct Mutation(draft_data::DraftDataMutation);
|
||||
|
||||
pub async fn new_schema(config: &ServerConfig) -> SimulationSchema {
|
||||
let dba = rtss_db::get_db_accessor(&config.database_url).await;
|
||||
Schema::build(Query::default(), Mutation::default(), EmptySubscription)
|
||||
|
@ -175,16 +175,19 @@ impl ReleaseDataAccessor for RtssDbAccessor {
|
||||
// 创建发布数据
|
||||
let rd_table = ReleaseDataColumn::Table.name();
|
||||
let rd_insert_columns = format!(
|
||||
"({}, {}, {})",
|
||||
"({}, {}, {}, {})",
|
||||
ReleaseDataColumn::Name.name(),
|
||||
ReleaseDataColumn::DataType.name(),
|
||||
ReleaseDataColumn::Options.name(),
|
||||
ReleaseDataColumn::UserId.name(),
|
||||
);
|
||||
let rd_insert_clause =
|
||||
format!("INSERT INTO {rd_table} {rd_insert_columns} VALUES ($1, $2, $3) RETURNING *");
|
||||
let rd_insert_clause = format!(
|
||||
"INSERT INTO {rd_table} {rd_insert_columns} VALUES ($1, $2, $3, $4) RETURNING *"
|
||||
);
|
||||
let mut rd = sqlx::query_as::<_, ReleaseDataModel>(&rd_insert_clause)
|
||||
.bind(name)
|
||||
.bind(draft.data_type as i32)
|
||||
.bind(draft.options)
|
||||
.bind(draft.user_id)
|
||||
.fetch_one(&mut *tx)
|
||||
.await?;
|
||||
@ -239,7 +242,7 @@ impl ReleaseDataAccessor for RtssDbAccessor {
|
||||
));
|
||||
}
|
||||
// 查询默认发布数据
|
||||
let mut rd = self
|
||||
let rd = self
|
||||
.query_release_data_by_id(draft.default_release_data_id.unwrap())
|
||||
.await?;
|
||||
// 开启事务
|
||||
@ -266,18 +269,19 @@ impl ReleaseDataAccessor for RtssDbAccessor {
|
||||
// 更新发布数据使用的版本
|
||||
let rd_table = ReleaseDataColumn::Table.name();
|
||||
let used_version_id = ReleaseDataColumn::UsedVersionId.name();
|
||||
let rd_options = ReleaseDataColumn::Options.name();
|
||||
let rd_updated_at = ReleaseDataColumn::UpdatedAt.name();
|
||||
let rd_id = ReleaseDataColumn::Id.name();
|
||||
let rd_update_clause =
|
||||
format!("UPDATE {rd_table} SET {used_version_id} = $1, {rd_updated_at} = 'now()' WHERE {rd_id} = $2");
|
||||
sqlx::query(&rd_update_clause)
|
||||
format!("UPDATE {rd_table} SET {used_version_id} = $1, {rd_options} = $2, {rd_updated_at} = 'now()' WHERE {rd_id} = $3 RETURNING *");
|
||||
let rd = sqlx::query_as::<_, ReleaseDataModel>(&rd_update_clause)
|
||||
.bind(rdv.id)
|
||||
.bind(draft.options.clone())
|
||||
.bind(rd.id)
|
||||
.execute(&mut *tx)
|
||||
.fetch_one(&mut *tx)
|
||||
.await?;
|
||||
// 成功后提交事务
|
||||
tx.commit().await?;
|
||||
rd.used_version_id = Some(rdv.id);
|
||||
Ok((rd, rdv))
|
||||
}
|
||||
|
||||
@ -350,17 +354,16 @@ impl ReleaseDataAccessor for RtssDbAccessor {
|
||||
let rdv_table = ReleaseDataVersionColumn::Table.name();
|
||||
// 查询列,除了data列
|
||||
let rdv_columns = format!(
|
||||
"{}, {}, {}, {}, {}, {}",
|
||||
"{}, {}, {}, {}, {}",
|
||||
ReleaseDataVersionColumn::Id.name(),
|
||||
ReleaseDataVersionColumn::ReleaseDataId.name(),
|
||||
ReleaseDataVersionColumn::Version.name(),
|
||||
ReleaseDataVersionColumn::Description.name(),
|
||||
ReleaseDataVersionColumn::UserId.name(),
|
||||
ReleaseDataVersionColumn::CreatedAt.name(),
|
||||
);
|
||||
let rdv_release_id = ReleaseDataVersionColumn::ReleaseDataId.name();
|
||||
// 按版本号倒序排序
|
||||
let sort = Sort::new(ReleaseDataVersionColumn::Version, SortOrder::Desc);
|
||||
let sort = Sort::new(ReleaseDataVersionColumn::Id, SortOrder::Desc);
|
||||
let order_by_clause = sort.to_order_by_clause();
|
||||
let rdv_query_clause = format!(
|
||||
"SELECT {rdv_columns} FROM {rdv_table} WHERE {rdv_release_id} = $1 {order_by_clause}",
|
||||
@ -507,7 +510,9 @@ mod tests {
|
||||
use crate::{CreateDraftData, DraftDataAccessor, RtssDbAccessor};
|
||||
|
||||
use super::*;
|
||||
use rtss_dto::common::IscsStyle;
|
||||
use rtss_log::tracing::Level;
|
||||
use serde::{Deserialize, Serialize};
|
||||
use sqlx::PgPool;
|
||||
|
||||
#[test]
|
||||
@ -543,6 +548,11 @@ mod tests {
|
||||
assert_eq!(query_with_all.build_filter(), expects);
|
||||
}
|
||||
|
||||
#[derive(Debug, Serialize, Deserialize)]
|
||||
pub struct IscsDataOptions {
|
||||
pub style: IscsStyle,
|
||||
}
|
||||
|
||||
// You could also do `use foo_crate::MIGRATOR` and just refer to it as `MIGRATOR` here.
|
||||
#[sqlx::test(migrator = "crate::MIGRATOR")]
|
||||
async fn test_basic_use(pool: PgPool) -> Result<(), DbAccessError> {
|
||||
@ -552,7 +562,14 @@ mod tests {
|
||||
let data = "test".as_bytes();
|
||||
let draft = accessor
|
||||
.create_draft_data(
|
||||
CreateDraftData::new("test", rtss_dto::common::DataType::Em, 1).with_data(data),
|
||||
CreateDraftData::new("test", rtss_dto::common::DataType::Iscs, 1)
|
||||
.with_options(
|
||||
serde_json::to_value(IscsDataOptions {
|
||||
style: IscsStyle::DaShiZhiNeng,
|
||||
})
|
||||
.unwrap(),
|
||||
)
|
||||
.with_data(data),
|
||||
)
|
||||
.await?;
|
||||
let name = "test_release";
|
||||
@ -576,6 +593,10 @@ mod tests {
|
||||
assert_eq!(release_data.name, name);
|
||||
// 检查使用版本是刚刚发布的版本
|
||||
assert_eq!(release_data.used_version_id, Some(version1.id));
|
||||
// 检查options数据
|
||||
let options: IscsDataOptions =
|
||||
serde_json::from_value(release_data.options.unwrap()).unwrap();
|
||||
assert_eq!(options.style, IscsStyle::DaShiZhiNeng);
|
||||
// 检查版本数据
|
||||
assert_eq!(version1.data, data);
|
||||
// 检查版本描述
|
||||
@ -694,7 +715,7 @@ mod tests {
|
||||
let query = ReleaseDataQuery::new().with_data_type(rtss_dto::common::DataType::Em);
|
||||
let page = PageQuery::new(1, 10);
|
||||
let page_result = accessor.query_release_data_list(query, page).await?;
|
||||
assert_eq!(page_result.total, 9);
|
||||
assert_eq!(page_result.total, 8);
|
||||
println!("分页查询发布数据测试成功");
|
||||
|
||||
Ok(())
|
||||
|
@ -74,7 +74,6 @@ pub(crate) enum ReleaseDataVersionColumn {
|
||||
Id,
|
||||
ReleaseDataId,
|
||||
Data,
|
||||
Version,
|
||||
Description,
|
||||
UserId,
|
||||
CreatedAt,
|
||||
@ -86,7 +85,6 @@ pub struct ReleaseDataVersionModel {
|
||||
pub release_data_id: i32,
|
||||
#[sqlx(default)]
|
||||
pub data: Vec<u8>,
|
||||
pub version: i32,
|
||||
pub description: String,
|
||||
pub user_id: i32,
|
||||
pub created_at: DateTime<Local>,
|
||||
@ -243,7 +241,6 @@ impl TableColumn for ReleaseDataVersionColumn {
|
||||
ReleaseDataVersionColumn::Id => "id",
|
||||
ReleaseDataVersionColumn::ReleaseDataId => "release_data_id",
|
||||
ReleaseDataVersionColumn::Data => "data",
|
||||
ReleaseDataVersionColumn::Version => "version",
|
||||
ReleaseDataVersionColumn::Description => "description",
|
||||
ReleaseDataVersionColumn::UserId => "user_id",
|
||||
ReleaseDataVersionColumn::CreatedAt => "created_at",
|
||||
|
@ -90,7 +90,6 @@ CREATE TABLE
|
||||
id SERIAL PRIMARY KEY, -- id 自增主键
|
||||
release_data_id INT NOT NULL, -- 发布数据id
|
||||
data BYTEA NOT NULL, -- 数据
|
||||
version SERIAL NOT NULL, -- 版本号
|
||||
description TEXT NOT NULL, -- 版本描述
|
||||
user_id INT NOT NULL, -- 发布用户id
|
||||
created_at TIMESTAMP WITH TIME ZONE NOT NULL DEFAULT CURRENT_TIMESTAMP, -- 创建时间
|
||||
@ -113,8 +112,6 @@ COMMENT ON COLUMN rtss.release_data_version.release_data_id IS '发布数据id';
|
||||
|
||||
COMMENT ON COLUMN rtss.release_data_version.data IS '数据';
|
||||
|
||||
COMMENT ON COLUMN rtss.release_data_version.version IS '版本号';
|
||||
|
||||
COMMENT ON COLUMN rtss.release_data_version.description IS '版本描述';
|
||||
|
||||
COMMENT ON COLUMN rtss.release_data_version.user_id IS '发布用户id';
|
||||
|
Loading…
Reference in New Issue
Block a user