feat: task ui & custom filter mutation
This commit is contained in:
parent
7eb4e41708
commit
421f9d0293
@ -6,6 +6,7 @@ use tracing::instrument;
|
||||
|
||||
use super::{builder::AppBuilder, context::AppContextTrait};
|
||||
use crate::{
|
||||
app::Environment,
|
||||
errors::{RecorderError, RecorderResult},
|
||||
web::{
|
||||
controller::{self, core::ControllerTrait},
|
||||
@ -72,7 +73,6 @@ impl App {
|
||||
.into_make_service_with_connect_info::<SocketAddr>();
|
||||
|
||||
let task = context.task();
|
||||
|
||||
tokio::try_join!(
|
||||
async {
|
||||
axum::serve(listener, router)
|
||||
@ -84,15 +84,20 @@ impl App {
|
||||
Ok::<(), RecorderError>(())
|
||||
},
|
||||
async {
|
||||
let monitor = task.setup_monitor().await?;
|
||||
|
||||
monitor
|
||||
.run_with_signal(async move {
|
||||
Self::shutdown_signal().await;
|
||||
tracing::info!("apalis shutting down...");
|
||||
Ok(())
|
||||
})
|
||||
.await?;
|
||||
{
|
||||
let monitor = task.setup_monitor().await?;
|
||||
if matches!(context.environment(), Environment::Development) {
|
||||
monitor.run().await?;
|
||||
} else {
|
||||
monitor
|
||||
.run_with_signal(async move {
|
||||
Self::shutdown_signal().await;
|
||||
tracing::info!("apalis shutting down...");
|
||||
Ok(())
|
||||
})
|
||||
.await?;
|
||||
}
|
||||
}
|
||||
|
||||
Ok::<(), RecorderError>(())
|
||||
},
|
||||
|
@ -103,7 +103,7 @@ pub enum RecorderError {
|
||||
#[snafu(source(from(Box<dyn std::error::Error + Send + Sync>, OptDynErr::some)))]
|
||||
source: OptDynErr,
|
||||
},
|
||||
#[snafu(display("Model Entity {entity} not found"))]
|
||||
#[snafu(display("Model Entity {entity} not found or not belong to subscriber"))]
|
||||
ModelEntityNotFound { entity: Cow<'static, str> },
|
||||
#[snafu(transparent)]
|
||||
FetchError { source: FetchError },
|
||||
@ -123,6 +123,8 @@ pub enum RecorderError {
|
||||
#[snafu(source(from(Box<dyn std::error::Error + Send + Sync>, OptDynErr::some)))]
|
||||
source: OptDynErr,
|
||||
},
|
||||
#[snafu(display("Invalid task id: {message}"))]
|
||||
InvalidTaskId { message: String },
|
||||
}
|
||||
|
||||
impl RecorderError {
|
||||
|
@ -1,35 +1,39 @@
|
||||
use std::{ops::Deref, pin::Pin, sync::Arc};
|
||||
use std::{ops::Deref, sync::Arc};
|
||||
|
||||
use async_graphql::dynamic::{ResolverContext, ValueAccessor};
|
||||
use async_graphql::dynamic::{FieldValue, TypeRef};
|
||||
use sea_orm::{
|
||||
ConnectionTrait, EntityTrait, QueryFilter, QuerySelect, QueryTrait, prelude::Expr,
|
||||
ColumnTrait, ConnectionTrait, EntityTrait, QueryFilter, QuerySelect, QueryTrait, prelude::Expr,
|
||||
sea_query::Query,
|
||||
};
|
||||
use seaography::{Builder as SeaographyBuilder, BuilderContext, get_filter_conditions};
|
||||
use seaography::{
|
||||
Builder as SeaographyBuilder, BuilderContext, EntityDeleteMutationBuilder, EntityObjectBuilder,
|
||||
EntityQueryFieldBuilder, get_filter_conditions,
|
||||
};
|
||||
|
||||
use crate::{
|
||||
app::AppContextTrait,
|
||||
errors::{RecorderError, RecorderResult},
|
||||
errors::RecorderError,
|
||||
graphql::{
|
||||
domains::subscribers::restrict_subscriber_for_entity,
|
||||
infra::{
|
||||
custom::generate_custom_entity_delete_mutation_field,
|
||||
custom::generate_entity_filter_mutation_field,
|
||||
json::{convert_jsonb_output_case_for_entity, restrict_jsonb_filter_input_for_entity},
|
||||
},
|
||||
},
|
||||
models::subscriber_tasks,
|
||||
task::ApalisJob,
|
||||
task::{ApalisJobs, ApalisSchema},
|
||||
};
|
||||
|
||||
pub fn register_subscriber_tasks_entity_mutations(builder: &mut SeaographyBuilder) {
|
||||
pub fn register_subscriber_tasks_entity_mutations(
|
||||
mut builder: SeaographyBuilder,
|
||||
) -> SeaographyBuilder {
|
||||
let context = builder.context;
|
||||
let delete_mutation = generate_custom_entity_delete_mutation_field::<subscriber_tasks::Entity>(
|
||||
context,
|
||||
Arc::new(
|
||||
|resolver_ctx: &ResolverContext<'_>,
|
||||
app_ctx: Arc<dyn AppContextTrait>,
|
||||
filters: Option<ValueAccessor<'_>>|
|
||||
-> Pin<Box<dyn Future<Output = RecorderResult<Option<i32>>> + Send>> {
|
||||
{
|
||||
let entitity_delete_mutation_builder = EntityDeleteMutationBuilder { context };
|
||||
let delete_mutation = generate_entity_filter_mutation_field::<subscriber_tasks::Entity, _, _>(
|
||||
context,
|
||||
entitity_delete_mutation_builder.type_name::<subscriber_tasks::Entity>(),
|
||||
TypeRef::named_nn(TypeRef::INT),
|
||||
Arc::new(|resolver_ctx, app_ctx, filters| {
|
||||
let filters_condition = get_filter_conditions::<subscriber_tasks::Entity>(
|
||||
resolver_ctx,
|
||||
context,
|
||||
@ -44,23 +48,74 @@ pub fn register_subscriber_tasks_entity_mutations(builder: &mut SeaographyBuilde
|
||||
.filter(filters_condition);
|
||||
|
||||
let delete_query = Query::delete()
|
||||
.from_table(ApalisJob::Table)
|
||||
.from_table((ApalisSchema::Schema, ApalisJobs::Table))
|
||||
.and_where(
|
||||
Expr::col(ApalisJob::Id).in_subquery(select_subquery.into_query()),
|
||||
Expr::col(ApalisJobs::Id).in_subquery(select_subquery.into_query()),
|
||||
)
|
||||
.to_owned();
|
||||
|
||||
let db_backend = db.deref().get_database_backend();
|
||||
let delete_statement = db_backend.build(&delete_query);
|
||||
|
||||
let result = db.execute(delete_statement).await?;
|
||||
|
||||
Ok::<Option<i32>, RecorderError>(Some(result.rows_affected() as i32))
|
||||
Ok::<_, RecorderError>(Some(FieldValue::value(result.rows_affected() as i32)))
|
||||
})
|
||||
as Pin<Box<dyn Future<Output = RecorderResult<Option<i32>>> + Send>>
|
||||
},
|
||||
),
|
||||
);
|
||||
builder.mutations.push(delete_mutation);
|
||||
}),
|
||||
);
|
||||
builder.mutations.push(delete_mutation);
|
||||
}
|
||||
{
|
||||
let entity_object_builder = EntityObjectBuilder { context };
|
||||
let entity_query_field = EntityQueryFieldBuilder { context };
|
||||
let entity_retry_one_mutation_name = format!(
|
||||
"{}RetryOne",
|
||||
entity_query_field.type_name::<subscriber_tasks::Entity>()
|
||||
);
|
||||
let retry_one_mutation =
|
||||
generate_entity_filter_mutation_field::<subscriber_tasks::Entity, _, _>(
|
||||
context,
|
||||
entity_retry_one_mutation_name,
|
||||
TypeRef::named_nn(entity_object_builder.type_name::<subscriber_tasks::Entity>()),
|
||||
Arc::new(|resolver_ctx, app_ctx, filters| {
|
||||
let filters_condition = get_filter_conditions::<subscriber_tasks::Entity>(
|
||||
resolver_ctx,
|
||||
context,
|
||||
filters,
|
||||
);
|
||||
Box::pin(async move {
|
||||
let db = app_ctx.db();
|
||||
|
||||
let job_id = subscriber_tasks::Entity::find()
|
||||
.filter(filters_condition)
|
||||
.select_only()
|
||||
.column(subscriber_tasks::Column::Id)
|
||||
.into_tuple::<String>()
|
||||
.one(db)
|
||||
.await?
|
||||
.ok_or_else(|| RecorderError::ModelEntityNotFound {
|
||||
entity: "SubscriberTask".into(),
|
||||
})?;
|
||||
|
||||
let task = app_ctx.task();
|
||||
task.retry_subscriber_task(job_id.clone()).await?;
|
||||
|
||||
let task_model = subscriber_tasks::Entity::find()
|
||||
.filter(subscriber_tasks::Column::Id.eq(&job_id))
|
||||
.one(db)
|
||||
.await?
|
||||
.ok_or_else(|| RecorderError::ModelEntityNotFound {
|
||||
entity: "SubscriberTask".into(),
|
||||
})?;
|
||||
|
||||
Ok::<_, RecorderError>(Some(FieldValue::owned_any(task_model)))
|
||||
})
|
||||
}),
|
||||
);
|
||||
builder.mutations.push(retry_one_mutation);
|
||||
}
|
||||
|
||||
builder
|
||||
}
|
||||
|
||||
pub fn register_subscriber_tasks_to_schema_context(context: &mut BuilderContext) {
|
||||
@ -89,6 +144,7 @@ pub fn register_subscriber_tasks_to_schema_builder(
|
||||
builder = builder.register_entity_dataloader_one_to_one(subscriber_tasks::Entity, tokio::spawn);
|
||||
builder =
|
||||
builder.register_entity_dataloader_one_to_many(subscriber_tasks::Entity, tokio::spawn);
|
||||
builder = register_subscriber_tasks_entity_mutations(builder);
|
||||
builder.register_enumeration::<subscriber_tasks::SubscriberTaskType>();
|
||||
builder.register_enumeration::<subscriber_tasks::SubscriberTaskStatus>();
|
||||
builder
|
||||
|
@ -1,104 +1,58 @@
|
||||
use std::sync::Arc;
|
||||
|
||||
use async_graphql::dynamic::{
|
||||
Field, FieldFuture, FieldValue, InputObject, InputValue, Object, TypeRef,
|
||||
use async_graphql::dynamic::{FieldValue, TypeRef};
|
||||
use sea_orm::{ColumnTrait, EntityTrait, QueryFilter};
|
||||
use seaography::{
|
||||
Builder as SeaographyBuilder, EntityObjectBuilder, EntityQueryFieldBuilder,
|
||||
get_filter_conditions,
|
||||
};
|
||||
use seaography::Builder as SeaographyBuilder;
|
||||
use serde::{Deserialize, Serialize};
|
||||
use util_derive::DynamicGraphql;
|
||||
|
||||
use crate::{
|
||||
app::AppContextTrait,
|
||||
auth::AuthUserInfo,
|
||||
models::subscriptions::{self, SubscriptionTrait},
|
||||
errors::RecorderError,
|
||||
graphql::infra::custom::generate_entity_filter_mutation_field,
|
||||
models::{
|
||||
subscriber_tasks,
|
||||
subscriptions::{self, SubscriptionTrait},
|
||||
},
|
||||
task::SubscriberTask,
|
||||
};
|
||||
|
||||
#[derive(DynamicGraphql, Serialize, Deserialize, Clone, Debug)]
|
||||
struct SyncOneSubscriptionFilterInput {
|
||||
pub id: i32,
|
||||
}
|
||||
|
||||
impl SyncOneSubscriptionFilterInput {
|
||||
fn input_type_name() -> &'static str {
|
||||
"SyncOneSubscriptionFilterInput"
|
||||
}
|
||||
|
||||
fn arg_name() -> &'static str {
|
||||
"filter"
|
||||
}
|
||||
|
||||
fn generate_input_object() -> InputObject {
|
||||
InputObject::new(Self::input_type_name())
|
||||
.description("The input of the subscriptionSyncOne series of mutations")
|
||||
.field(InputValue::new(
|
||||
SyncOneSubscriptionFilterInputFieldEnum::Id.as_str(),
|
||||
TypeRef::named_nn(TypeRef::INT),
|
||||
))
|
||||
}
|
||||
}
|
||||
|
||||
#[derive(DynamicGraphql, Serialize, Deserialize, Clone, Debug)]
|
||||
pub struct SyncOneSubscriptionInfo {
|
||||
pub task_id: String,
|
||||
}
|
||||
|
||||
impl SyncOneSubscriptionInfo {
|
||||
fn object_type_name() -> &'static str {
|
||||
"SyncOneSubscriptionInfo"
|
||||
}
|
||||
|
||||
fn generate_output_object() -> Object {
|
||||
Object::new(Self::object_type_name())
|
||||
.description("The output of the subscriptionSyncOne series of mutations")
|
||||
.field(Field::new(
|
||||
SyncOneSubscriptionInfoFieldEnum::TaskId,
|
||||
TypeRef::named_nn(TypeRef::STRING),
|
||||
move |ctx| {
|
||||
FieldFuture::new(async move {
|
||||
let subscription_info = ctx.parent_value.try_downcast_ref::<Self>()?;
|
||||
Ok(Some(async_graphql::Value::from(
|
||||
subscription_info.task_id.as_str(),
|
||||
)))
|
||||
})
|
||||
},
|
||||
))
|
||||
}
|
||||
}
|
||||
|
||||
pub fn register_subscriptions_to_schema_builder(
|
||||
mut builder: SeaographyBuilder,
|
||||
) -> SeaographyBuilder {
|
||||
builder.schema = builder
|
||||
.schema
|
||||
.register(SyncOneSubscriptionFilterInput::generate_input_object());
|
||||
builder.schema = builder
|
||||
.schema
|
||||
.register(SyncOneSubscriptionInfo::generate_output_object());
|
||||
let context = builder.context;
|
||||
|
||||
builder.mutations.push(
|
||||
Field::new(
|
||||
"subscriptionSyncOneFeedsIncremental",
|
||||
TypeRef::named_nn(SyncOneSubscriptionInfo::object_type_name()),
|
||||
move |ctx| {
|
||||
FieldFuture::new(async move {
|
||||
let auth_user_info = ctx.data::<AuthUserInfo>()?;
|
||||
let entity_object_builder = EntityObjectBuilder { context };
|
||||
let entity_query_field = EntityQueryFieldBuilder { context };
|
||||
|
||||
let app_ctx = ctx.data::<Arc<dyn AppContextTrait>>()?;
|
||||
let subscriber_id = auth_user_info.subscriber_auth.subscriber_id;
|
||||
{
|
||||
let sync_one_feeds_incremental_mutation_name = format!(
|
||||
"{}SyncOneFeedsIncremental",
|
||||
entity_query_field.type_name::<subscriptions::Entity>()
|
||||
);
|
||||
|
||||
let filter_input: SyncOneSubscriptionFilterInput = ctx
|
||||
.args
|
||||
.get(SyncOneSubscriptionFilterInput::arg_name())
|
||||
.unwrap()
|
||||
.deserialize()?;
|
||||
let sync_one_feeds_incremental_mutation = generate_entity_filter_mutation_field::<
|
||||
subscriptions::Entity,
|
||||
_,
|
||||
_,
|
||||
>(
|
||||
builder.context,
|
||||
sync_one_feeds_incremental_mutation_name,
|
||||
TypeRef::named_nn(entity_object_builder.type_name::<subscriber_tasks::Entity>()),
|
||||
Arc::new(|resolver_ctx, app_ctx, filters| {
|
||||
let filters_condition =
|
||||
get_filter_conditions::<subscriptions::Entity>(resolver_ctx, context, filters);
|
||||
|
||||
let subscription_model = subscriptions::Model::find_by_id_and_subscriber_id(
|
||||
app_ctx.as_ref(),
|
||||
filter_input.id,
|
||||
subscriber_id,
|
||||
)
|
||||
.await?;
|
||||
Box::pin(async move {
|
||||
let db = app_ctx.db();
|
||||
|
||||
let subscription_model = subscriptions::Entity::find()
|
||||
.filter(filters_condition)
|
||||
.one(db)
|
||||
.await?
|
||||
.ok_or_else(|| RecorderError::ModelEntityNotFound {
|
||||
entity: "Subscription".into(),
|
||||
})?;
|
||||
|
||||
let subscription =
|
||||
subscriptions::Subscription::try_from_model(&subscription_model)?;
|
||||
@ -107,48 +61,56 @@ pub fn register_subscriptions_to_schema_builder(
|
||||
|
||||
let task_id = task_service
|
||||
.add_subscriber_task(
|
||||
auth_user_info.subscriber_auth.subscriber_id,
|
||||
subscription_model.subscriber_id,
|
||||
SubscriberTask::SyncOneSubscriptionFeedsIncremental(
|
||||
subscription.into(),
|
||||
),
|
||||
)
|
||||
.await?;
|
||||
|
||||
Ok(Some(FieldValue::owned_any(SyncOneSubscriptionInfo {
|
||||
task_id: task_id.to_string(),
|
||||
})))
|
||||
let task_model = subscriber_tasks::Entity::find()
|
||||
.filter(subscriber_tasks::Column::Id.eq(task_id.to_string()))
|
||||
.one(db)
|
||||
.await?
|
||||
.ok_or_else(|| RecorderError::ModelEntityNotFound {
|
||||
entity: "SubscriberTask".into(),
|
||||
})?;
|
||||
|
||||
Ok(Some(FieldValue::owned_any(task_model)))
|
||||
})
|
||||
},
|
||||
)
|
||||
.argument(InputValue::new(
|
||||
SyncOneSubscriptionFilterInput::arg_name(),
|
||||
TypeRef::named_nn(SyncOneSubscriptionFilterInput::input_type_name()),
|
||||
)),
|
||||
);
|
||||
}),
|
||||
);
|
||||
|
||||
builder.mutations.push(
|
||||
Field::new(
|
||||
"subscriptionSyncOneFeedsFull",
|
||||
TypeRef::named_nn(SyncOneSubscriptionInfo::object_type_name()),
|
||||
move |ctx| {
|
||||
FieldFuture::new(async move {
|
||||
let auth_user_info = ctx.data::<AuthUserInfo>()?;
|
||||
builder.mutations.push(sync_one_feeds_incremental_mutation);
|
||||
}
|
||||
{
|
||||
let sync_one_feeds_full_mutation_name = format!(
|
||||
"{}SyncOneFeedsFull",
|
||||
entity_query_field.type_name::<subscriptions::Entity>()
|
||||
);
|
||||
|
||||
let app_ctx = ctx.data::<Arc<dyn AppContextTrait>>()?;
|
||||
let subscriber_id = auth_user_info.subscriber_auth.subscriber_id;
|
||||
let sync_one_feeds_full_mutation = generate_entity_filter_mutation_field::<
|
||||
subscriptions::Entity,
|
||||
_,
|
||||
_,
|
||||
>(
|
||||
builder.context,
|
||||
sync_one_feeds_full_mutation_name,
|
||||
TypeRef::named_nn(entity_object_builder.type_name::<subscriber_tasks::Entity>()),
|
||||
Arc::new(|resolver_ctx, app_ctx, filters| {
|
||||
let filters_condition =
|
||||
get_filter_conditions::<subscriptions::Entity>(resolver_ctx, context, filters);
|
||||
|
||||
let filter_input: SyncOneSubscriptionFilterInput = ctx
|
||||
.args
|
||||
.get(SyncOneSubscriptionFilterInput::arg_name())
|
||||
.unwrap()
|
||||
.deserialize()?;
|
||||
Box::pin(async move {
|
||||
let db = app_ctx.db();
|
||||
|
||||
let subscription_model = subscriptions::Model::find_by_id_and_subscriber_id(
|
||||
app_ctx.as_ref(),
|
||||
filter_input.id,
|
||||
subscriber_id,
|
||||
)
|
||||
.await?;
|
||||
let subscription_model = subscriptions::Entity::find()
|
||||
.filter(filters_condition)
|
||||
.one(db)
|
||||
.await?
|
||||
.ok_or_else(|| RecorderError::ModelEntityNotFound {
|
||||
entity: "Subscription".into(),
|
||||
})?;
|
||||
|
||||
let subscription =
|
||||
subscriptions::Subscription::try_from_model(&subscription_model)?;
|
||||
@ -157,46 +119,55 @@ pub fn register_subscriptions_to_schema_builder(
|
||||
|
||||
let task_id = task_service
|
||||
.add_subscriber_task(
|
||||
auth_user_info.subscriber_auth.subscriber_id,
|
||||
subscription_model.subscriber_id,
|
||||
SubscriberTask::SyncOneSubscriptionFeedsFull(subscription.into()),
|
||||
)
|
||||
.await?;
|
||||
|
||||
Ok(Some(FieldValue::owned_any(SyncOneSubscriptionInfo {
|
||||
task_id: task_id.to_string(),
|
||||
})))
|
||||
let task_model = subscriber_tasks::Entity::find()
|
||||
.filter(subscriber_tasks::Column::Id.eq(task_id.to_string()))
|
||||
.one(db)
|
||||
.await?
|
||||
.ok_or_else(|| RecorderError::ModelEntityNotFound {
|
||||
entity: "SubscriberTask".into(),
|
||||
})?;
|
||||
|
||||
Ok(Some(FieldValue::owned_any(task_model)))
|
||||
})
|
||||
},
|
||||
)
|
||||
.argument(InputValue::new(
|
||||
SyncOneSubscriptionFilterInput::arg_name(),
|
||||
TypeRef::named_nn(SyncOneSubscriptionFilterInput::input_type_name()),
|
||||
)),
|
||||
);
|
||||
}),
|
||||
);
|
||||
|
||||
builder.mutations.push(
|
||||
Field::new(
|
||||
"subscriptionSyncOneSources",
|
||||
TypeRef::named_nn(SyncOneSubscriptionInfo::object_type_name()),
|
||||
move |ctx| {
|
||||
FieldFuture::new(async move {
|
||||
let auth_user_info = ctx.data::<AuthUserInfo>()?;
|
||||
let app_ctx = ctx.data::<Arc<dyn AppContextTrait>>()?;
|
||||
builder.mutations.push(sync_one_feeds_full_mutation);
|
||||
}
|
||||
|
||||
let subscriber_id = auth_user_info.subscriber_auth.subscriber_id;
|
||||
{
|
||||
let sync_one_sources_mutation_name = format!(
|
||||
"{}SyncOneSources",
|
||||
entity_query_field.type_name::<subscriptions::Entity>()
|
||||
);
|
||||
|
||||
let filter_input: SyncOneSubscriptionFilterInput = ctx
|
||||
.args
|
||||
.get(SyncOneSubscriptionFilterInput::arg_name())
|
||||
.unwrap()
|
||||
.deserialize()?;
|
||||
let sync_one_sources_mutation = generate_entity_filter_mutation_field::<
|
||||
subscriptions::Entity,
|
||||
_,
|
||||
_,
|
||||
>(
|
||||
builder.context,
|
||||
sync_one_sources_mutation_name,
|
||||
TypeRef::named_nn(entity_object_builder.type_name::<subscriber_tasks::Entity>()),
|
||||
Arc::new(|resolver_ctx, app_ctx, filters| {
|
||||
let filters_condition =
|
||||
get_filter_conditions::<subscriptions::Entity>(resolver_ctx, context, filters);
|
||||
|
||||
let subscription_model = subscriptions::Model::find_by_id_and_subscriber_id(
|
||||
app_ctx.as_ref(),
|
||||
filter_input.id,
|
||||
subscriber_id,
|
||||
)
|
||||
.await?;
|
||||
Box::pin(async move {
|
||||
let db = app_ctx.db();
|
||||
|
||||
let subscription_model = subscriptions::Entity::find()
|
||||
.filter(filters_condition)
|
||||
.one(db)
|
||||
.await?
|
||||
.ok_or_else(|| RecorderError::ModelEntityNotFound {
|
||||
entity: "Subscription".into(),
|
||||
})?;
|
||||
|
||||
let subscription =
|
||||
subscriptions::Subscription::try_from_model(&subscription_model)?;
|
||||
@ -205,22 +176,26 @@ pub fn register_subscriptions_to_schema_builder(
|
||||
|
||||
let task_id = task_service
|
||||
.add_subscriber_task(
|
||||
auth_user_info.subscriber_auth.subscriber_id,
|
||||
subscription_model.subscriber_id,
|
||||
SubscriberTask::SyncOneSubscriptionSources(subscription.into()),
|
||||
)
|
||||
.await?;
|
||||
|
||||
Ok(Some(FieldValue::owned_any(SyncOneSubscriptionInfo {
|
||||
task_id: task_id.to_string(),
|
||||
})))
|
||||
let task_model = subscriber_tasks::Entity::find()
|
||||
.filter(subscriber_tasks::Column::Id.eq(task_id.to_string()))
|
||||
.one(db)
|
||||
.await?
|
||||
.ok_or_else(|| RecorderError::ModelEntityNotFound {
|
||||
entity: "SubscriberTask".into(),
|
||||
})?;
|
||||
|
||||
Ok(Some(FieldValue::owned_any(task_model)))
|
||||
})
|
||||
},
|
||||
)
|
||||
.argument(InputValue::new(
|
||||
SyncOneSubscriptionFilterInput::arg_name(),
|
||||
TypeRef::named_nn(SyncOneSubscriptionFilterInput::input_type_name()),
|
||||
)),
|
||||
);
|
||||
}),
|
||||
);
|
||||
|
||||
builder.mutations.push(sync_one_sources_mutation);
|
||||
}
|
||||
|
||||
builder
|
||||
}
|
||||
|
@ -1,33 +1,35 @@
|
||||
use std::{pin::Pin, sync::Arc};
|
||||
|
||||
use async_graphql::dynamic::{
|
||||
Field, FieldFuture, InputValue, ResolverContext, TypeRef, ValueAccessor,
|
||||
Field, FieldFuture, FieldValue, InputValue, ResolverContext, TypeRef, ValueAccessor,
|
||||
};
|
||||
use sea_orm::EntityTrait;
|
||||
use seaography::{
|
||||
BuilderContext, EntityDeleteMutationBuilder, EntityObjectBuilder, FilterInputBuilder,
|
||||
GuardAction,
|
||||
};
|
||||
use seaography::{BuilderContext, EntityObjectBuilder, FilterInputBuilder, GuardAction};
|
||||
|
||||
use crate::{app::AppContextTrait, errors::RecorderResult};
|
||||
|
||||
pub type DeleteMutationFn = Arc<
|
||||
dyn Fn(
|
||||
&ResolverContext<'_>,
|
||||
pub type FilterMutationFn = Arc<
|
||||
dyn for<'a> Fn(
|
||||
&ResolverContext<'a>,
|
||||
Arc<dyn AppContextTrait>,
|
||||
Option<ValueAccessor<'_>>,
|
||||
) -> Pin<Box<dyn Future<Output = RecorderResult<Option<i32>>> + Send>>
|
||||
+ Send
|
||||
) -> Pin<
|
||||
Box<dyn Future<Output = RecorderResult<Option<FieldValue<'a>>>> + Send + 'a>,
|
||||
> + Send
|
||||
+ Sync,
|
||||
>;
|
||||
|
||||
pub fn generate_custom_entity_delete_mutation_field<T>(
|
||||
pub fn generate_entity_filter_mutation_field<T, N, R>(
|
||||
builder_context: &'static BuilderContext,
|
||||
mutation_fn: DeleteMutationFn,
|
||||
field_name: N,
|
||||
type_ref: R,
|
||||
mutation_fn: FilterMutationFn,
|
||||
) -> Field
|
||||
where
|
||||
T: EntityTrait,
|
||||
<T as EntityTrait>::Model: Sync,
|
||||
N: Into<String>,
|
||||
R: Into<TypeRef>,
|
||||
{
|
||||
let entity_filter_input_builder = FilterInputBuilder {
|
||||
context: builder_context,
|
||||
@ -35,43 +37,38 @@ where
|
||||
let entity_object_builder = EntityObjectBuilder {
|
||||
context: builder_context,
|
||||
};
|
||||
let entity_delete_mutation_builder = EntityDeleteMutationBuilder {
|
||||
context: builder_context,
|
||||
};
|
||||
let object_name: String = entity_object_builder.type_name::<T>();
|
||||
|
||||
let context = builder_context;
|
||||
|
||||
let guard = builder_context.guards.entity_guards.get(&object_name);
|
||||
|
||||
Field::new(
|
||||
entity_delete_mutation_builder.type_name::<T>(),
|
||||
TypeRef::named_nn(TypeRef::INT),
|
||||
move |ctx| {
|
||||
let mutation_fn = mutation_fn.clone();
|
||||
FieldFuture::new(async move {
|
||||
let guard_flag = if let Some(guard) = guard {
|
||||
(*guard)(&ctx)
|
||||
} else {
|
||||
GuardAction::Allow
|
||||
};
|
||||
Field::new(field_name, type_ref, move |ctx| {
|
||||
let mutation_fn = mutation_fn.clone();
|
||||
FieldFuture::new(async move {
|
||||
let guard_flag = if let Some(guard) = guard {
|
||||
(*guard)(&ctx)
|
||||
} else {
|
||||
GuardAction::Allow
|
||||
};
|
||||
|
||||
if let GuardAction::Block(reason) = guard_flag {
|
||||
return Err::<Option<_>, async_graphql::Error>(async_graphql::Error::new(
|
||||
reason.unwrap_or("Entity guard triggered.".into()),
|
||||
));
|
||||
}
|
||||
if let GuardAction::Block(reason) = guard_flag {
|
||||
return Err::<Option<_>, async_graphql::Error>(async_graphql::Error::new(
|
||||
reason.unwrap_or("Entity guard triggered.".into()),
|
||||
));
|
||||
}
|
||||
|
||||
let app_ctx = ctx.data::<Arc<dyn AppContextTrait>>()?;
|
||||
let app_ctx = ctx.data::<Arc<dyn AppContextTrait>>()?;
|
||||
|
||||
let filters = ctx.args.get(&context.entity_delete_mutation.filter_field);
|
||||
let filters = ctx.args.get(&context.entity_delete_mutation.filter_field);
|
||||
|
||||
let result = mutation_fn(&ctx, app_ctx.clone(), filters).await?;
|
||||
let result = mutation_fn(&ctx, app_ctx.clone(), filters)
|
||||
.await
|
||||
.map_err(async_graphql::Error::new_with_source)?;
|
||||
|
||||
Ok(result.map(async_graphql::Value::from))
|
||||
})
|
||||
},
|
||||
)
|
||||
Ok(result)
|
||||
})
|
||||
})
|
||||
.argument(InputValue::new(
|
||||
&context.entity_delete_mutation.filter_field,
|
||||
TypeRef::named(entity_filter_input_builder.type_name(&object_name)),
|
||||
|
@ -99,7 +99,9 @@ impl Model {
|
||||
..Default::default()
|
||||
};
|
||||
|
||||
let new_item: Model = new_item.save(&txn).await?.try_into()?;
|
||||
let new_item: Model = new_item.insert(&txn).await?;
|
||||
|
||||
txn.commit().await?;
|
||||
|
||||
Ok(new_item)
|
||||
}
|
||||
|
@ -186,19 +186,13 @@ impl Model {
|
||||
let subscription_model = Entity::find_by_id(subscription_id)
|
||||
.one(db)
|
||||
.await?
|
||||
.ok_or_else(|| RecorderError::DbError {
|
||||
source: DbErr::RecordNotFound(format!(
|
||||
"Subscription id {subscription_id} not found or not belong to subscriber \
|
||||
{subscriber_id}",
|
||||
)),
|
||||
.ok_or_else(|| RecorderError::ModelEntityNotFound {
|
||||
entity: "Subscription".into(),
|
||||
})?;
|
||||
|
||||
if subscription_model.subscriber_id != subscriber_id {
|
||||
Err(RecorderError::DbError {
|
||||
source: DbErr::RecordNotFound(format!(
|
||||
"Subscription id {subscription_id} not found or not belong to subscriber \
|
||||
{subscriber_id}",
|
||||
)),
|
||||
Err(RecorderError::ModelEntityNotFound {
|
||||
entity: "Subscription".into(),
|
||||
})?;
|
||||
}
|
||||
|
||||
|
@ -1,7 +0,0 @@
|
||||
use sea_orm::sea_query;
|
||||
|
||||
#[derive(sea_query::Iden)]
|
||||
pub enum ApalisJob {
|
||||
Table,
|
||||
Id,
|
||||
}
|
16
apps/recorder/src/task/extern.rs
Normal file
16
apps/recorder/src/task/extern.rs
Normal file
@ -0,0 +1,16 @@
|
||||
use sea_orm::sea_query;
|
||||
|
||||
#[derive(sea_query::Iden)]
|
||||
|
||||
pub enum ApalisSchema {
|
||||
#[iden = "apalis"]
|
||||
Schema,
|
||||
}
|
||||
|
||||
#[derive(sea_query::Iden)]
|
||||
|
||||
pub enum ApalisJobs {
|
||||
#[iden = "jobs"]
|
||||
Table,
|
||||
Id,
|
||||
}
|
@ -1,13 +1,13 @@
|
||||
mod config;
|
||||
mod core;
|
||||
mod db;
|
||||
mod r#extern;
|
||||
mod registry;
|
||||
mod service;
|
||||
|
||||
pub use core::{SUBSCRIBER_TASK_APALIS_NAME, SubscriberAsyncTaskTrait, SubscriberStreamTaskTrait};
|
||||
|
||||
pub use config::TaskConfig;
|
||||
pub use db::ApalisJob;
|
||||
pub use r#extern::{ApalisJobs, ApalisSchema};
|
||||
pub use registry::{
|
||||
SubscriberTask, SubscriberTaskType, SubscriberTaskTypeEnum, SubscriberTaskTypeVariant,
|
||||
SubscriberTaskTypeVariantIter, SyncOneSubscriptionFeedsFullTask,
|
||||
|
@ -1,4 +1,4 @@
|
||||
use std::{ops::Deref, sync::Arc};
|
||||
use std::{ops::Deref, str::FromStr, sync::Arc};
|
||||
|
||||
use apalis::prelude::*;
|
||||
use apalis_sql::{
|
||||
@ -10,7 +10,7 @@ use tokio::sync::RwLock;
|
||||
|
||||
use crate::{
|
||||
app::AppContextTrait,
|
||||
errors::RecorderResult,
|
||||
errors::{RecorderError, RecorderResult},
|
||||
task::{SUBSCRIBER_TASK_APALIS_NAME, SubscriberTask, TaskConfig},
|
||||
};
|
||||
|
||||
@ -45,6 +45,19 @@ impl TaskService {
|
||||
job.run(ctx).await
|
||||
}
|
||||
|
||||
pub async fn retry_subscriber_task(&self, job_id: String) -> RecorderResult<()> {
|
||||
{
|
||||
let mut storage = self.subscriber_task_storage.write().await;
|
||||
let task_id =
|
||||
TaskId::from_str(&job_id).map_err(|err| RecorderError::InvalidTaskId {
|
||||
message: err.to_string(),
|
||||
})?;
|
||||
let worker_id = WorkerId::new(SUBSCRIBER_TASK_APALIS_NAME);
|
||||
storage.retry(&worker_id, &task_id).await?;
|
||||
}
|
||||
Ok(())
|
||||
}
|
||||
|
||||
pub async fn add_subscriber_task(
|
||||
&self,
|
||||
_subscriber_id: i32,
|
||||
@ -65,15 +78,23 @@ impl TaskService {
|
||||
}
|
||||
|
||||
pub async fn setup_monitor(&self) -> RecorderResult<Monitor> {
|
||||
let monitor = Monitor::new();
|
||||
let worker = WorkerBuilder::new(SUBSCRIBER_TASK_APALIS_NAME)
|
||||
.catch_panic()
|
||||
.enable_tracing()
|
||||
.data(self.ctx.clone())
|
||||
.backend(self.subscriber_task_storage.read().await.clone())
|
||||
.build_fn(Self::run_subscriber_task);
|
||||
let mut monitor = Monitor::new();
|
||||
|
||||
Ok(monitor.register(worker))
|
||||
{
|
||||
let subscriber_task_worker = WorkerBuilder::new(SUBSCRIBER_TASK_APALIS_NAME)
|
||||
.catch_panic()
|
||||
.enable_tracing()
|
||||
.data(self.ctx.clone())
|
||||
.backend({
|
||||
let storage = self.subscriber_task_storage.read().await;
|
||||
storage.clone()
|
||||
})
|
||||
.build_fn(Self::run_subscriber_task);
|
||||
|
||||
monitor = monitor.register(subscriber_task_worker);
|
||||
}
|
||||
|
||||
Ok(monitor)
|
||||
}
|
||||
|
||||
pub async fn setup_listener(&self) -> RecorderResult<PgListen> {
|
||||
|
@ -123,25 +123,25 @@ query GetSubscriptionDetail ($id: Int!) {
|
||||
`;
|
||||
|
||||
export const SYNC_SUBSCRIPTION_FEEDS_INCREMENTAL = gql`
|
||||
mutation SyncSubscriptionFeedsIncremental($id: Int!) {
|
||||
subscriptionSyncOneFeedsIncremental(filter: { id: $id }) {
|
||||
taskId
|
||||
mutation SyncSubscriptionFeedsIncremental($filter: SubscriptionsFilterInput!) {
|
||||
subscriptionsSyncOneFeedsIncremental(filter: $filter) {
|
||||
id
|
||||
}
|
||||
}
|
||||
`;
|
||||
|
||||
export const SYNC_SUBSCRIPTION_FEEDS_FULL = gql`
|
||||
mutation SyncSubscriptionFeedsFull($id: Int!) {
|
||||
subscriptionSyncOneFeedsFull(filter: { id: $id }) {
|
||||
taskId
|
||||
mutation SyncSubscriptionFeedsFull($filter: SubscriptionsFilterInput!) {
|
||||
subscriptionsSyncOneFeedsFull(filter: $filter) {
|
||||
id
|
||||
}
|
||||
}
|
||||
`;
|
||||
|
||||
export const SYNC_SUBSCRIPTION_SOURCES = gql`
|
||||
mutation SyncSubscriptionSources($id: Int!) {
|
||||
subscriptionSyncOneSources(filter: { id: $id }) {
|
||||
taskId
|
||||
mutation SyncSubscriptionSources($filter: SubscriptionsFilterInput!) {
|
||||
subscriptionsSyncOneSources(filter: $filter) {
|
||||
id
|
||||
}
|
||||
}
|
||||
`;
|
||||
|
@ -35,6 +35,31 @@ export const GET_TASKS = gql`
|
||||
}
|
||||
`;
|
||||
|
||||
export const DELETE_TASKS = gql`
|
||||
mutation DeleteTasks($filters: SubscriberTasksFilterInput!) {
|
||||
subscriberTasksDelete(filter: $filters)
|
||||
}
|
||||
`;
|
||||
|
||||
export const RETRY_TASKS = gql`
|
||||
mutation RetryTasks($filters: SubscriberTasksFilterInput!) {
|
||||
subscriberTasksRetryOne(filter: $filters) {
|
||||
id,
|
||||
job,
|
||||
taskType,
|
||||
status,
|
||||
attempts,
|
||||
maxAttempts,
|
||||
runAt,
|
||||
lastError,
|
||||
lockAt,
|
||||
lockBy,
|
||||
doneAt,
|
||||
priority
|
||||
}
|
||||
}
|
||||
`;
|
||||
|
||||
export const TaskTypedSyncOneSubscriptionFeedsIncrementalSchema = type({
|
||||
taskType: `'${SubscriberTaskTypeEnum.SyncOneSubscriptionFeedsIncremental}'`,
|
||||
}).and(SubscriptionSchema);
|
||||
|
@ -25,10 +25,12 @@ type Documents = {
|
||||
"\n mutation UpdateSubscriptions(\n $data: SubscriptionsUpdateInput!,\n $filters: SubscriptionsFilterInput!,\n ) {\n subscriptionsUpdate (\n data: $data\n filter: $filters\n ) {\n id\n createdAt\n updatedAt\n displayName\n category\n sourceUrl\n enabled\n }\n}\n": typeof types.UpdateSubscriptionsDocument,
|
||||
"\n mutation DeleteSubscriptions($filters: SubscriptionsFilterInput) {\n subscriptionsDelete(filter: $filters)\n }\n": typeof types.DeleteSubscriptionsDocument,
|
||||
"\nquery GetSubscriptionDetail ($id: Int!) {\n subscriptions(filters: { id: {\n eq: $id\n } }) {\n nodes {\n id\n displayName\n createdAt\n updatedAt\n category\n sourceUrl\n enabled\n credential3rd {\n id\n username\n }\n bangumi {\n nodes {\n createdAt\n updatedAt\n id\n mikanBangumiId\n displayName\n rawName\n season\n seasonRaw\n fansub\n mikanFansubId\n rssLink\n posterLink\n savePath\n homepage\n }\n }\n }\n }\n}\n": typeof types.GetSubscriptionDetailDocument,
|
||||
"\n mutation SyncSubscriptionFeedsIncremental($id: Int!) {\n subscriptionSyncOneFeedsIncremental(filter: { id: $id }) {\n taskId\n }\n }\n": typeof types.SyncSubscriptionFeedsIncrementalDocument,
|
||||
"\n mutation SyncSubscriptionFeedsFull($id: Int!) {\n subscriptionSyncOneFeedsFull(filter: { id: $id }) {\n taskId\n }\n }\n": typeof types.SyncSubscriptionFeedsFullDocument,
|
||||
"\n mutation SyncSubscriptionSources($id: Int!) {\n subscriptionSyncOneSources(filter: { id: $id }) {\n taskId\n }\n }\n": typeof types.SyncSubscriptionSourcesDocument,
|
||||
"\n mutation SyncSubscriptionFeedsIncremental($filter: SubscriptionsFilterInput!) {\n subscriptionsSyncOneFeedsIncremental(filter: $filter) {\n id\n }\n }\n": typeof types.SyncSubscriptionFeedsIncrementalDocument,
|
||||
"\n mutation SyncSubscriptionFeedsFull($filter: SubscriptionsFilterInput!) {\n subscriptionsSyncOneFeedsFull(filter: $filter) {\n id\n }\n }\n": typeof types.SyncSubscriptionFeedsFullDocument,
|
||||
"\n mutation SyncSubscriptionSources($filter: SubscriptionsFilterInput!) {\n subscriptionsSyncOneSources(filter: $filter) {\n id\n }\n }\n": typeof types.SyncSubscriptionSourcesDocument,
|
||||
"\n query GetTasks($filters: SubscriberTasksFilterInput!, $orderBy: SubscriberTasksOrderInput!, $pagination: PaginationInput!) {\n subscriberTasks(\n pagination: $pagination\n filters: $filters\n orderBy: $orderBy\n ) {\n nodes {\n id,\n job,\n taskType,\n status,\n attempts,\n maxAttempts,\n runAt,\n lastError,\n lockAt,\n lockBy,\n doneAt,\n priority\n }\n paginationInfo {\n total\n pages\n }\n }\n }\n": typeof types.GetTasksDocument,
|
||||
"\n mutation DeleteTasks($filters: SubscriberTasksFilterInput!) {\n subscriberTasksDelete(filter: $filters)\n }\n": typeof types.DeleteTasksDocument,
|
||||
"\n mutation RetryTasks($filters: SubscriberTasksFilterInput!) {\n subscriberTasksRetryOne(filter: $filters) {\n id,\n job,\n taskType,\n status,\n attempts,\n maxAttempts,\n runAt,\n lastError,\n lockAt,\n lockBy,\n doneAt,\n priority\n }\n }\n": typeof types.RetryTasksDocument,
|
||||
};
|
||||
const documents: Documents = {
|
||||
"\n query GetCredential3rd($filters: Credential3rdFilterInput!, $orderBy: Credential3rdOrderInput, $pagination: PaginationInput) {\n credential3rd(filters: $filters, orderBy: $orderBy, pagination: $pagination) {\n nodes {\n id\n cookies\n username\n password\n userAgent\n createdAt\n updatedAt\n credentialType\n }\n paginationInfo {\n total\n pages\n }\n }\n }\n": types.GetCredential3rdDocument,
|
||||
@ -42,10 +44,12 @@ const documents: Documents = {
|
||||
"\n mutation UpdateSubscriptions(\n $data: SubscriptionsUpdateInput!,\n $filters: SubscriptionsFilterInput!,\n ) {\n subscriptionsUpdate (\n data: $data\n filter: $filters\n ) {\n id\n createdAt\n updatedAt\n displayName\n category\n sourceUrl\n enabled\n }\n}\n": types.UpdateSubscriptionsDocument,
|
||||
"\n mutation DeleteSubscriptions($filters: SubscriptionsFilterInput) {\n subscriptionsDelete(filter: $filters)\n }\n": types.DeleteSubscriptionsDocument,
|
||||
"\nquery GetSubscriptionDetail ($id: Int!) {\n subscriptions(filters: { id: {\n eq: $id\n } }) {\n nodes {\n id\n displayName\n createdAt\n updatedAt\n category\n sourceUrl\n enabled\n credential3rd {\n id\n username\n }\n bangumi {\n nodes {\n createdAt\n updatedAt\n id\n mikanBangumiId\n displayName\n rawName\n season\n seasonRaw\n fansub\n mikanFansubId\n rssLink\n posterLink\n savePath\n homepage\n }\n }\n }\n }\n}\n": types.GetSubscriptionDetailDocument,
|
||||
"\n mutation SyncSubscriptionFeedsIncremental($id: Int!) {\n subscriptionSyncOneFeedsIncremental(filter: { id: $id }) {\n taskId\n }\n }\n": types.SyncSubscriptionFeedsIncrementalDocument,
|
||||
"\n mutation SyncSubscriptionFeedsFull($id: Int!) {\n subscriptionSyncOneFeedsFull(filter: { id: $id }) {\n taskId\n }\n }\n": types.SyncSubscriptionFeedsFullDocument,
|
||||
"\n mutation SyncSubscriptionSources($id: Int!) {\n subscriptionSyncOneSources(filter: { id: $id }) {\n taskId\n }\n }\n": types.SyncSubscriptionSourcesDocument,
|
||||
"\n mutation SyncSubscriptionFeedsIncremental($filter: SubscriptionsFilterInput!) {\n subscriptionsSyncOneFeedsIncremental(filter: $filter) {\n id\n }\n }\n": types.SyncSubscriptionFeedsIncrementalDocument,
|
||||
"\n mutation SyncSubscriptionFeedsFull($filter: SubscriptionsFilterInput!) {\n subscriptionsSyncOneFeedsFull(filter: $filter) {\n id\n }\n }\n": types.SyncSubscriptionFeedsFullDocument,
|
||||
"\n mutation SyncSubscriptionSources($filter: SubscriptionsFilterInput!) {\n subscriptionsSyncOneSources(filter: $filter) {\n id\n }\n }\n": types.SyncSubscriptionSourcesDocument,
|
||||
"\n query GetTasks($filters: SubscriberTasksFilterInput!, $orderBy: SubscriberTasksOrderInput!, $pagination: PaginationInput!) {\n subscriberTasks(\n pagination: $pagination\n filters: $filters\n orderBy: $orderBy\n ) {\n nodes {\n id,\n job,\n taskType,\n status,\n attempts,\n maxAttempts,\n runAt,\n lastError,\n lockAt,\n lockBy,\n doneAt,\n priority\n }\n paginationInfo {\n total\n pages\n }\n }\n }\n": types.GetTasksDocument,
|
||||
"\n mutation DeleteTasks($filters: SubscriberTasksFilterInput!) {\n subscriberTasksDelete(filter: $filters)\n }\n": types.DeleteTasksDocument,
|
||||
"\n mutation RetryTasks($filters: SubscriberTasksFilterInput!) {\n subscriberTasksRetryOne(filter: $filters) {\n id,\n job,\n taskType,\n status,\n attempts,\n maxAttempts,\n runAt,\n lastError,\n lockAt,\n lockBy,\n doneAt,\n priority\n }\n }\n": types.RetryTasksDocument,
|
||||
};
|
||||
|
||||
/**
|
||||
@ -109,19 +113,27 @@ export function gql(source: "\nquery GetSubscriptionDetail ($id: Int!) {\n subs
|
||||
/**
|
||||
* The gql function is used to parse GraphQL queries into a document that can be used by GraphQL clients.
|
||||
*/
|
||||
export function gql(source: "\n mutation SyncSubscriptionFeedsIncremental($id: Int!) {\n subscriptionSyncOneFeedsIncremental(filter: { id: $id }) {\n taskId\n }\n }\n"): (typeof documents)["\n mutation SyncSubscriptionFeedsIncremental($id: Int!) {\n subscriptionSyncOneFeedsIncremental(filter: { id: $id }) {\n taskId\n }\n }\n"];
|
||||
export function gql(source: "\n mutation SyncSubscriptionFeedsIncremental($filter: SubscriptionsFilterInput!) {\n subscriptionsSyncOneFeedsIncremental(filter: $filter) {\n id\n }\n }\n"): (typeof documents)["\n mutation SyncSubscriptionFeedsIncremental($filter: SubscriptionsFilterInput!) {\n subscriptionsSyncOneFeedsIncremental(filter: $filter) {\n id\n }\n }\n"];
|
||||
/**
|
||||
* The gql function is used to parse GraphQL queries into a document that can be used by GraphQL clients.
|
||||
*/
|
||||
export function gql(source: "\n mutation SyncSubscriptionFeedsFull($id: Int!) {\n subscriptionSyncOneFeedsFull(filter: { id: $id }) {\n taskId\n }\n }\n"): (typeof documents)["\n mutation SyncSubscriptionFeedsFull($id: Int!) {\n subscriptionSyncOneFeedsFull(filter: { id: $id }) {\n taskId\n }\n }\n"];
|
||||
export function gql(source: "\n mutation SyncSubscriptionFeedsFull($filter: SubscriptionsFilterInput!) {\n subscriptionsSyncOneFeedsFull(filter: $filter) {\n id\n }\n }\n"): (typeof documents)["\n mutation SyncSubscriptionFeedsFull($filter: SubscriptionsFilterInput!) {\n subscriptionsSyncOneFeedsFull(filter: $filter) {\n id\n }\n }\n"];
|
||||
/**
|
||||
* The gql function is used to parse GraphQL queries into a document that can be used by GraphQL clients.
|
||||
*/
|
||||
export function gql(source: "\n mutation SyncSubscriptionSources($id: Int!) {\n subscriptionSyncOneSources(filter: { id: $id }) {\n taskId\n }\n }\n"): (typeof documents)["\n mutation SyncSubscriptionSources($id: Int!) {\n subscriptionSyncOneSources(filter: { id: $id }) {\n taskId\n }\n }\n"];
|
||||
export function gql(source: "\n mutation SyncSubscriptionSources($filter: SubscriptionsFilterInput!) {\n subscriptionsSyncOneSources(filter: $filter) {\n id\n }\n }\n"): (typeof documents)["\n mutation SyncSubscriptionSources($filter: SubscriptionsFilterInput!) {\n subscriptionsSyncOneSources(filter: $filter) {\n id\n }\n }\n"];
|
||||
/**
|
||||
* The gql function is used to parse GraphQL queries into a document that can be used by GraphQL clients.
|
||||
*/
|
||||
export function gql(source: "\n query GetTasks($filters: SubscriberTasksFilterInput!, $orderBy: SubscriberTasksOrderInput!, $pagination: PaginationInput!) {\n subscriberTasks(\n pagination: $pagination\n filters: $filters\n orderBy: $orderBy\n ) {\n nodes {\n id,\n job,\n taskType,\n status,\n attempts,\n maxAttempts,\n runAt,\n lastError,\n lockAt,\n lockBy,\n doneAt,\n priority\n }\n paginationInfo {\n total\n pages\n }\n }\n }\n"): (typeof documents)["\n query GetTasks($filters: SubscriberTasksFilterInput!, $orderBy: SubscriberTasksOrderInput!, $pagination: PaginationInput!) {\n subscriberTasks(\n pagination: $pagination\n filters: $filters\n orderBy: $orderBy\n ) {\n nodes {\n id,\n job,\n taskType,\n status,\n attempts,\n maxAttempts,\n runAt,\n lastError,\n lockAt,\n lockBy,\n doneAt,\n priority\n }\n paginationInfo {\n total\n pages\n }\n }\n }\n"];
|
||||
/**
|
||||
* The gql function is used to parse GraphQL queries into a document that can be used by GraphQL clients.
|
||||
*/
|
||||
export function gql(source: "\n mutation DeleteTasks($filters: SubscriberTasksFilterInput!) {\n subscriberTasksDelete(filter: $filters)\n }\n"): (typeof documents)["\n mutation DeleteTasks($filters: SubscriberTasksFilterInput!) {\n subscriberTasksDelete(filter: $filters)\n }\n"];
|
||||
/**
|
||||
* The gql function is used to parse GraphQL queries into a document that can be used by GraphQL clients.
|
||||
*/
|
||||
export function gql(source: "\n mutation RetryTasks($filters: SubscriberTasksFilterInput!) {\n subscriberTasksRetryOne(filter: $filters) {\n id,\n job,\n taskType,\n status,\n attempts,\n maxAttempts,\n runAt,\n lastError,\n lockAt,\n lockBy,\n doneAt,\n priority\n }\n }\n"): (typeof documents)["\n mutation RetryTasks($filters: SubscriberTasksFilterInput!) {\n subscriberTasksRetryOne(filter: $filters) {\n id,\n job,\n taskType,\n status,\n attempts,\n maxAttempts,\n runAt,\n lastError,\n lockAt,\n lockBy,\n doneAt,\n priority\n }\n }\n"];
|
||||
|
||||
export function gql(source: string) {
|
||||
return (documents as any)[source] ?? {};
|
||||
|
@ -114,7 +114,7 @@ export type BangumiFilterInput = {
|
||||
savePath?: InputMaybe<StringFilterInput>;
|
||||
season?: InputMaybe<IntegerFilterInput>;
|
||||
seasonRaw?: InputMaybe<StringFilterInput>;
|
||||
subscriberId?: InputMaybe<SubscriberIdFilterInput>;
|
||||
subscriberId?: InputMaybe<IntegerFilterInput>;
|
||||
updatedAt?: InputMaybe<TextFilterInput>;
|
||||
};
|
||||
|
||||
@ -133,7 +133,7 @@ export type BangumiInsertInput = {
|
||||
savePath?: InputMaybe<Scalars['String']['input']>;
|
||||
season: Scalars['Int']['input'];
|
||||
seasonRaw?: InputMaybe<Scalars['String']['input']>;
|
||||
subscriberId?: InputMaybe<Scalars['Int']['input']>;
|
||||
subscriberId: Scalars['Int']['input'];
|
||||
updatedAt?: InputMaybe<Scalars['String']['input']>;
|
||||
};
|
||||
|
||||
@ -171,6 +171,7 @@ export type BangumiUpdateInput = {
|
||||
savePath?: InputMaybe<Scalars['String']['input']>;
|
||||
season?: InputMaybe<Scalars['Int']['input']>;
|
||||
seasonRaw?: InputMaybe<Scalars['String']['input']>;
|
||||
subscriberId?: InputMaybe<Scalars['Int']['input']>;
|
||||
updatedAt?: InputMaybe<Scalars['String']['input']>;
|
||||
};
|
||||
|
||||
@ -813,10 +814,8 @@ export type Mutation = {
|
||||
episodesCreateOne: EpisodesBasic;
|
||||
episodesDelete: Scalars['Int']['output'];
|
||||
episodesUpdate: Array<EpisodesBasic>;
|
||||
subscriberTasksCreateBatch: Array<SubscriberTasksBasic>;
|
||||
subscriberTasksCreateOne: SubscriberTasksBasic;
|
||||
subscriberTasksDelete: Scalars['Int']['output'];
|
||||
subscriberTasksUpdate: Array<SubscriberTasksBasic>;
|
||||
subscriberTasksRetryOne: SubscriberTasks;
|
||||
subscriptionBangumiCreateBatch: Array<SubscriptionBangumiBasic>;
|
||||
subscriptionBangumiCreateOne: SubscriptionBangumiBasic;
|
||||
subscriptionBangumiDelete: Scalars['Int']['output'];
|
||||
@ -825,12 +824,12 @@ export type Mutation = {
|
||||
subscriptionEpisodeCreateOne: SubscriptionEpisodeBasic;
|
||||
subscriptionEpisodeDelete: Scalars['Int']['output'];
|
||||
subscriptionEpisodeUpdate: Array<SubscriptionEpisodeBasic>;
|
||||
subscriptionSyncOneFeedsFull: SyncOneSubscriptionInfo;
|
||||
subscriptionSyncOneFeedsIncremental: SyncOneSubscriptionInfo;
|
||||
subscriptionSyncOneSources: SyncOneSubscriptionInfo;
|
||||
subscriptionsCreateBatch: Array<SubscriptionsBasic>;
|
||||
subscriptionsCreateOne: SubscriptionsBasic;
|
||||
subscriptionsDelete: Scalars['Int']['output'];
|
||||
subscriptionsSyncOneFeedsFull: SubscriberTasks;
|
||||
subscriptionsSyncOneFeedsIncremental: SubscriberTasks;
|
||||
subscriptionsSyncOneSources: SubscriberTasks;
|
||||
subscriptionsUpdate: Array<SubscriptionsBasic>;
|
||||
};
|
||||
|
||||
@ -940,23 +939,12 @@ export type MutationEpisodesUpdateArgs = {
|
||||
};
|
||||
|
||||
|
||||
export type MutationSubscriberTasksCreateBatchArgs = {
|
||||
data: Array<SubscriberTasksInsertInput>;
|
||||
};
|
||||
|
||||
|
||||
export type MutationSubscriberTasksCreateOneArgs = {
|
||||
data: SubscriberTasksInsertInput;
|
||||
};
|
||||
|
||||
|
||||
export type MutationSubscriberTasksDeleteArgs = {
|
||||
filter?: InputMaybe<SubscriberTasksFilterInput>;
|
||||
};
|
||||
|
||||
|
||||
export type MutationSubscriberTasksUpdateArgs = {
|
||||
data: SubscriberTasksUpdateInput;
|
||||
export type MutationSubscriberTasksRetryOneArgs = {
|
||||
filter?: InputMaybe<SubscriberTasksFilterInput>;
|
||||
};
|
||||
|
||||
@ -1003,21 +991,6 @@ export type MutationSubscriptionEpisodeUpdateArgs = {
|
||||
};
|
||||
|
||||
|
||||
export type MutationSubscriptionSyncOneFeedsFullArgs = {
|
||||
filter: SyncOneSubscriptionFilterInput;
|
||||
};
|
||||
|
||||
|
||||
export type MutationSubscriptionSyncOneFeedsIncrementalArgs = {
|
||||
filter: SyncOneSubscriptionFilterInput;
|
||||
};
|
||||
|
||||
|
||||
export type MutationSubscriptionSyncOneSourcesArgs = {
|
||||
filter: SyncOneSubscriptionFilterInput;
|
||||
};
|
||||
|
||||
|
||||
export type MutationSubscriptionsCreateBatchArgs = {
|
||||
data: Array<SubscriptionsInsertInput>;
|
||||
};
|
||||
@ -1033,6 +1006,21 @@ export type MutationSubscriptionsDeleteArgs = {
|
||||
};
|
||||
|
||||
|
||||
export type MutationSubscriptionsSyncOneFeedsFullArgs = {
|
||||
filter?: InputMaybe<SubscriptionsFilterInput>;
|
||||
};
|
||||
|
||||
|
||||
export type MutationSubscriptionsSyncOneFeedsIncrementalArgs = {
|
||||
filter?: InputMaybe<SubscriptionsFilterInput>;
|
||||
};
|
||||
|
||||
|
||||
export type MutationSubscriptionsSyncOneSourcesArgs = {
|
||||
filter?: InputMaybe<SubscriptionsFilterInput>;
|
||||
};
|
||||
|
||||
|
||||
export type MutationSubscriptionsUpdateArgs = {
|
||||
data: SubscriptionsUpdateInput;
|
||||
filter?: InputMaybe<SubscriptionsFilterInput>;
|
||||
@ -1231,23 +1219,6 @@ export type SubscriberTasks = {
|
||||
taskType: SubscriberTaskTypeEnum;
|
||||
};
|
||||
|
||||
export type SubscriberTasksBasic = {
|
||||
__typename?: 'SubscriberTasksBasic';
|
||||
attempts: Scalars['Int']['output'];
|
||||
doneAt?: Maybe<Scalars['String']['output']>;
|
||||
id: Scalars['String']['output'];
|
||||
job: Scalars['Json']['output'];
|
||||
lastError?: Maybe<Scalars['String']['output']>;
|
||||
lockAt?: Maybe<Scalars['String']['output']>;
|
||||
lockBy?: Maybe<Scalars['String']['output']>;
|
||||
maxAttempts: Scalars['Int']['output'];
|
||||
priority: Scalars['Int']['output'];
|
||||
runAt: Scalars['String']['output'];
|
||||
status: SubscriberTaskStatusEnum;
|
||||
subscriberId: Scalars['Int']['output'];
|
||||
taskType: SubscriberTaskTypeEnum;
|
||||
};
|
||||
|
||||
export type SubscriberTasksConnection = {
|
||||
__typename?: 'SubscriberTasksConnection';
|
||||
edges: Array<SubscriberTasksEdge>;
|
||||
@ -1280,22 +1251,6 @@ export type SubscriberTasksFilterInput = {
|
||||
taskType?: InputMaybe<StringFilterInput>;
|
||||
};
|
||||
|
||||
export type SubscriberTasksInsertInput = {
|
||||
attempts: Scalars['Int']['input'];
|
||||
doneAt?: InputMaybe<Scalars['String']['input']>;
|
||||
id?: InputMaybe<Scalars['String']['input']>;
|
||||
job: Scalars['Json']['input'];
|
||||
lastError?: InputMaybe<Scalars['String']['input']>;
|
||||
lockAt?: InputMaybe<Scalars['String']['input']>;
|
||||
lockBy?: InputMaybe<Scalars['String']['input']>;
|
||||
maxAttempts: Scalars['Int']['input'];
|
||||
priority: Scalars['Int']['input'];
|
||||
runAt: Scalars['String']['input'];
|
||||
status: SubscriberTaskStatusEnum;
|
||||
subscriberId?: InputMaybe<Scalars['Int']['input']>;
|
||||
taskType: SubscriberTaskTypeEnum;
|
||||
};
|
||||
|
||||
export type SubscriberTasksOrderInput = {
|
||||
attempts?: InputMaybe<OrderByEnum>;
|
||||
doneAt?: InputMaybe<OrderByEnum>;
|
||||
@ -1312,21 +1267,6 @@ export type SubscriberTasksOrderInput = {
|
||||
taskType?: InputMaybe<OrderByEnum>;
|
||||
};
|
||||
|
||||
export type SubscriberTasksUpdateInput = {
|
||||
attempts?: InputMaybe<Scalars['Int']['input']>;
|
||||
doneAt?: InputMaybe<Scalars['String']['input']>;
|
||||
id?: InputMaybe<Scalars['String']['input']>;
|
||||
job?: InputMaybe<Scalars['Json']['input']>;
|
||||
lastError?: InputMaybe<Scalars['String']['input']>;
|
||||
lockAt?: InputMaybe<Scalars['String']['input']>;
|
||||
lockBy?: InputMaybe<Scalars['String']['input']>;
|
||||
maxAttempts?: InputMaybe<Scalars['Int']['input']>;
|
||||
priority?: InputMaybe<Scalars['Int']['input']>;
|
||||
runAt?: InputMaybe<Scalars['String']['input']>;
|
||||
status?: InputMaybe<SubscriberTaskStatusEnum>;
|
||||
taskType?: InputMaybe<SubscriberTaskTypeEnum>;
|
||||
};
|
||||
|
||||
export type Subscribers = {
|
||||
__typename?: 'Subscribers';
|
||||
bangumi: BangumiConnection;
|
||||
@ -1672,17 +1612,6 @@ export type SubscriptionsUpdateInput = {
|
||||
updatedAt?: InputMaybe<Scalars['String']['input']>;
|
||||
};
|
||||
|
||||
/** The input of the subscriptionSyncOne series of mutations */
|
||||
export type SyncOneSubscriptionFilterInput = {
|
||||
id: Scalars['Int']['input'];
|
||||
};
|
||||
|
||||
/** The output of the subscriptionSyncOne series of mutations */
|
||||
export type SyncOneSubscriptionInfo = {
|
||||
__typename?: 'SyncOneSubscriptionInfo';
|
||||
taskId: Scalars['String']['output'];
|
||||
};
|
||||
|
||||
export type TextFilterInput = {
|
||||
between?: InputMaybe<Array<Scalars['String']['input']>>;
|
||||
eq?: InputMaybe<Scalars['String']['input']>;
|
||||
@ -1782,25 +1711,25 @@ export type GetSubscriptionDetailQueryVariables = Exact<{
|
||||
export type GetSubscriptionDetailQuery = { __typename?: 'Query', subscriptions: { __typename?: 'SubscriptionsConnection', nodes: Array<{ __typename?: 'Subscriptions', id: number, displayName: string, createdAt: string, updatedAt: string, category: SubscriptionCategoryEnum, sourceUrl: string, enabled: boolean, credential3rd?: { __typename?: 'Credential3rd', id: number, username?: string | null } | null, bangumi: { __typename?: 'BangumiConnection', nodes: Array<{ __typename?: 'Bangumi', createdAt: string, updatedAt: string, id: number, mikanBangumiId?: string | null, displayName: string, rawName: string, season: number, seasonRaw?: string | null, fansub?: string | null, mikanFansubId?: string | null, rssLink?: string | null, posterLink?: string | null, savePath?: string | null, homepage?: string | null }> } }> } };
|
||||
|
||||
export type SyncSubscriptionFeedsIncrementalMutationVariables = Exact<{
|
||||
id: Scalars['Int']['input'];
|
||||
filter: SubscriptionsFilterInput;
|
||||
}>;
|
||||
|
||||
|
||||
export type SyncSubscriptionFeedsIncrementalMutation = { __typename?: 'Mutation', subscriptionSyncOneFeedsIncremental: { __typename?: 'SyncOneSubscriptionInfo', taskId: string } };
|
||||
export type SyncSubscriptionFeedsIncrementalMutation = { __typename?: 'Mutation', subscriptionsSyncOneFeedsIncremental: { __typename?: 'SubscriberTasks', id: string } };
|
||||
|
||||
export type SyncSubscriptionFeedsFullMutationVariables = Exact<{
|
||||
id: Scalars['Int']['input'];
|
||||
filter: SubscriptionsFilterInput;
|
||||
}>;
|
||||
|
||||
|
||||
export type SyncSubscriptionFeedsFullMutation = { __typename?: 'Mutation', subscriptionSyncOneFeedsFull: { __typename?: 'SyncOneSubscriptionInfo', taskId: string } };
|
||||
export type SyncSubscriptionFeedsFullMutation = { __typename?: 'Mutation', subscriptionsSyncOneFeedsFull: { __typename?: 'SubscriberTasks', id: string } };
|
||||
|
||||
export type SyncSubscriptionSourcesMutationVariables = Exact<{
|
||||
id: Scalars['Int']['input'];
|
||||
filter: SubscriptionsFilterInput;
|
||||
}>;
|
||||
|
||||
|
||||
export type SyncSubscriptionSourcesMutation = { __typename?: 'Mutation', subscriptionSyncOneSources: { __typename?: 'SyncOneSubscriptionInfo', taskId: string } };
|
||||
export type SyncSubscriptionSourcesMutation = { __typename?: 'Mutation', subscriptionsSyncOneSources: { __typename?: 'SubscriberTasks', id: string } };
|
||||
|
||||
export type GetTasksQueryVariables = Exact<{
|
||||
filters: SubscriberTasksFilterInput;
|
||||
@ -1811,6 +1740,20 @@ export type GetTasksQueryVariables = Exact<{
|
||||
|
||||
export type GetTasksQuery = { __typename?: 'Query', subscriberTasks: { __typename?: 'SubscriberTasksConnection', nodes: Array<{ __typename?: 'SubscriberTasks', id: string, job: any, taskType: SubscriberTaskTypeEnum, status: SubscriberTaskStatusEnum, attempts: number, maxAttempts: number, runAt: string, lastError?: string | null, lockAt?: string | null, lockBy?: string | null, doneAt?: string | null, priority: number }>, paginationInfo?: { __typename?: 'PaginationInfo', total: number, pages: number } | null } };
|
||||
|
||||
export type DeleteTasksMutationVariables = Exact<{
|
||||
filters: SubscriberTasksFilterInput;
|
||||
}>;
|
||||
|
||||
|
||||
export type DeleteTasksMutation = { __typename?: 'Mutation', subscriberTasksDelete: number };
|
||||
|
||||
export type RetryTasksMutationVariables = Exact<{
|
||||
filters: SubscriberTasksFilterInput;
|
||||
}>;
|
||||
|
||||
|
||||
export type RetryTasksMutation = { __typename?: 'Mutation', subscriberTasksRetryOne: { __typename?: 'SubscriberTasks', id: string, job: any, taskType: SubscriberTaskTypeEnum, status: SubscriberTaskStatusEnum, attempts: number, maxAttempts: number, runAt: string, lastError?: string | null, lockAt?: string | null, lockBy?: string | null, doneAt?: string | null, priority: number } };
|
||||
|
||||
|
||||
export const GetCredential3rdDocument = {"kind":"Document","definitions":[{"kind":"OperationDefinition","operation":"query","name":{"kind":"Name","value":"GetCredential3rd"},"variableDefinitions":[{"kind":"VariableDefinition","variable":{"kind":"Variable","name":{"kind":"Name","value":"filters"}},"type":{"kind":"NonNullType","type":{"kind":"NamedType","name":{"kind":"Name","value":"Credential3rdFilterInput"}}}},{"kind":"VariableDefinition","variable":{"kind":"Variable","name":{"kind":"Name","value":"orderBy"}},"type":{"kind":"NamedType","name":{"kind":"Name","value":"Credential3rdOrderInput"}}},{"kind":"VariableDefinition","variable":{"kind":"Variable","name":{"kind":"Name","value":"pagination"}},"type":{"kind":"NamedType","name":{"kind":"Name","value":"PaginationInput"}}}],"selectionSet":{"kind":"SelectionSet","selections":[{"kind":"Field","name":{"kind":"Name","value":"credential3rd"},"arguments":[{"kind":"Argument","name":{"kind":"Name","value":"filters"},"value":{"kind":"Variable","name":{"kind":"Name","value":"filters"}}},{"kind":"Argument","name":{"kind":"Name","value":"orderBy"},"value":{"kind":"Variable","name":{"kind":"Name","value":"orderBy"}}},{"kind":"Argument","name":{"kind":"Name","value":"pagination"},"value":{"kind":"Variable","name":{"kind":"Name","value":"pagination"}}}],"selectionSet":{"kind":"SelectionSet","selections":[{"kind":"Field","name":{"kind":"Name","value":"nodes"},"selectionSet":{"kind":"SelectionSet","selections":[{"kind":"Field","name":{"kind":"Name","value":"id"}},{"kind":"Field","name":{"kind":"Name","value":"cookies"}},{"kind":"Field","name":{"kind":"Name","value":"username"}},{"kind":"Field","name":{"kind":"Name","value":"password"}},{"kind":"Field","name":{"kind":"Name","value":"userAgent"}},{"kind":"Field","name":{"kind":"Name","value":"createdAt"}},{"kind":"Field","name":{"kind":"Name","value":"updatedAt"}},{"kind":"Field","name":{"kind":"Name","value":"credentialType"}}]}},{"kind":"Field","name":{"kind":"Name","value":"paginationInfo"},"selectionSet":{"kind":"SelectionSet","selections":[{"kind":"Field","name":{"kind":"Name","value":"total"}},{"kind":"Field","name":{"kind":"Name","value":"pages"}}]}}]}}]}}]} as unknown as DocumentNode<GetCredential3rdQuery, GetCredential3rdQueryVariables>;
|
||||
export const InsertCredential3rdDocument = {"kind":"Document","definitions":[{"kind":"OperationDefinition","operation":"mutation","name":{"kind":"Name","value":"InsertCredential3rd"},"variableDefinitions":[{"kind":"VariableDefinition","variable":{"kind":"Variable","name":{"kind":"Name","value":"data"}},"type":{"kind":"NonNullType","type":{"kind":"NamedType","name":{"kind":"Name","value":"Credential3rdInsertInput"}}}}],"selectionSet":{"kind":"SelectionSet","selections":[{"kind":"Field","name":{"kind":"Name","value":"credential3rdCreateOne"},"arguments":[{"kind":"Argument","name":{"kind":"Name","value":"data"},"value":{"kind":"Variable","name":{"kind":"Name","value":"data"}}}],"selectionSet":{"kind":"SelectionSet","selections":[{"kind":"Field","name":{"kind":"Name","value":"id"}},{"kind":"Field","name":{"kind":"Name","value":"cookies"}},{"kind":"Field","name":{"kind":"Name","value":"username"}},{"kind":"Field","name":{"kind":"Name","value":"password"}},{"kind":"Field","name":{"kind":"Name","value":"userAgent"}},{"kind":"Field","name":{"kind":"Name","value":"createdAt"}},{"kind":"Field","name":{"kind":"Name","value":"updatedAt"}},{"kind":"Field","name":{"kind":"Name","value":"credentialType"}}]}}]}}]} as unknown as DocumentNode<InsertCredential3rdMutation, InsertCredential3rdMutationVariables>;
|
||||
@ -1823,7 +1766,9 @@ export const InsertSubscriptionDocument = {"kind":"Document","definitions":[{"ki
|
||||
export const UpdateSubscriptionsDocument = {"kind":"Document","definitions":[{"kind":"OperationDefinition","operation":"mutation","name":{"kind":"Name","value":"UpdateSubscriptions"},"variableDefinitions":[{"kind":"VariableDefinition","variable":{"kind":"Variable","name":{"kind":"Name","value":"data"}},"type":{"kind":"NonNullType","type":{"kind":"NamedType","name":{"kind":"Name","value":"SubscriptionsUpdateInput"}}}},{"kind":"VariableDefinition","variable":{"kind":"Variable","name":{"kind":"Name","value":"filters"}},"type":{"kind":"NonNullType","type":{"kind":"NamedType","name":{"kind":"Name","value":"SubscriptionsFilterInput"}}}}],"selectionSet":{"kind":"SelectionSet","selections":[{"kind":"Field","name":{"kind":"Name","value":"subscriptionsUpdate"},"arguments":[{"kind":"Argument","name":{"kind":"Name","value":"data"},"value":{"kind":"Variable","name":{"kind":"Name","value":"data"}}},{"kind":"Argument","name":{"kind":"Name","value":"filter"},"value":{"kind":"Variable","name":{"kind":"Name","value":"filters"}}}],"selectionSet":{"kind":"SelectionSet","selections":[{"kind":"Field","name":{"kind":"Name","value":"id"}},{"kind":"Field","name":{"kind":"Name","value":"createdAt"}},{"kind":"Field","name":{"kind":"Name","value":"updatedAt"}},{"kind":"Field","name":{"kind":"Name","value":"displayName"}},{"kind":"Field","name":{"kind":"Name","value":"category"}},{"kind":"Field","name":{"kind":"Name","value":"sourceUrl"}},{"kind":"Field","name":{"kind":"Name","value":"enabled"}}]}}]}}]} as unknown as DocumentNode<UpdateSubscriptionsMutation, UpdateSubscriptionsMutationVariables>;
|
||||
export const DeleteSubscriptionsDocument = {"kind":"Document","definitions":[{"kind":"OperationDefinition","operation":"mutation","name":{"kind":"Name","value":"DeleteSubscriptions"},"variableDefinitions":[{"kind":"VariableDefinition","variable":{"kind":"Variable","name":{"kind":"Name","value":"filters"}},"type":{"kind":"NamedType","name":{"kind":"Name","value":"SubscriptionsFilterInput"}}}],"selectionSet":{"kind":"SelectionSet","selections":[{"kind":"Field","name":{"kind":"Name","value":"subscriptionsDelete"},"arguments":[{"kind":"Argument","name":{"kind":"Name","value":"filter"},"value":{"kind":"Variable","name":{"kind":"Name","value":"filters"}}}]}]}}]} as unknown as DocumentNode<DeleteSubscriptionsMutation, DeleteSubscriptionsMutationVariables>;
|
||||
export const GetSubscriptionDetailDocument = {"kind":"Document","definitions":[{"kind":"OperationDefinition","operation":"query","name":{"kind":"Name","value":"GetSubscriptionDetail"},"variableDefinitions":[{"kind":"VariableDefinition","variable":{"kind":"Variable","name":{"kind":"Name","value":"id"}},"type":{"kind":"NonNullType","type":{"kind":"NamedType","name":{"kind":"Name","value":"Int"}}}}],"selectionSet":{"kind":"SelectionSet","selections":[{"kind":"Field","name":{"kind":"Name","value":"subscriptions"},"arguments":[{"kind":"Argument","name":{"kind":"Name","value":"filters"},"value":{"kind":"ObjectValue","fields":[{"kind":"ObjectField","name":{"kind":"Name","value":"id"},"value":{"kind":"ObjectValue","fields":[{"kind":"ObjectField","name":{"kind":"Name","value":"eq"},"value":{"kind":"Variable","name":{"kind":"Name","value":"id"}}}]}}]}}],"selectionSet":{"kind":"SelectionSet","selections":[{"kind":"Field","name":{"kind":"Name","value":"nodes"},"selectionSet":{"kind":"SelectionSet","selections":[{"kind":"Field","name":{"kind":"Name","value":"id"}},{"kind":"Field","name":{"kind":"Name","value":"displayName"}},{"kind":"Field","name":{"kind":"Name","value":"createdAt"}},{"kind":"Field","name":{"kind":"Name","value":"updatedAt"}},{"kind":"Field","name":{"kind":"Name","value":"category"}},{"kind":"Field","name":{"kind":"Name","value":"sourceUrl"}},{"kind":"Field","name":{"kind":"Name","value":"enabled"}},{"kind":"Field","name":{"kind":"Name","value":"credential3rd"},"selectionSet":{"kind":"SelectionSet","selections":[{"kind":"Field","name":{"kind":"Name","value":"id"}},{"kind":"Field","name":{"kind":"Name","value":"username"}}]}},{"kind":"Field","name":{"kind":"Name","value":"bangumi"},"selectionSet":{"kind":"SelectionSet","selections":[{"kind":"Field","name":{"kind":"Name","value":"nodes"},"selectionSet":{"kind":"SelectionSet","selections":[{"kind":"Field","name":{"kind":"Name","value":"createdAt"}},{"kind":"Field","name":{"kind":"Name","value":"updatedAt"}},{"kind":"Field","name":{"kind":"Name","value":"id"}},{"kind":"Field","name":{"kind":"Name","value":"mikanBangumiId"}},{"kind":"Field","name":{"kind":"Name","value":"displayName"}},{"kind":"Field","name":{"kind":"Name","value":"rawName"}},{"kind":"Field","name":{"kind":"Name","value":"season"}},{"kind":"Field","name":{"kind":"Name","value":"seasonRaw"}},{"kind":"Field","name":{"kind":"Name","value":"fansub"}},{"kind":"Field","name":{"kind":"Name","value":"mikanFansubId"}},{"kind":"Field","name":{"kind":"Name","value":"rssLink"}},{"kind":"Field","name":{"kind":"Name","value":"posterLink"}},{"kind":"Field","name":{"kind":"Name","value":"savePath"}},{"kind":"Field","name":{"kind":"Name","value":"homepage"}}]}}]}}]}}]}}]}}]} as unknown as DocumentNode<GetSubscriptionDetailQuery, GetSubscriptionDetailQueryVariables>;
|
||||
export const SyncSubscriptionFeedsIncrementalDocument = {"kind":"Document","definitions":[{"kind":"OperationDefinition","operation":"mutation","name":{"kind":"Name","value":"SyncSubscriptionFeedsIncremental"},"variableDefinitions":[{"kind":"VariableDefinition","variable":{"kind":"Variable","name":{"kind":"Name","value":"id"}},"type":{"kind":"NonNullType","type":{"kind":"NamedType","name":{"kind":"Name","value":"Int"}}}}],"selectionSet":{"kind":"SelectionSet","selections":[{"kind":"Field","name":{"kind":"Name","value":"subscriptionSyncOneFeedsIncremental"},"arguments":[{"kind":"Argument","name":{"kind":"Name","value":"filter"},"value":{"kind":"ObjectValue","fields":[{"kind":"ObjectField","name":{"kind":"Name","value":"id"},"value":{"kind":"Variable","name":{"kind":"Name","value":"id"}}}]}}],"selectionSet":{"kind":"SelectionSet","selections":[{"kind":"Field","name":{"kind":"Name","value":"taskId"}}]}}]}}]} as unknown as DocumentNode<SyncSubscriptionFeedsIncrementalMutation, SyncSubscriptionFeedsIncrementalMutationVariables>;
|
||||
export const SyncSubscriptionFeedsFullDocument = {"kind":"Document","definitions":[{"kind":"OperationDefinition","operation":"mutation","name":{"kind":"Name","value":"SyncSubscriptionFeedsFull"},"variableDefinitions":[{"kind":"VariableDefinition","variable":{"kind":"Variable","name":{"kind":"Name","value":"id"}},"type":{"kind":"NonNullType","type":{"kind":"NamedType","name":{"kind":"Name","value":"Int"}}}}],"selectionSet":{"kind":"SelectionSet","selections":[{"kind":"Field","name":{"kind":"Name","value":"subscriptionSyncOneFeedsFull"},"arguments":[{"kind":"Argument","name":{"kind":"Name","value":"filter"},"value":{"kind":"ObjectValue","fields":[{"kind":"ObjectField","name":{"kind":"Name","value":"id"},"value":{"kind":"Variable","name":{"kind":"Name","value":"id"}}}]}}],"selectionSet":{"kind":"SelectionSet","selections":[{"kind":"Field","name":{"kind":"Name","value":"taskId"}}]}}]}}]} as unknown as DocumentNode<SyncSubscriptionFeedsFullMutation, SyncSubscriptionFeedsFullMutationVariables>;
|
||||
export const SyncSubscriptionSourcesDocument = {"kind":"Document","definitions":[{"kind":"OperationDefinition","operation":"mutation","name":{"kind":"Name","value":"SyncSubscriptionSources"},"variableDefinitions":[{"kind":"VariableDefinition","variable":{"kind":"Variable","name":{"kind":"Name","value":"id"}},"type":{"kind":"NonNullType","type":{"kind":"NamedType","name":{"kind":"Name","value":"Int"}}}}],"selectionSet":{"kind":"SelectionSet","selections":[{"kind":"Field","name":{"kind":"Name","value":"subscriptionSyncOneSources"},"arguments":[{"kind":"Argument","name":{"kind":"Name","value":"filter"},"value":{"kind":"ObjectValue","fields":[{"kind":"ObjectField","name":{"kind":"Name","value":"id"},"value":{"kind":"Variable","name":{"kind":"Name","value":"id"}}}]}}],"selectionSet":{"kind":"SelectionSet","selections":[{"kind":"Field","name":{"kind":"Name","value":"taskId"}}]}}]}}]} as unknown as DocumentNode<SyncSubscriptionSourcesMutation, SyncSubscriptionSourcesMutationVariables>;
|
||||
export const GetTasksDocument = {"kind":"Document","definitions":[{"kind":"OperationDefinition","operation":"query","name":{"kind":"Name","value":"GetTasks"},"variableDefinitions":[{"kind":"VariableDefinition","variable":{"kind":"Variable","name":{"kind":"Name","value":"filters"}},"type":{"kind":"NonNullType","type":{"kind":"NamedType","name":{"kind":"Name","value":"SubscriberTasksFilterInput"}}}},{"kind":"VariableDefinition","variable":{"kind":"Variable","name":{"kind":"Name","value":"orderBy"}},"type":{"kind":"NonNullType","type":{"kind":"NamedType","name":{"kind":"Name","value":"SubscriberTasksOrderInput"}}}},{"kind":"VariableDefinition","variable":{"kind":"Variable","name":{"kind":"Name","value":"pagination"}},"type":{"kind":"NonNullType","type":{"kind":"NamedType","name":{"kind":"Name","value":"PaginationInput"}}}}],"selectionSet":{"kind":"SelectionSet","selections":[{"kind":"Field","name":{"kind":"Name","value":"subscriberTasks"},"arguments":[{"kind":"Argument","name":{"kind":"Name","value":"pagination"},"value":{"kind":"Variable","name":{"kind":"Name","value":"pagination"}}},{"kind":"Argument","name":{"kind":"Name","value":"filters"},"value":{"kind":"Variable","name":{"kind":"Name","value":"filters"}}},{"kind":"Argument","name":{"kind":"Name","value":"orderBy"},"value":{"kind":"Variable","name":{"kind":"Name","value":"orderBy"}}}],"selectionSet":{"kind":"SelectionSet","selections":[{"kind":"Field","name":{"kind":"Name","value":"nodes"},"selectionSet":{"kind":"SelectionSet","selections":[{"kind":"Field","name":{"kind":"Name","value":"id"}},{"kind":"Field","name":{"kind":"Name","value":"job"}},{"kind":"Field","name":{"kind":"Name","value":"taskType"}},{"kind":"Field","name":{"kind":"Name","value":"status"}},{"kind":"Field","name":{"kind":"Name","value":"attempts"}},{"kind":"Field","name":{"kind":"Name","value":"maxAttempts"}},{"kind":"Field","name":{"kind":"Name","value":"runAt"}},{"kind":"Field","name":{"kind":"Name","value":"lastError"}},{"kind":"Field","name":{"kind":"Name","value":"lockAt"}},{"kind":"Field","name":{"kind":"Name","value":"lockBy"}},{"kind":"Field","name":{"kind":"Name","value":"doneAt"}},{"kind":"Field","name":{"kind":"Name","value":"priority"}}]}},{"kind":"Field","name":{"kind":"Name","value":"paginationInfo"},"selectionSet":{"kind":"SelectionSet","selections":[{"kind":"Field","name":{"kind":"Name","value":"total"}},{"kind":"Field","name":{"kind":"Name","value":"pages"}}]}}]}}]}}]} as unknown as DocumentNode<GetTasksQuery, GetTasksQueryVariables>;
|
||||
export const SyncSubscriptionFeedsIncrementalDocument = {"kind":"Document","definitions":[{"kind":"OperationDefinition","operation":"mutation","name":{"kind":"Name","value":"SyncSubscriptionFeedsIncremental"},"variableDefinitions":[{"kind":"VariableDefinition","variable":{"kind":"Variable","name":{"kind":"Name","value":"filter"}},"type":{"kind":"NonNullType","type":{"kind":"NamedType","name":{"kind":"Name","value":"SubscriptionsFilterInput"}}}}],"selectionSet":{"kind":"SelectionSet","selections":[{"kind":"Field","name":{"kind":"Name","value":"subscriptionsSyncOneFeedsIncremental"},"arguments":[{"kind":"Argument","name":{"kind":"Name","value":"filter"},"value":{"kind":"Variable","name":{"kind":"Name","value":"filter"}}}],"selectionSet":{"kind":"SelectionSet","selections":[{"kind":"Field","name":{"kind":"Name","value":"id"}}]}}]}}]} as unknown as DocumentNode<SyncSubscriptionFeedsIncrementalMutation, SyncSubscriptionFeedsIncrementalMutationVariables>;
|
||||
export const SyncSubscriptionFeedsFullDocument = {"kind":"Document","definitions":[{"kind":"OperationDefinition","operation":"mutation","name":{"kind":"Name","value":"SyncSubscriptionFeedsFull"},"variableDefinitions":[{"kind":"VariableDefinition","variable":{"kind":"Variable","name":{"kind":"Name","value":"filter"}},"type":{"kind":"NonNullType","type":{"kind":"NamedType","name":{"kind":"Name","value":"SubscriptionsFilterInput"}}}}],"selectionSet":{"kind":"SelectionSet","selections":[{"kind":"Field","name":{"kind":"Name","value":"subscriptionsSyncOneFeedsFull"},"arguments":[{"kind":"Argument","name":{"kind":"Name","value":"filter"},"value":{"kind":"Variable","name":{"kind":"Name","value":"filter"}}}],"selectionSet":{"kind":"SelectionSet","selections":[{"kind":"Field","name":{"kind":"Name","value":"id"}}]}}]}}]} as unknown as DocumentNode<SyncSubscriptionFeedsFullMutation, SyncSubscriptionFeedsFullMutationVariables>;
|
||||
export const SyncSubscriptionSourcesDocument = {"kind":"Document","definitions":[{"kind":"OperationDefinition","operation":"mutation","name":{"kind":"Name","value":"SyncSubscriptionSources"},"variableDefinitions":[{"kind":"VariableDefinition","variable":{"kind":"Variable","name":{"kind":"Name","value":"filter"}},"type":{"kind":"NonNullType","type":{"kind":"NamedType","name":{"kind":"Name","value":"SubscriptionsFilterInput"}}}}],"selectionSet":{"kind":"SelectionSet","selections":[{"kind":"Field","name":{"kind":"Name","value":"subscriptionsSyncOneSources"},"arguments":[{"kind":"Argument","name":{"kind":"Name","value":"filter"},"value":{"kind":"Variable","name":{"kind":"Name","value":"filter"}}}],"selectionSet":{"kind":"SelectionSet","selections":[{"kind":"Field","name":{"kind":"Name","value":"id"}}]}}]}}]} as unknown as DocumentNode<SyncSubscriptionSourcesMutation, SyncSubscriptionSourcesMutationVariables>;
|
||||
export const GetTasksDocument = {"kind":"Document","definitions":[{"kind":"OperationDefinition","operation":"query","name":{"kind":"Name","value":"GetTasks"},"variableDefinitions":[{"kind":"VariableDefinition","variable":{"kind":"Variable","name":{"kind":"Name","value":"filters"}},"type":{"kind":"NonNullType","type":{"kind":"NamedType","name":{"kind":"Name","value":"SubscriberTasksFilterInput"}}}},{"kind":"VariableDefinition","variable":{"kind":"Variable","name":{"kind":"Name","value":"orderBy"}},"type":{"kind":"NonNullType","type":{"kind":"NamedType","name":{"kind":"Name","value":"SubscriberTasksOrderInput"}}}},{"kind":"VariableDefinition","variable":{"kind":"Variable","name":{"kind":"Name","value":"pagination"}},"type":{"kind":"NonNullType","type":{"kind":"NamedType","name":{"kind":"Name","value":"PaginationInput"}}}}],"selectionSet":{"kind":"SelectionSet","selections":[{"kind":"Field","name":{"kind":"Name","value":"subscriberTasks"},"arguments":[{"kind":"Argument","name":{"kind":"Name","value":"pagination"},"value":{"kind":"Variable","name":{"kind":"Name","value":"pagination"}}},{"kind":"Argument","name":{"kind":"Name","value":"filters"},"value":{"kind":"Variable","name":{"kind":"Name","value":"filters"}}},{"kind":"Argument","name":{"kind":"Name","value":"orderBy"},"value":{"kind":"Variable","name":{"kind":"Name","value":"orderBy"}}}],"selectionSet":{"kind":"SelectionSet","selections":[{"kind":"Field","name":{"kind":"Name","value":"nodes"},"selectionSet":{"kind":"SelectionSet","selections":[{"kind":"Field","name":{"kind":"Name","value":"id"}},{"kind":"Field","name":{"kind":"Name","value":"job"}},{"kind":"Field","name":{"kind":"Name","value":"taskType"}},{"kind":"Field","name":{"kind":"Name","value":"status"}},{"kind":"Field","name":{"kind":"Name","value":"attempts"}},{"kind":"Field","name":{"kind":"Name","value":"maxAttempts"}},{"kind":"Field","name":{"kind":"Name","value":"runAt"}},{"kind":"Field","name":{"kind":"Name","value":"lastError"}},{"kind":"Field","name":{"kind":"Name","value":"lockAt"}},{"kind":"Field","name":{"kind":"Name","value":"lockBy"}},{"kind":"Field","name":{"kind":"Name","value":"doneAt"}},{"kind":"Field","name":{"kind":"Name","value":"priority"}}]}},{"kind":"Field","name":{"kind":"Name","value":"paginationInfo"},"selectionSet":{"kind":"SelectionSet","selections":[{"kind":"Field","name":{"kind":"Name","value":"total"}},{"kind":"Field","name":{"kind":"Name","value":"pages"}}]}}]}}]}}]} as unknown as DocumentNode<GetTasksQuery, GetTasksQueryVariables>;
|
||||
export const DeleteTasksDocument = {"kind":"Document","definitions":[{"kind":"OperationDefinition","operation":"mutation","name":{"kind":"Name","value":"DeleteTasks"},"variableDefinitions":[{"kind":"VariableDefinition","variable":{"kind":"Variable","name":{"kind":"Name","value":"filters"}},"type":{"kind":"NonNullType","type":{"kind":"NamedType","name":{"kind":"Name","value":"SubscriberTasksFilterInput"}}}}],"selectionSet":{"kind":"SelectionSet","selections":[{"kind":"Field","name":{"kind":"Name","value":"subscriberTasksDelete"},"arguments":[{"kind":"Argument","name":{"kind":"Name","value":"filter"},"value":{"kind":"Variable","name":{"kind":"Name","value":"filters"}}}]}]}}]} as unknown as DocumentNode<DeleteTasksMutation, DeleteTasksMutationVariables>;
|
||||
export const RetryTasksDocument = {"kind":"Document","definitions":[{"kind":"OperationDefinition","operation":"mutation","name":{"kind":"Name","value":"RetryTasks"},"variableDefinitions":[{"kind":"VariableDefinition","variable":{"kind":"Variable","name":{"kind":"Name","value":"filters"}},"type":{"kind":"NonNullType","type":{"kind":"NamedType","name":{"kind":"Name","value":"SubscriberTasksFilterInput"}}}}],"selectionSet":{"kind":"SelectionSet","selections":[{"kind":"Field","name":{"kind":"Name","value":"subscriberTasksRetryOne"},"arguments":[{"kind":"Argument","name":{"kind":"Name","value":"filter"},"value":{"kind":"Variable","name":{"kind":"Name","value":"filters"}}}],"selectionSet":{"kind":"SelectionSet","selections":[{"kind":"Field","name":{"kind":"Name","value":"id"}},{"kind":"Field","name":{"kind":"Name","value":"job"}},{"kind":"Field","name":{"kind":"Name","value":"taskType"}},{"kind":"Field","name":{"kind":"Name","value":"status"}},{"kind":"Field","name":{"kind":"Name","value":"attempts"}},{"kind":"Field","name":{"kind":"Name","value":"maxAttempts"}},{"kind":"Field","name":{"kind":"Name","value":"runAt"}},{"kind":"Field","name":{"kind":"Name","value":"lastError"}},{"kind":"Field","name":{"kind":"Name","value":"lockAt"}},{"kind":"Field","name":{"kind":"Name","value":"lockBy"}},{"kind":"Field","name":{"kind":"Name","value":"doneAt"}},{"kind":"Field","name":{"kind":"Name","value":"priority"}}]}}]}}]} as unknown as DocumentNode<RetryTasksMutation, RetryTasksMutationVariables>;
|
@ -26,7 +26,7 @@ import { memo, useCallback } from 'react';
|
||||
import { toast } from 'sonner';
|
||||
|
||||
export type SubscriptionSyncViewCompletePayload = {
|
||||
taskId: string;
|
||||
id: string;
|
||||
};
|
||||
|
||||
export interface SubscriptionSyncViewProps {
|
||||
@ -43,7 +43,7 @@ export const SubscriptionSyncView = memo(
|
||||
>(SYNC_SUBSCRIPTION_FEEDS_INCREMENTAL, {
|
||||
onCompleted: (data) => {
|
||||
toast.success('Sync completed');
|
||||
onComplete(data.subscriptionSyncOneFeedsIncremental);
|
||||
onComplete(data.subscriptionsSyncOneFeedsIncremental);
|
||||
},
|
||||
onError: (error) => {
|
||||
toast.error('Failed to sync subscription', {
|
||||
@ -58,7 +58,7 @@ export const SubscriptionSyncView = memo(
|
||||
>(SYNC_SUBSCRIPTION_FEEDS_FULL, {
|
||||
onCompleted: (data) => {
|
||||
toast.success('Sync completed');
|
||||
onComplete(data.subscriptionSyncOneFeedsFull);
|
||||
onComplete(data.subscriptionsSyncOneFeedsFull);
|
||||
},
|
||||
onError: (error) => {
|
||||
toast.error('Failed to sync subscription', {
|
||||
@ -73,7 +73,7 @@ export const SubscriptionSyncView = memo(
|
||||
>(SYNC_SUBSCRIPTION_SOURCES, {
|
||||
onCompleted: (data) => {
|
||||
toast.success('Sync completed');
|
||||
onComplete(data.subscriptionSyncOneSources);
|
||||
onComplete(data.subscriptionsSyncOneSources);
|
||||
},
|
||||
onError: (error) => {
|
||||
toast.error('Failed to sync subscription', {
|
||||
@ -89,7 +89,11 @@ export const SubscriptionSyncView = memo(
|
||||
<Button
|
||||
size="lg"
|
||||
variant="outline"
|
||||
onClick={() => syncSubscriptionSources({ variables: { id } })}
|
||||
onClick={() =>
|
||||
syncSubscriptionSources({
|
||||
variables: { filter: { id: { eq: id } } },
|
||||
})
|
||||
}
|
||||
>
|
||||
<RefreshCcwIcon className="h-4 w-4" />
|
||||
<span>Sources</span>
|
||||
@ -98,7 +102,9 @@ export const SubscriptionSyncView = memo(
|
||||
size="lg"
|
||||
variant="outline"
|
||||
onClick={() =>
|
||||
syncSubscriptionFeedsIncremental({ variables: { id } })
|
||||
syncSubscriptionFeedsIncremental({
|
||||
variables: { filter: { id: { eq: id } } },
|
||||
})
|
||||
}
|
||||
>
|
||||
<RefreshCcwIcon className="h-4 w-4" />
|
||||
@ -107,7 +113,11 @@ export const SubscriptionSyncView = memo(
|
||||
<Button
|
||||
size="lg"
|
||||
variant="outline"
|
||||
onClick={() => syncSubscriptionFeedsFull({ variables: { id } })}
|
||||
onClick={() =>
|
||||
syncSubscriptionFeedsFull({
|
||||
variables: { filter: { id: { eq: id } } },
|
||||
})
|
||||
}
|
||||
>
|
||||
<RefreshCcwIcon className="h-4 w-4" />
|
||||
<span>Full Feeds</span>
|
||||
@ -138,7 +148,7 @@ export const SubscriptionSyncDialogContent = memo(
|
||||
navigate({
|
||||
to: '/tasks/detail/$id',
|
||||
params: {
|
||||
id: `${payload.taskId}`,
|
||||
id: `${payload.id}`,
|
||||
},
|
||||
});
|
||||
},
|
||||
|
@ -25,13 +25,9 @@ import {
|
||||
apolloErrorToMessage,
|
||||
getApolloQueryError,
|
||||
} from '@/infra/errors/apollo';
|
||||
import type {
|
||||
GetSubscriptionsQuery,
|
||||
SubscriptionsUpdateInput,
|
||||
} from '@/infra/graphql/gql/graphql';
|
||||
import type { GetSubscriptionsQuery } from '@/infra/graphql/gql/graphql';
|
||||
import type { RouteStateDataOption } from '@/infra/routes/traits';
|
||||
import { useDebouncedSkeleton } from '@/presentation/hooks/use-debounded-skeleton';
|
||||
import { useEvent } from '@/presentation/hooks/use-event';
|
||||
import { cn } from '@/presentation/utils';
|
||||
import { useMutation, useQuery } from '@apollo/client';
|
||||
import { createFileRoute } from '@tanstack/react-router';
|
||||
@ -39,7 +35,6 @@ import { useNavigate } from '@tanstack/react-router';
|
||||
import {
|
||||
type ColumnDef,
|
||||
type PaginationState,
|
||||
type Row,
|
||||
type SortingState,
|
||||
type VisibilityState,
|
||||
flexRender,
|
||||
@ -131,29 +126,6 @@ function SubscriptionManageRouteComponent() {
|
||||
|
||||
const subscriptions = data?.subscriptions;
|
||||
|
||||
const handleUpdateRecord = useEvent(
|
||||
(row: Row<SubscriptionDto>) => async (data: SubscriptionsUpdateInput) => {
|
||||
await updateSubscription({
|
||||
variables: {
|
||||
data,
|
||||
filters: {
|
||||
id: {
|
||||
eq: row.original.id,
|
||||
},
|
||||
},
|
||||
},
|
||||
});
|
||||
}
|
||||
);
|
||||
|
||||
const handleDeleteRecord = useEvent(
|
||||
(row: Row<SubscriptionDto>) => async () => {
|
||||
await deleteSubscription({
|
||||
variables: { filters: { id: { eq: row.original.id } } },
|
||||
});
|
||||
}
|
||||
);
|
||||
|
||||
const columns = useMemo(() => {
|
||||
const cs: ColumnDef<SubscriptionDto>[] = [
|
||||
{
|
||||
@ -166,7 +138,18 @@ function SubscriptionManageRouteComponent() {
|
||||
<Switch
|
||||
checked={enabled}
|
||||
onCheckedChange={(enabled) =>
|
||||
handleUpdateRecord(row)({ enabled: enabled })
|
||||
updateSubscription({
|
||||
variables: {
|
||||
data: {
|
||||
enabled,
|
||||
},
|
||||
filters: {
|
||||
id: {
|
||||
eq: row.original.id,
|
||||
},
|
||||
},
|
||||
},
|
||||
})
|
||||
}
|
||||
/>
|
||||
</div>
|
||||
@ -242,7 +225,11 @@ function SubscriptionManageRouteComponent() {
|
||||
params: { id: `${row.original.id}` },
|
||||
});
|
||||
}}
|
||||
onDelete={handleDeleteRecord(row)}
|
||||
onDelete={() =>
|
||||
deleteSubscription({
|
||||
variables: { filters: { id: { eq: row.original.id } } },
|
||||
})
|
||||
}
|
||||
>
|
||||
<Dialog>
|
||||
<DialogTrigger asChild>
|
||||
@ -257,7 +244,7 @@ function SubscriptionManageRouteComponent() {
|
||||
},
|
||||
];
|
||||
return cs;
|
||||
}, [handleUpdateRecord, handleDeleteRecord, navigate]);
|
||||
}, [updateSubscription, deleteSubscription, navigate]);
|
||||
|
||||
const table = useReactTable({
|
||||
data: useMemo(() => subscriptions?.nodes ?? [], [subscriptions]),
|
||||
|
@ -1,5 +0,0 @@
|
||||
import { memo } from 'react';
|
||||
|
||||
export const TaskActionsView = memo(() => {
|
||||
return null;
|
||||
});
|
@ -12,14 +12,18 @@ import { DetailEmptyView } from '@/components/ui/detail-empty-view';
|
||||
import { Label } from '@/components/ui/label';
|
||||
import { QueryErrorView } from '@/components/ui/query-error-view';
|
||||
import { Separator } from '@/components/ui/separator';
|
||||
import { GET_TASKS } from '@/domains/recorder/schema/tasks';
|
||||
import { GET_TASKS, RETRY_TASKS } from '@/domains/recorder/schema/tasks';
|
||||
import { getApolloQueryError } from '@/infra/errors/apollo';
|
||||
import { apolloErrorToMessage } from '@/infra/errors/apollo';
|
||||
import {
|
||||
type GetTasksQuery,
|
||||
type GetTasksQueryVariables,
|
||||
type RetryTasksMutation,
|
||||
type RetryTasksMutationVariables,
|
||||
SubscriberTaskStatusEnum,
|
||||
} from '@/infra/graphql/gql/graphql';
|
||||
import type { RouteStateDataOption } from '@/infra/routes/traits';
|
||||
import { useQuery } from '@apollo/client';
|
||||
import { useMutation, useQuery } from '@apollo/client';
|
||||
import {
|
||||
createFileRoute,
|
||||
useCanGoBack,
|
||||
@ -28,6 +32,7 @@ import {
|
||||
} from '@tanstack/react-router';
|
||||
import { format } from 'date-fns';
|
||||
import { ArrowLeft, RefreshCw } from 'lucide-react';
|
||||
import { toast } from 'sonner';
|
||||
import { getStatusBadge } from './-status-badge';
|
||||
|
||||
export const Route = createFileRoute('/_app/tasks/detail/$id')({
|
||||
@ -76,6 +81,28 @@ function TaskDetailRouteComponent() {
|
||||
|
||||
const task = data?.subscriberTasks?.nodes?.[0];
|
||||
|
||||
const [retryTasks] = useMutation<
|
||||
RetryTasksMutation,
|
||||
RetryTasksMutationVariables
|
||||
>(RETRY_TASKS, {
|
||||
onCompleted: async () => {
|
||||
const refetchResult = await refetch();
|
||||
const error = getApolloQueryError(refetchResult);
|
||||
if (error) {
|
||||
toast.error('Failed to retry task', {
|
||||
description: apolloErrorToMessage(error),
|
||||
});
|
||||
return;
|
||||
}
|
||||
toast.success('Task retried successfully');
|
||||
},
|
||||
onError: (error) => {
|
||||
toast.error('Failed to retry task', {
|
||||
description: apolloErrorToMessage(error),
|
||||
});
|
||||
},
|
||||
});
|
||||
|
||||
if (loading) {
|
||||
return <DetailCardSkeleton />;
|
||||
}
|
||||
@ -123,6 +150,21 @@ function TaskDetailRouteComponent() {
|
||||
</div>
|
||||
<div className="flex items-center gap-2">
|
||||
{getStatusBadge(task.status)}
|
||||
{task.status ===
|
||||
(SubscriberTaskStatusEnum.Killed ||
|
||||
SubscriberTaskStatusEnum.Failed) && (
|
||||
<Button
|
||||
variant="ghost"
|
||||
size="sm"
|
||||
onClick={() =>
|
||||
retryTasks({
|
||||
variables: { filters: { id: { eq: task.id } } },
|
||||
})
|
||||
}
|
||||
>
|
||||
Retry
|
||||
</Button>
|
||||
)}
|
||||
</div>
|
||||
</div>
|
||||
</CardHeader>
|
||||
|
@ -5,14 +5,23 @@ import { DetailEmptyView } from '@/components/ui/detail-empty-view';
|
||||
import { DropdownMenuActions } from '@/components/ui/dropdown-menu-actions';
|
||||
import { QueryErrorView } from '@/components/ui/query-error-view';
|
||||
import { Skeleton } from '@/components/ui/skeleton';
|
||||
import { GET_TASKS, type TaskDto } from '@/domains/recorder/schema/tasks';
|
||||
import {
|
||||
DELETE_TASKS,
|
||||
GET_TASKS,
|
||||
RETRY_TASKS,
|
||||
type TaskDto,
|
||||
} from '@/domains/recorder/schema/tasks';
|
||||
import {
|
||||
type DeleteTasksMutation,
|
||||
type DeleteTasksMutationVariables,
|
||||
type GetTasksQuery,
|
||||
type RetryTasksMutation,
|
||||
type RetryTasksMutationVariables,
|
||||
SubscriberTaskStatusEnum,
|
||||
} from '@/infra/graphql/gql/graphql';
|
||||
import type { RouteStateDataOption } from '@/infra/routes/traits';
|
||||
import { useDebouncedSkeleton } from '@/presentation/hooks/use-debounded-skeleton';
|
||||
import { useQuery } from '@apollo/client';
|
||||
import { useMutation, useQuery } from '@apollo/client';
|
||||
import { createFileRoute, useNavigate } from '@tanstack/react-router';
|
||||
import {
|
||||
type ColumnDef,
|
||||
@ -26,7 +35,13 @@ import {
|
||||
import { format } from 'date-fns';
|
||||
import { RefreshCw } from 'lucide-react';
|
||||
|
||||
import { DropdownMenuItem } from '@/components/ui/dropdown-menu';
|
||||
import {
|
||||
apolloErrorToMessage,
|
||||
getApolloQueryError,
|
||||
} from '@/infra/errors/apollo';
|
||||
import { useMemo, useState } from 'react';
|
||||
import { toast } from 'sonner';
|
||||
import { getStatusBadge } from './-status-badge';
|
||||
|
||||
export const Route = createFileRoute('/_app/tasks/manage')({
|
||||
@ -70,6 +85,42 @@ function TaskManageRouteComponent() {
|
||||
|
||||
const tasks = data?.subscriberTasks;
|
||||
|
||||
const [deleteTasks] = useMutation<
|
||||
DeleteTasksMutation,
|
||||
DeleteTasksMutationVariables
|
||||
>(DELETE_TASKS, {
|
||||
onCompleted: async () => {
|
||||
const refetchResult = await refetch();
|
||||
const error = getApolloQueryError(refetchResult);
|
||||
if (error) {
|
||||
toast.error('Failed to delete tasks', {
|
||||
description: apolloErrorToMessage(error),
|
||||
});
|
||||
return;
|
||||
}
|
||||
toast.success('Tasks deleted');
|
||||
},
|
||||
onError: (error) => {
|
||||
toast.error('Failed to delete tasks', {
|
||||
description: error.message,
|
||||
});
|
||||
},
|
||||
});
|
||||
|
||||
const [retryTasks] = useMutation<
|
||||
RetryTasksMutation,
|
||||
RetryTasksMutationVariables
|
||||
>(RETRY_TASKS, {
|
||||
onCompleted: () => {
|
||||
toast.success('Tasks retried');
|
||||
},
|
||||
onError: (error) => {
|
||||
toast.error('Failed to retry tasks', {
|
||||
description: error.message,
|
||||
});
|
||||
},
|
||||
});
|
||||
|
||||
const columns = useMemo(() => {
|
||||
const cs: ColumnDef<TaskDto>[] = [
|
||||
{
|
||||
@ -167,7 +218,39 @@ function TaskManageRouteComponent() {
|
||||
params: { id: task.id },
|
||||
});
|
||||
}}
|
||||
/>
|
||||
showDelete
|
||||
onDelete={() =>
|
||||
deleteTasks({
|
||||
variables: {
|
||||
filters: {
|
||||
id: {
|
||||
eq: task.id,
|
||||
},
|
||||
},
|
||||
},
|
||||
})
|
||||
}
|
||||
>
|
||||
{task.status ===
|
||||
(SubscriberTaskStatusEnum.Killed ||
|
||||
SubscriberTaskStatusEnum.Failed) && (
|
||||
<DropdownMenuItem
|
||||
onSelect={() =>
|
||||
retryTasks({
|
||||
variables: {
|
||||
filters: {
|
||||
id: {
|
||||
eq: task.id,
|
||||
},
|
||||
},
|
||||
},
|
||||
})
|
||||
}
|
||||
>
|
||||
Retry
|
||||
</DropdownMenuItem>
|
||||
)}
|
||||
</DropdownMenuActions>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
|
Loading…
Reference in New Issue
Block a user