-- SPDX-FileCopyrightText: 2022 Gregor Kleen <gregor.kleen@ifi.lmu.de>
--
-- SPDX-License-Identifier: AGPL-3.0-or-later

{-# LANGUAGE NoImplicitPrelude #-}

module CronSpec where

import TestImport

import Cron

import Data.Time
import Data.Time.Clock.System
import Data.Time.Zones

import Data.List (iterate)


baseTime :: UTCTime
baseTime = UTCTime (addDays 58400 systemEpochDay) 50000


sampleCron :: Natural -> Cron -> [UTCTime]
sampleCron n = go n baseTime Nothing
  where
    go 0 _ _ _ = []
    go (pred -> n') t mPrev cron = case nextCronMatch utcTZ mPrev 0 t cron of
      MatchAsap -> t : go n' t (Just t) cron
      MatchAt t' -> t' : go n' t' (Just t') cron
      MatchNone -> []


spec :: Spec
spec = do
  describe "Cron" $ do
    it "generates correct example series" . mapM_ seriesExample $ 
      [ (Cron CronAsap CronRepeatNever 0 (Right CronNotScheduled), [baseTime])
      , (Cron CronAsap (CronRepeatScheduled CronAsap) 10 (Right CronNotScheduled), iterate (addUTCTime 10) baseTime)
      ]

seriesExample :: (Cron, [UTCTime]) -> Expectation
seriesExample (cron, res) = example $ sampleCron 10 cron `shouldBe` take 10 res
