holidays 0.3.0.2 → 0.4.0.0
raw patch · 13 files changed
+145/−82 lines, 13 filesPVP ok
version bump matches the API change (PVP)
API changes (from Hackage documentation)
- Holidays: type ISO_3166_1_Alpha_3 = Text
- Holidays: type Region = Text
+ Holidays: BB :: GermanRegion
+ Holidays: BE :: GermanRegion
+ Holidays: BW :: GermanRegion
+ Holidays: BY :: GermanRegion
+ Holidays: DEU :: Set GermanRegion -> ISO_3166_1_Alpha_3
+ Holidays: GBR :: ISO_3166_1_Alpha_3
+ Holidays: HB :: GermanRegion
+ Holidays: HE :: GermanRegion
+ Holidays: HH :: GermanRegion
+ Holidays: ISR :: ISO_3166_1_Alpha_3
+ Holidays: MOZ :: ISO_3166_1_Alpha_3
+ Holidays: MV :: GermanRegion
+ Holidays: NAM :: ISO_3166_1_Alpha_3
+ Holidays: NI :: GermanRegion
+ Holidays: NW :: GermanRegion
+ Holidays: RP :: GermanRegion
+ Holidays: SH :: GermanRegion
+ Holidays: SL :: GermanRegion
+ Holidays: SN :: GermanRegion
+ Holidays: ST :: GermanRegion
+ Holidays: TH :: GermanRegion
+ Holidays: USA :: ISO_3166_1_Alpha_3
+ Holidays: ZAF :: ISO_3166_1_Alpha_3
+ Holidays: data GermanRegion
+ Holidays: data ISO_3166_1_Alpha_3
+ Holidays: instance GHC.Show.Show Holidays.ISO_3166_1_Alpha_3
+ Holidays: mkCountryCode :: Text -> [Text] -> Maybe ISO_3166_1_Alpha_3
- Holidays: holidays :: ISO_3166_1_Alpha_3 -> [Region] -> Year -> Set Holiday
+ Holidays: holidays :: ISO_3166_1_Alpha_3 -> Year -> Set Holiday
Files
- CHANGELOG.md +3/−0
- holidays.cabal +1/−1
- src/Holidays.hs +46/−21
- src/Holidays/Base.hs +0/−8
- src/Holidays/Germany.hs +73/−19
- tst/Test/Holidays.hs +3/−3
- tst/Test/Holidays/Germany.hs +4/−4
- tst/Test/Holidays/Israel.hs +2/−2
- tst/Test/Holidays/Mozambique.hs +2/−13
- tst/Test/Holidays/Namibia.hs +3/−3
- tst/Test/Holidays/SouthAfrica.hs +3/−3
- tst/Test/Holidays/UnitedKingdom.hs +3/−3
- tst/Test/Holidays/UnitedStates.hs +2/−2
CHANGELOG.md view
@@ -19,3 +19,6 @@ ## **0.3.0.2** - 2026-05-07 - new country supported: ISR++## **0.4.0.0** - 2026-06-04+- use ADT's for country codes and regions
holidays.cabal view
@@ -1,6 +1,6 @@ cabal-version: 3.0 name: holidays-version: 0.3.0.2+version: 0.4.0.0 synopsis: Library for country public holidays description: Public holidays with Haskell.
src/Holidays.hs view
@@ -2,26 +2,52 @@ This module determines public holidays based on country code and year. -} module Holidays (- ISO_3166_1_Alpha_3,- Region,+ ISO_3166_1_Alpha_3 (..),+ Germany.GermanRegion (..), holidays, hday, Holiday (..),+ mkCountryCode, ) where import qualified Data.Set as S+import qualified Data.Text as T import Data.Time import Holidays.Base import Holidays.DateTransform-import qualified Holidays.Germany as DEU-import qualified Holidays.Israel as ISR-import qualified Holidays.Mozambique as MOZ-import qualified Holidays.Namibia as NAM-import qualified Holidays.SouthAfrica as ZAF-import qualified Holidays.UnitedKingdom as GBR-import qualified Holidays.UnitedStates as USA+import qualified Holidays.Germany as Germany+import qualified Holidays.Israel as Israel+import qualified Holidays.Mozambique as Mozambique+import qualified Holidays.Namibia as Namibia+import qualified Holidays.SouthAfrica as SouthAfrica+import qualified Holidays.UnitedKingdom as UnitedKingdom+import qualified Holidays.UnitedStates as UnitedStates +-- | 3-letter country codes.+data ISO_3166_1_Alpha_3+ = DEU (S.Set Germany.GermanRegion)+ | GBR+ | ISR+ | MOZ+ | NAM+ | USA+ | ZAF+ deriving (Show)++-- | Constructor for country code.+mkCountryCode :: T.Text -> [T.Text] -> Maybe ISO_3166_1_Alpha_3+mkCountryCode t regions =+ case t of+ "DEU" -> Just (DEU (Germany.mkGermanRegions regions))+ "GBR" -> Just GBR+ "ISR" -> Just ISR+ "MOZ" -> Just MOZ+ "NAM" -> Just NAM+ "USA" -> Just USA+ "ZAF" -> Just ZAF+ _ -> Nothing+ {- | Returns a set of public holidays based on the country code (ISO_3166_1_Alpha_3) and a specific year. If a country is not supported an empty set is returned.@@ -30,21 +56,20 @@ Examples: @-holidays \"DEU\" [\"BW\",\"BY\",\"BE\"] 2025 -- Germany and various regions-holidays \"USA\" [] 2025+holidays DEU (S.fromList [BW, BY ,BE]) 2025 -- Germany and various regions+holidays USA 2025 @ -}-holidays :: ISO_3166_1_Alpha_3 -> [Region] -> Year -> S.Set Holiday-holidays countryCode regions year =+holidays :: ISO_3166_1_Alpha_3 -> Year -> S.Set Holiday+holidays countryCode year = case countryCode of- "DEU" -> DEU.holidays regions `apply` year- "GBR" -> GBR.holidays `apply` year- "ISR" -> S.union (ISR.holidays `apply` year) (ISR.sabbaths year)- "MOZ" -> MOZ.holidays `apply` year- "NAM" -> NAM.holidays `apply` year- "USA" -> USA.holidays `apply` year- "ZAF" -> ZAF.holidays `apply` year- _ -> S.empty+ (DEU regions) -> Germany.holidays regions `apply` year+ GBR -> UnitedKingdom.holidays `apply` year+ ISR -> S.union (Israel.holidays `apply` year) (Israel.sabbaths year)+ MOZ -> Mozambique.holidays `apply` year+ NAM -> Namibia.holidays `apply` year+ USA -> UnitedStates.holidays `apply` year+ ZAF -> SouthAfrica.holidays `apply` year -- | Applies year and date transformations to holidays apply :: ([Year -> Holiday], [DateTransform]) -> Year -> S.Set Holiday
src/Holidays/Base.hs view
@@ -1,7 +1,5 @@ module Holidays.Base ( Holiday (..),- ISO_3166_1_Alpha_3,- Region, day, hday, nullDay,@@ -10,12 +8,6 @@ import qualified Data.Text as T import Data.Time---- | 3-letter country codes.-type ISO_3166_1_Alpha_3 = T.Text---- | Custom regions for a country.-type Region = T.Text data Holiday = Holiday
src/Holidays/Germany.hs view
@@ -4,16 +4,71 @@ https://publicholidays.de/ --} module Holidays.Germany (+ GermanRegion (..), holidays,+ mkGermanRegions, ) where +import Data.Maybe+import qualified Data.Set as S+import qualified Data.Text as T import Data.Time import Holidays.Base import Holidays.DateFinder import Holidays.DateTransform -holidays :: [Region] -> ([Year -> Holiday], [DateTransform])+-- | 2-letter german region.+data GermanRegion+ = BW+ | BY+ | BE+ | BB+ | HB+ | HH+ | HE+ | MV+ | NI+ | NW+ | RP+ | SL+ | SN+ | ST+ | SH+ | TH+ deriving (Eq, Ord, Show)++mkGermanRegions :: [T.Text] -> S.Set GermanRegion+mkGermanRegions ts =+ foldr+ ( \r acc ->+ let gr = mkRegion r in if isJust gr then S.insert (fromJust gr) acc else acc+ )+ S.empty+ ts++mkRegion :: T.Text -> Maybe GermanRegion+mkRegion t =+ case t of+ "BW" -> Just BW+ "BY" -> Just BY+ "BE" -> Just BE+ "BB" -> Just BB+ "HB" -> Just HB+ "HH" -> Just HH+ "HE" -> Just HE+ "MV" -> Just MV+ "NI" -> Just NI+ "NW" -> Just NW+ "RP" -> Just RP+ "SL" -> Just SL+ "SN" -> Just SN+ "ST" -> Just ST+ "SH" -> Just SH+ "TH" -> Just TH+ _ -> Nothing++holidays :: S.Set GermanRegion -> ([Year -> Holiday], [DateTransform]) holidays regions = ( concat [ federalHolidays,@@ -35,27 +90,26 @@ hday "second_day_of_christmas" . boxingDay ] -regionalHolidays :: [Region] -> [Year -> Holiday]+regionalHolidays :: S.Set GermanRegion -> [Year -> Holiday] regionalHolidays = concatMap ( \r -> case r of- "BW" -> badenWurttembergHolidays- "BY" -> bavariaHolidays- "BE" -> berlinHolidays- "BB" -> brandenburgHolidays- "HB" -> bremenHolidays- "HH" -> hamburgHolidays- "HE" -> hesseHolidays- "MV" -> mecklenburgVorpommernHolidays- "NI" -> lowerSaxonyHolidays- "NW" -> northRhineWestphaliaHolidays- "RP" -> rhinelandPalatinateHolidays- "SL" -> saarlandHolidays- "SN" -> saxonyHolidays- "ST" -> saxonyAnhaltHolidays- "SH" -> schleswigHolsteinHolidays- "TH" -> thuringiaHolidays- _ -> []+ BW -> badenWurttembergHolidays+ BY -> bavariaHolidays+ BE -> berlinHolidays+ BB -> brandenburgHolidays+ HB -> bremenHolidays+ HH -> hamburgHolidays+ HE -> hesseHolidays+ MV -> mecklenburgVorpommernHolidays+ NI -> lowerSaxonyHolidays+ NW -> northRhineWestphaliaHolidays+ RP -> rhinelandPalatinateHolidays+ SL -> saarlandHolidays+ SN -> saxonyHolidays+ ST -> saxonyAnhaltHolidays+ SH -> schleswigHolsteinHolidays+ TH -> thuringiaHolidays ) -- common holidays
tst/Test/Holidays.hs view
@@ -12,8 +12,8 @@ day :: Year -> MonthOfYear -> DayOfMonth -> Day day = fromGregorian -countryPropTests :: H.ISO_3166_1_Alpha_3 -> [H.Region] -> TestTree-countryPropTests countryCode regions =+countryPropTests :: H.ISO_3166_1_Alpha_3 -> TestTree+countryPropTests countryCode = let uniqueYears c y = S.map ( \h ->@@ -22,7 +22,7 @@ in year' )- (H.holidays c regions y)+ (H.holidays c y) in testGroup ("Holidays property based tests for country " <> show countryCode) [ QC.testProperty "Day always in the same year" $
tst/Test/Holidays/Germany.hs view
@@ -11,15 +11,15 @@ import Test.Tasty.HUnit -- german states-regions :: [Region]-regions = ["BW", "BY", "BE", "BB", "HB", "HH", "HE", "MV", "NI", "NW", "RP", "SL", "SN", "ST", "SH", "TH"]+regions :: S.Set GermanRegion+regions = S.fromList [BW, BY, BE, BB, HB, HH, HE, MV, NI, NW, RP, SL, SN, ST, SH, TH] unitTests :: TestTree unitTests = testGroup "DEU unit tests" [ testCase "2025" $- sortOn holidayValue (S.toAscList (holidays "DEU" regions 2025))+ sortOn holidayValue (S.toAscList (holidays (DEU regions) 2025)) @?= [ hday "new_years_day" (day 2025 1 1), hday "epiphany" (day 2025 1 6), hday "international_womens_day" (day 2025 3 8),@@ -44,4 +44,4 @@ ] propTests :: TestTree-propTests = countryPropTests "DEU" regions+propTests = countryPropTests (DEU regions)
tst/Test/Holidays/Israel.hs view
@@ -20,7 +20,7 @@ testGroup "ISR unit tests" [ testCase "2024" $- sortOn holidayValue (excludeSabbaths (S.toAscList (holidays "ISR" [] 2024)))+ sortOn holidayValue (excludeSabbaths (S.toAscList (holidays ISR 2024))) @?= [ hday "passover" (day 2024 4 23), hday "seventh_day_of_passover" (day 2024 4 29), hday "independence_day" (day 2024 5 13),@@ -35,7 +35,7 @@ ] propTests :: TestTree-propTests = countryPropTests "ISR" []+propTests = countryPropTests ISR excludeSabbaths :: [Holiday] -> [Holiday] excludeSabbaths hs = filter (not . T.isPrefixOf "sabbath_" . holidayKey) hs
tst/Test/Holidays/Mozambique.hs view
@@ -15,7 +15,7 @@ testGroup "MOZ unit tests" [ testCase "2025" $- sortOn holidayValue (S.toList (holidays "MOZ" [] 2025))+ sortOn holidayValue (S.toList (holidays MOZ 2025)) @?= [ hday "new_years_day" (day 2025 1 1), hday "heroes_day" (day 2025 2 3), hday "womens_day" (day 2025 4 7),@@ -29,15 +29,4 @@ ] propTests :: TestTree-propTests = countryPropTests "MOZ" []--{-- ( [ hday "new_years_day" . newYearsDay,- hday "heroes_day" . feb 3,- hday "womens_day" . apr 7,- hday "workers_day" . workersDay,- hday "independence_day" . jun 25,- hday "victory_day" . sep 7,- hday "armed_forces_day" . sep 25,- hday "day_of_peace_and_reconciliation" . oct 4,- hday "family_day" . christmasDay -}+propTests = countryPropTests MOZ
tst/Test/Holidays/Namibia.hs view
@@ -15,7 +15,7 @@ testGroup "NAM unit tests" [ testCase "2024" $- sortOn holidayValue (S.toAscList (holidays "NAM" [] 2024))+ sortOn holidayValue (S.toAscList (holidays NAM 2024)) @?= [ hday "new_years_day" (day 2024 1 1), hday "independence_day" (day 2024 3 21), hday "good_friday" (day 2024 3 29),@@ -30,7 +30,7 @@ hday "family_day" (day 2024 12 26) ], testCase "2025" $- sortOn holidayValue (S.toAscList (holidays "NAM" [] 2025))+ sortOn holidayValue (S.toAscList (holidays NAM 2025)) @?= [ hday "new_years_day" (day 2025 1 1), hday "independence_day" (day 2025 3 21), hday "good_friday" (day 2025 4 18),@@ -48,4 +48,4 @@ ] propTests :: TestTree-propTests = countryPropTests "NAM" []+propTests = countryPropTests NAM
tst/Test/Holidays/SouthAfrica.hs view
@@ -15,7 +15,7 @@ testGroup "ZAF unit tests" [ testCase "2024" $- sortOn holidayValue (S.toAscList (holidays "ZAF" [] 2024))+ sortOn holidayValue (S.toAscList (holidays ZAF 2024)) @?= [ hday "new_years_day" (day 2024 1 1), hday "human_rights_day" (day 2024 3 21), hday "good_friday" (day 2024 3 29),@@ -31,7 +31,7 @@ hday "day_of_goodwill" (day 2024 12 26) ], testCase "2025" $- sortOn holidayValue (S.toList (holidays "ZAF" [] 2025))+ sortOn holidayValue (S.toList (holidays ZAF 2025)) @?= [ hday "new_years_day" (day 2025 1 1), hday "human_rights_day" (day 2025 3 21), hday "good_friday" (day 2025 4 18),@@ -48,4 +48,4 @@ ] propTests :: TestTree-propTests = countryPropTests "ZAF" []+propTests = countryPropTests ZAF
tst/Test/Holidays/UnitedKingdom.hs view
@@ -15,7 +15,7 @@ testGroup "GBR unit tests" [ testCase "2025" $- sortOn holidayValue (S.toList (holidays "GBR" [] 2025))+ sortOn holidayValue (S.toList (holidays GBR 2025)) @?= [ hday "new_years_day" (day 2025 1 1), hday "good_friday" (day 2025 4 18), hday "easter_sunday" (day 2025 4 21),@@ -26,7 +26,7 @@ hday "boxing_day" (day 2025 12 26) ], testCase "2026" $- sortOn holidayValue (S.toList (holidays "GBR" [] 2026))+ sortOn holidayValue (S.toList (holidays GBR 2026)) @?= [ hday "new_years_day" (day 2026 1 1), hday "good_friday" (day 2026 4 3), hday "easter_sunday" (day 2026 4 6),@@ -39,4 +39,4 @@ ] propTests :: TestTree-propTests = countryPropTests "GBR" []+propTests = countryPropTests GBR
tst/Test/Holidays/UnitedStates.hs view
@@ -15,7 +15,7 @@ testGroup "USA unit tests" [ testCase "2025" $- sortOn holidayValue (S.toAscList (holidays "USA" [] 2025))+ sortOn holidayValue (S.toAscList (holidays USA 2025)) @?= [ hday "new_years_day" (day 2025 1 1), hday "martin_luther_kings_birthday" (day 2025 1 20), hday "george_washingtons_birthday" (day 2025 2 17),@@ -31,4 +31,4 @@ ] propTests :: TestTree-propTests = countryPropTests "USA" []+propTests = countryPropTests USA