1use crate::environment::{parse_environment, Environment};
2use serde::{Deserialize, Serialize};
3use syn::{
4 parse::{Parse, ParseStream},
5 token, Ident, LitStr,
6};
7
8#[derive(Debug, Clone, Serialize, Deserialize)]
9pub struct Cron {
10 pub name: Option<String>,
11 pub schedule: String,
12 pub environment: Environment,
13}
14
15impl Parse for Cron {
16 fn parse(input: ParseStream) -> syn::Result<Self> {
17 let mut name = None;
18 let mut environment = None;
19 let mut schedule = None;
20
21 while !input.is_empty() {
22 let ident_span = input.span();
23 let ident: Ident = input.parse()?;
24 input.parse::<token::Eq>()?;
25
26 match ident.to_string().as_str() {
27 "name" => {
28 if name.is_some() {
29 return Err(syn::Error::new(ident_span, "Duplicate attribute `name`"));
30 }
31 name = Some(input.parse::<LitStr>()?.value());
32 }
33 "environment" => {
34 if environment.is_some() {
35 return Err(syn::Error::new(
36 ident_span,
37 "Duplicate attribute `environment`",
38 ));
39 }
40 environment = Some(parse_environment(input)?);
41 }
42 "schedule" => {
43 if schedule.is_some() {
44 return Err(syn::Error::new(
45 ident_span,
46 "Duplicate attribute `schedule`",
47 ));
48 }
49 schedule = Some(input.parse::<LitStr>()?.value());
50 }
51 _ => {}
53 }
54
55 if !input.is_empty() {
56 input.parse::<token::Comma>()?;
57 }
58 }
59
60 Ok(Cron {
61 name,
62 environment: environment.unwrap_or_default(),
63 schedule: schedule
64 .ok_or_else(|| input.error("Cron validation failed: no schedule provided"))?,
65 })
66 }
67}