Skip to main content

ironflow_api/entities/
schedule.rs

1//! Schedule request and response DTOs.
2
3use chrono::{DateTime, Utc};
4use serde::{Deserialize, Serialize};
5use serde_json::Value;
6use uuid::Uuid;
7use validator::Validate;
8
9use ironflow_store::entities::{Schedule, ScheduleSource};
10
11/// Schedule list/detail response.
12#[cfg_attr(feature = "openapi", derive(utoipa::ToSchema))]
13#[derive(Debug, Serialize)]
14pub struct ScheduleResponse {
15    /// Schedule ID.
16    pub id: Uuid,
17    /// Name of the workflow to trigger.
18    pub workflow_name: String,
19    /// Cron expression.
20    pub cron_expression: String,
21    /// JSON payload passed to the workflow.
22    pub inputs: Value,
23    /// Where this schedule was created (`handler` or `api`).
24    pub source: ScheduleSource,
25    /// When the schedule was disabled. `None` means active.
26    pub disabled_at: Option<DateTime<Utc>>,
27    /// When the schedule last created a run.
28    pub last_triggered_at: Option<DateTime<Utc>>,
29    /// When the schedule will next fire.
30    pub next_trigger_at: Option<DateTime<Utc>>,
31    /// User who created the schedule.
32    pub created_by_user_id: Uuid,
33    /// When the schedule was created.
34    pub created_at: DateTime<Utc>,
35    /// When the schedule was last updated.
36    pub updated_at: DateTime<Utc>,
37}
38
39impl From<Schedule> for ScheduleResponse {
40    fn from(s: Schedule) -> Self {
41        Self {
42            id: s.id,
43            workflow_name: s.workflow_name,
44            cron_expression: s.cron_expression,
45            inputs: s.inputs,
46            source: s.source,
47            disabled_at: s.disabled_at,
48            last_triggered_at: s.last_triggered_at,
49            next_trigger_at: s.next_trigger_at,
50            created_by_user_id: s.created_by_user_id,
51            created_at: s.created_at,
52            updated_at: s.updated_at,
53        }
54    }
55}
56
57/// Create schedule request body.
58#[cfg_attr(feature = "openapi", derive(utoipa::ToSchema))]
59#[derive(Debug, Deserialize, Validate)]
60pub struct CreateScheduleRequest {
61    /// Name of the workflow to trigger.
62    #[validate(length(min = 1, message = "workflow_name must not be empty"))]
63    pub workflow_name: String,
64    /// Cron expression (6-field format, e.g. `"0 */5 * * * *"`).
65    #[validate(length(min = 1, message = "cron_expression must not be empty"))]
66    pub cron_expression: String,
67    /// JSON payload for the workflow. Defaults to `{}`.
68    #[serde(default = "default_inputs")]
69    pub inputs: Value,
70}
71
72fn default_inputs() -> Value {
73    Value::Object(serde_json::Map::new())
74}
75
76/// Update schedule request body. All fields optional.
77#[cfg_attr(feature = "openapi", derive(utoipa::ToSchema))]
78#[derive(Debug, Deserialize)]
79pub struct UpdateScheduleRequest {
80    /// New cron expression.
81    pub cron_expression: Option<String>,
82    /// New inputs payload.
83    pub inputs: Option<Value>,
84}