Repository: vacanza/python-holidays

Issue:
Jersey
Hello,

Would it be possible to add Jersey as a country to Holidays please?

Many thanks


Discussion:
@jjanderson I assume these two are usable sources, right?

https://www.jerseylaw.je/laws/current/Pages/15.560.aspx (Original 1951 Law)
https://www.jerseylaw.je/laws/current/Pages/15.560.20.aspx (Current 2010 Act)

oh wow! Thanks for such a quick response. Yes those look good. Thanks very much
> @jjanderson I assume these two are usable sources, right?
> 
> https://www.jerseylaw.je/laws/current/Pages/15.560.aspx (Original 1951 Law) https://www.jerseylaw.je/laws/current/Pages/15.560.20.aspx (Current 2010 Act)

Hey @PPsyrius, does it mean you're going to take care of this one?
> Hey @PPsyrius, does it mean you're going to take care of this one?

Yes, I have a PR for this being worked on at the moment 



Resolving patch:
diff --git a/holidays/countries/__init__.py b/holidays/countries/__init__.py
--- a/holidays/countries/__init__.py
+++ b/holidays/countries/__init__.py
@@ -81,6 +81,7 @@
 from .italy import Italy, IT, ITA
 from .jamaica import Jamaica, JM, JAM
 from .japan import Japan, JP, JPN
+from .jersey import Jersey, JE, JEY
 from .kazakhstan import Kazakhstan, KZ, KAZ
 from .kenya import Kenya, KE, KEN
 from .kyrgyzstan import Kyrgyzstan, KG, KGZ
diff --git a/holidays/countries/jersey.py b/holidays/countries/jersey.py
new file mode 100644
--- /dev/null
+++ b/holidays/countries/jersey.py
@@ -0,0 +1,234 @@
+#  python-holidays
+#  ---------------
+#  A fast, efficient Python library for generating country, province and state
+#  specific sets of holidays on the fly. It aims to make determining whether a
+#  specific date is a holiday as fast and flexible as possible.
+#
+#  Authors: vacanza team (https://github.com/orgs/vacanza/teams) (c) 2023-2024
+#           dr-prodigy <dr.prodigy.github@gmail.com> (c) 2017-2023
+#           ryanss <ryanssdev@icloud.com> (c) 2014-2017
+#  Website: https://github.com/vacanza/python-holidays
+#  License: MIT (see LICENSE file)
+
+from datetime import date
+from typing import Tuple
+
+from holidays.calendars.gregorian import JAN, APR, MAY, JUN, JUL, SEP, OCT, DEC
+from holidays.groups import ChristianHolidays, InternationalHolidays, StaticHolidays
+from holidays.observed_holiday_base import (
+    ObservedHolidayBase,
+    SAT_SUN_TO_NEXT_WORKDAY,
+    SUN_TO_NEXT_WORKDAY,
+)
+
+
+class Jersey(ObservedHolidayBase, ChristianHolidays, InternationalHolidays, StaticHolidays):
+    """
+    References:
+      - https://en.wikipedia.org/wiki/Public_holidays_in_Jersey
+      - https://www.jerseylaw.je/laws/current/Pages/15.560.20.aspx # 2010 Revision
+      - https://www.jerseylaw.je/laws/superseded/Pages/2006/15.560.20.aspx # 1952 Revision
+      - https://www.jerseylaw.je/laws/enacted/Pages/RO-3038.aspx # 1952 as enacted
+      - https://www.jerseylaw.je/laws/enacted/Pages/Jersey%20RO%205331.aspx # Bank Holidays
+      - https://www.jerseylaw.je/laws/enacted/Pages/Jersey%20RO%206795.aspx # May Day
+    Checked with:
+      - https://www.gov.je/Leisure/Events/WhatsOn/pages/bankholidaydates.aspx # From 2010 onwards
+
+    This has only been cross-checked with the official source from 2010 onwards.
+
+    Jersey has the same public holidays as the United Kingdom (England Subdivision)
+    - plus an extra day on 9 May, to mark Liberation Day (ignoring special holidays
+    like the Corn Riots Anniversary in 2021).
+
+    If a bank holiday is on a sunday, a substitute weekday becomes a bank holiday,
+    normally the following Monday. From 2004 onwards this also applies to saturday.
+    """
+
+    country = "JE"
+    observed_label = "%s (observed)"
+
+    def __init__(self, *args, **kwargs):
+        ChristianHolidays.__init__(self)
+        InternationalHolidays.__init__(self)
+        StaticHolidays.__init__(self, JerseyStaticHolidays)
+        kwargs.setdefault("observed_rule", SAT_SUN_TO_NEXT_WORKDAY)
+        ObservedHolidayBase.__init__(self, *args, **kwargs)
+
+    def _add_observed(self, dt: date, **kwargs) -> Tuple[bool, date]:
+        # Prior to 2004, in-lieu are only given for Sundays.
+        # https://www.jerseylaw.je/laws/enacted/Pages/RO-123-2004.aspx
+        kwargs.setdefault(
+            "rule", SUN_TO_NEXT_WORKDAY if dt < date(2004, OCT, 12) else self._observed_rule
+        )
+        return super()._add_observed(dt, **kwargs)
+
+    def _populate_public_holidays(self) -> None:
+        # Earliest available piece of law available is from 1952.
+        if self._year <= 1951:
+            return None
+
+        # New Year's Day.
+        # Available online source shown that this was celebrated since at least 1952.
+        # Was briefly removed in 1983 only to be added back again before that came to effect.
+
+        # New Year's Day
+        self._add_observed(self._add_new_years_day("New Year's Day"))
+
+        # Good Friday
+        self._add_good_friday("Good Friday")
+
+        # Easter Monday
+        self._add_easter_monday("Easter Monday")
+
+        # May Day
+        # This only starts in 1980 (instead of 1978) for Jersey.
+        # The date is not moved in 2020 (unlike in the UK) as there's already VE Day Celebrations.
+
+        # May Day bank holiday (first Monday in May)
+        if self._year >= 1980:
+            name = "May Day"
+            if self._year == 1995:
+                self._add_holiday_may_8(name)
+            else:
+                self._add_holiday_1st_mon_of_may(name)
+
+        # Spring bank holiday
+        # Current Pattern started in 1970 for Jersey.
+
+        # Spring bank holiday (last Monday in May)
+        if self._year >= 1970:
+            spring_bank_dates = {
+                2002: (JUN, 4),
+                2012: (JUN, 4),
+                2022: (JUN, 2),
+            }
+            name = "Spring Bank Holiday"
+            if self._year in spring_bank_dates:
+                self._add_holiday(name, spring_bank_dates[self._year])
+            else:
+                self._add_holiday_last_mon_of_may(name)
+
+        # Whit Monday.
+        # Was in-use prior to Spring bank holiday adoption.
+
+        if self._year <= 1969:
+            # Whit Monday.
+            self._add_whit_monday("Whit Monday")
+
+        # Late Summer Bank Holiday
+        # Current Pattern started in 1970. Was previously first Monday of September for Jersey.
+
+        # Late Summer bank holiday (last Monday in August)
+        summer_bank_holiday = "Late Summer Bank Holiday"
+        if self._year >= 1970:
+            self._add_holiday_last_mon_of_aug(summer_bank_holiday)
+        else:
+            self._add_holiday_1st_mon_of_sep(summer_bank_holiday)
+
+        # Christmas Day
+        christmas_day = self._add_christmas_day("Christmas Day")
+
+        # Boxing Day
+        boxing_day = self._add_christmas_day_two("Boxing Day")
+
+        self._add_observed(christmas_day)
+        self._add_observed(boxing_day)
+
+        # Jersey exclusive holidays
+
+        # Liberation Day.
+        # Started in 1952. This has no in-lieus.
+        # Counts as Public Holiday when fall on the weekdays, also on Saturday from 2010 onwards.
+        # Specially held in 2010 on Sunday for the 65th Anniversary.
+
+        # Liberation Day
+        liberation_day = self._add_holiday_may_9("Liberation Day")
+        if (self._is_sunday(liberation_day) and self._year != 2010) or (
+            self._is_saturday(liberation_day) and self._year <= 2010
+        ):
+            self.pop(liberation_day)
+
+
+class JE(Jersey):
+    pass
+
+
+class JEY(Jersey):
+    pass
+
+
+class JerseyStaticHolidays:
+    """
+    References:
+      - https://www.gov.je/News/2019/pages/vedaypublicholiday8may.aspx
+      - https://www.gov.je/news/2021/pages/cornriots.aspx
+      - https://www.jerseylaw.je/laws/enacted/Pages/Jersey%20R%20%20O%209288.aspx
+      - https://www.jerseylaw.je/laws/enacted/Pages/Jersey%20R%20%20O%209317.aspx
+      - https://www.jerseylaw.je/laws/enacted/Pages/Jersey%20RO%2042-2001.aspx
+      - https://www.jerseylaw.je/laws/enacted/Pages/Jersey%20RO%206350.aspx
+      - https://www.jerseylaw.je/laws/enacted/Pages/Jersey%20RO%206514.aspx
+      - https://www.jerseylaw.je/laws/enacted/Pages/Jersey%20RO%206924.aspx
+      - https://www.jerseylaw.je/laws/enacted/Pages/Jersey%20RO%207689.aspx
+      - https://www.jerseylaw.je/laws/enacted/Pages/Jersey%20RO%207877.aspx
+      - https://www.jerseylaw.je/laws/enacted/Pages/Jersey%20RO%208451.aspx
+      - https://www.jerseylaw.je/laws/enacted/Pages/Jersey%20RO%208596.aspx
+      - https://www.jerseylaw.je/laws/enacted/Pages/RO-050-2021.aspx
+      - https://www.jerseylaw.je/laws/enacted/Pages/RO-108-2009.aspx
+      - https://www.jerseylaw.je/laws/enacted/Pages/RO-3038.aspx
+    """
+
+    # Mostly a direct copy of UnitedKingdomStaticHolidays.
+
+    # Jersey Specifics:
+    #   - Queen Elizabeth II's Royal Visit (1957, 1978, 1989, 2001)*
+    #        *2004 one falls on existing Liberation Day.
+    #   - 75th VE Day Anniversary (2020)
+    #   - 250th Corn Riots/Code of 1771 Anniversary (2021).
+
+    # Jersey-specific Special Observance
+    #   - New Year's Day (1977, 1983, 1994, 2000)
+    #   - Boxing Day (1976, 1981, 1982, 1987, 1992, 1993, 1994, 1998, 1999, 2009)
+
+    # New Year's Day
+    new_years_day_in_lieu = "New Year's Day"
+
+    # Boxing Day
+    boxing_day_in_lieu = "Boxing Day"
+
+    # Elizabeth II's Royal Visit.
+    elizabeth_2_royal_visit = "Elizabeth II's Royal Visit"
+
+    special_public_holidays = {
+        1957: (JUL, 26, elizabeth_2_royal_visit),
+        1977: (JUN, 7, "Silver Jubilee of Elizabeth II"),
+        1978: (JUN, 27, elizabeth_2_royal_visit),
+        1981: (JUL, 29, "Wedding of Charles and Diana"),
+        1989: (MAY, 25, elizabeth_2_royal_visit),
+        1999: (DEC, 31, "Millennium Celebrations"),
+        2001: (JUL, 13, elizabeth_2_royal_visit),
+        2002: (JUN, 3, "Golden Jubilee of Elizabeth II"),
+        2011: (APR, 29, "Wedding of William and Catherine"),
+        2012: (JUN, 5, "Diamond Jubilee of Elizabeth II"),
+        2020: (MAY, 8, "75th Anniversary of VE Day"),
+        2021: (SEP, 27, "250th Anniversary of the 1769 Corn Riots"),
+        2022: (
+            (JUN, 3, "Platinum Jubilee of Elizabeth II"),
+            (SEP, 19, "State Funeral of Queen Elizabeth II"),
+        ),
+        2023: (MAY, 8, "Coronation of Charles III"),
+    }
+    special_public_holidays_observed = {
+        1976: (DEC, 28, boxing_day_in_lieu),
+        1977: (JAN, 3, new_years_day_in_lieu),
+        1981: (DEC, 28, boxing_day_in_lieu),
+        1982: (DEC, 28, boxing_day_in_lieu),
+        1983: (JAN, 3, new_years_day_in_lieu),
+        1987: (DEC, 28, boxing_day_in_lieu),
+        1992: (DEC, 28, boxing_day_in_lieu),
+        1993: (DEC, 28, boxing_day_in_lieu),
+        1994: (JAN, 3, new_years_day_in_lieu),
+        1998: (DEC, 28, boxing_day_in_lieu),
+        1999: (DEC, 28, boxing_day_in_lieu),
+        2000: (JAN, 3, new_years_day_in_lieu),
+        2009: (DEC, 28, boxing_day_in_lieu),
+    }
diff --git a/holidays/registry.py b/holidays/registry.py
--- a/holidays/registry.py
+++ b/holidays/registry.py
@@ -87,6 +87,7 @@
     "italy": ("Italy", "IT", "ITA"),
     "jamaica": ("Jamaica", "JM", "JAM"),
     "japan": ("Japan", "JP", "JPN"),
+    "jersey": ("Jersey", "JE", "JEY"),
     "kazakhstan": ("Kazakhstan", "KZ", "KAZ"),
     "kenya": ("Kenya", "KE", "KEN"),
     "kyrgyzstan": ("Kyrgyzstan", "KG", "KGZ"),


Test patch:
diff --git a/tests/countries/test_jersey.py b/tests/countries/test_jersey.py
new file mode 100644
--- /dev/null
+++ b/tests/countries/test_jersey.py
@@ -0,0 +1,341 @@
+#  python-holidays
+#  ---------------
+#  A fast, efficient Python library for generating country, province and state
+#  specific sets of holidays on the fly. It aims to make determining whether a
+#  specific date is a holiday as fast and flexible as possible.
+#
+#  Authors: vacanza team (https://github.com/orgs/vacanza/teams) (c) 2023-2024
+#           dr-prodigy <dr.prodigy.github@gmail.com> (c) 2017-2023
+#           ryanss <ryanssdev@icloud.com> (c) 2014-2017
+#  Website: https://github.com/vacanza/python-holidays
+#  License: MIT (see LICENSE file)
+
+from unittest import TestCase
+
+from holidays.countries.jersey import Jersey, JE, JEY
+from tests.common import CommonCountryTests
+
+
+class TestJE(CommonCountryTests, TestCase):
+    @classmethod
+    def setUpClass(cls):
+        super().setUpClass(Jersey, years=range(1952, 2070))
+
+    def test_country_aliases(self):
+        self.assertAliases(Jersey, JE, JEY)
+
+    def test_no_holidays(self):
+        self.assertNoHolidays(Jersey(years=1951))
+
+    def test_special_holidays(self):
+        dt = (
+            "1957-07-26",
+            "1977-06-07",
+            "1978-06-27",
+            "1981-07-29",
+            "1989-05-25",
+            "1999-12-31",
+            "2001-07-13",
+            "2002-06-03",
+            "2011-04-29",
+            "2012-06-05",
+            "2020-05-04",
+            "2020-05-08",
+            "2021-09-27",
+            "2022-06-03",
+            "2022-09-19",
+            "2023-05-08",
+        )
+        dt_observed = (
+            "1976-12-28",
+            "1977-01-03",
+            "1981-12-28",
+            "1982-12-28",
+            "1983-01-03",
+            "1987-12-28",
+            "1992-12-28",
+            "1993-12-28",
+            "1994-01-03",
+            "1998-12-28",
+            "1999-12-28",
+            "2000-01-03",
+            "2009-12-28",
+        )
+        self.assertHoliday(dt, dt_observed)
+        self.assertNoNonObservedHoliday(dt_observed)
+
+    def test_liberation_day(self):
+        name = "Liberation Day"
+        non_obs_date = (
+            # Sunday, May 9th list 1952-2050 excl. 2010 (65th Anniversary)
+            "1954-05-09",
+            "1965-05-09",  # 20th Anniversary special? need to check
+            "1971-05-09",
+            "1976-05-09",
+            "1982-05-09",
+            "1993-05-09",
+            "1999-05-09",
+            "2004-05-09",
+            "2021-05-09",
+            "2027-05-09",
+            "2032-05-09",
+            "2038-05-09",
+            "2049-05-09",
+            # Saturday, May 9th list 1952-2010
+            "1953-05-09",
+            "1959-05-09",
+            "1964-05-09",
+            "1970-05-09",  # 25th Anniversary special? need to check
+            "1981-05-09",
+            "1987-05-09",
+            "1992-05-09",
+            "1998-05-09",
+            "2009-05-09",
+        )
+        self.assertNoHolidayName(name, non_obs_date)
+        self.assertHolidayName(name, range(2010, 2021))
+
+    def test_2010(self):
+        # Wayback Machine of https://www.gov.je/Leisure/Events/WhatsOn/Pages/BankHolidayDates.aspx
+        self.assertHolidays(
+            Jersey(years=2010),
+            ("2010-01-01", "New Year's Day"),
+            ("2010-04-02", "Good Friday"),
+            ("2010-04-05", "Easter Monday"),
+            ("2010-05-03", "May Day"),
+            ("2010-05-09", "Liberation Day"),
+            ("2010-05-31", "Spring Bank Holiday"),
+            ("2010-08-30", "Late Summer Bank Holiday"),
+            ("2010-12-25", "Christmas Day"),
+            ("2010-12-26", "Boxing Day"),
+            ("2010-12-27", "Christmas Day (observed)"),
+            ("2010-12-28", "Boxing Day (observed)"),
+        )
+
+    def test_2011(self):
+        # Wayback Machine of https://www.gov.je/Leisure/Events/WhatsOn/Pages/BankHolidayDates.aspx
+        self.assertHolidays(
+            Jersey(years=2011),
+            ("2011-01-01", "New Year's Day"),
+            ("2011-01-03", "New Year's Day (observed)"),
+            ("2011-04-22", "Good Friday"),
+            ("2011-04-25", "Easter Monday"),
+            ("2011-04-29", "Wedding of William and Catherine"),
+            ("2011-05-02", "May Day"),
+            ("2011-05-09", "Liberation Day"),
+            ("2011-05-30", "Spring Bank Holiday"),
+            ("2011-08-29", "Late Summer Bank Holiday"),
+            ("2011-12-25", "Christmas Day"),
+            ("2011-12-26", "Boxing Day"),
+            ("2011-12-27", "Christmas Day (observed)"),
+        )
+
+    def test_2012(self):
+        # Wayback Machine of https://www.gov.je/Leisure/Events/WhatsOn/Pages/BankHolidayDates.aspx
+        self.assertHolidays(
+            Jersey(years=2012),
+            ("2012-01-01", "New Year's Day"),
+            ("2012-01-02", "New Year's Day (observed)"),
+            ("2012-04-06", "Good Friday"),
+            ("2012-04-09", "Easter Monday"),
+            ("2012-05-07", "May Day"),
+            ("2012-05-09", "Liberation Day"),
+            ("2012-06-04", "Spring Bank Holiday"),
+            ("2012-06-05", "Diamond Jubilee of Elizabeth II"),
+            ("2012-08-27", "Late Summer Bank Holiday"),
+            ("2012-12-25", "Christmas Day"),
+            ("2012-12-26", "Boxing Day"),
+        )
+
+    def test_2013(self):
+        # Wayback Machine of https://www.gov.je/Leisure/Events/WhatsOn/Pages/BankHolidayDates.aspx
+        self.assertHolidays(
+            Jersey(years=2013),
+            ("2013-01-01", "New Year's Day"),
+            ("2013-03-29", "Good Friday"),
+            ("2013-04-01", "Easter Monday"),
+            ("2013-05-06", "May Day"),
+            ("2013-05-09", "Liberation Day"),
+            ("2013-05-27", "Spring Bank Holiday"),
+            ("2013-08-26", "Late Summer Bank Holiday"),
+            ("2013-12-25", "Christmas Day"),
+            ("2013-12-26", "Boxing Day"),
+        )
+
+    def test_2014(self):
+        # Wayback Machine of https://www.gov.je/Leisure/Events/WhatsOn/Pages/BankHolidayDates.aspx
+        self.assertHolidays(
+            Jersey(years=2014),
+            ("2014-01-01", "New Year's Day"),
+            ("2014-04-18", "Good Friday"),
+            ("2014-04-21", "Easter Monday"),
+            ("2014-05-05", "May Day"),
+            ("2014-05-09", "Liberation Day"),
+            ("2014-05-26", "Spring Bank Holiday"),
+            ("2014-08-25", "Late Summer Bank Holiday"),
+            ("2014-12-25", "Christmas Day"),
+            ("2014-12-26", "Boxing Day"),
+        )
+
+    def test_2015(self):
+        # Wayback Machine of https://www.gov.je/Leisure/Events/WhatsOn/Pages/BankHolidayDates.aspx
+        self.assertHolidays(
+            Jersey(years=2015),
+            ("2015-01-01", "New Year's Day"),
+            ("2015-04-03", "Good Friday"),
+            ("2015-04-06", "Easter Monday"),
+            ("2015-05-04", "May Day"),
+            ("2015-05-09", "Liberation Day"),
+            ("2015-05-25", "Spring Bank Holiday"),
+            ("2015-08-31", "Late Summer Bank Holiday"),
+            ("2015-12-25", "Christmas Day"),
+            ("2015-12-26", "Boxing Day"),
+            ("2015-12-28", "Boxing Day (observed)"),
+        )
+
+    def test_2016(self):
+        # Wayback Machine of https://www.gov.je/Leisure/Events/WhatsOn/Pages/BankHolidayDates.aspx
+        self.assertHolidays(
+            Jersey(years=2016),
+            ("2016-01-01", "New Year's Day"),
+            ("2016-03-25", "Good Friday"),
+            ("2016-03-28", "Easter Monday"),
+            ("2016-05-02", "May Day"),
+            ("2016-05-09", "Liberation Day"),
+            ("2016-05-30", "Spring Bank Holiday"),
+            ("2016-08-29", "Late Summer Bank Holiday"),
+            ("2016-12-25", "Christmas Day"),
+            ("2016-12-26", "Boxing Day"),
+            ("2016-12-27", "Christmas Day (observed)"),
+        )
+
+    def test_2017(self):
+        # Wayback Machine of https://www.gov.je/Leisure/Events/WhatsOn/Pages/BankHolidayDates.aspx
+        self.assertHolidays(
+            Jersey(years=2017),
+            ("2017-01-01", "New Year's Day"),
+            ("2017-01-02", "New Year's Day (observed)"),
+            ("2017-04-14", "Good Friday"),
+            ("2017-04-17", "Easter Monday"),
+            ("2017-05-01", "May Day"),
+            ("2017-05-09", "Liberation Day"),
+            ("2017-05-29", "Spring Bank Holiday"),
+            ("2017-08-28", "Late Summer Bank Holiday"),
+            ("2017-12-25", "Christmas Day"),
+            ("2017-12-26", "Boxing Day"),
+        )
+
+    def test_2018(self):
+        # Wayback Machine of https://www.gov.je/Leisure/Events/WhatsOn/Pages/BankHolidayDates.aspx
+        self.assertHolidays(
+            Jersey(years=2018),
+            ("2018-01-01", "New Year's Day"),
+            ("2018-03-30", "Good Friday"),
+            ("2018-04-02", "Easter Monday"),
+            ("2018-05-07", "May Day"),
+            ("2018-05-09", "Liberation Day"),
+            ("2018-05-28", "Spring Bank Holiday"),
+            ("2018-08-27", "Late Summer Bank Holiday"),
+            ("2018-12-25", "Christmas Day"),
+            ("2018-12-26", "Boxing Day"),
+        )
+
+    def test_2019(self):
+        # Wayback Machine of https://www.gov.je/Leisure/Events/WhatsOn/Pages/BankHolidayDates.aspx
+        self.assertHolidays(
+            Jersey(years=2019),
+            ("2019-01-01", "New Year's Day"),
+            ("2019-04-19", "Good Friday"),
+            ("2019-04-22", "Easter Monday"),
+            ("2019-05-06", "May Day"),
+            ("2019-05-09", "Liberation Day"),
+            ("2019-05-27", "Spring Bank Holiday"),
+            ("2019-08-26", "Late Summer Bank Holiday"),
+            ("2019-12-25", "Christmas Day"),
+            ("2019-12-26", "Boxing Day"),
+        )
+
+    def test_2020(self):
+        # Wayback Machine of https://www.gov.je/Leisure/Events/WhatsOn/Pages/BankHolidayDates.aspx
+        self.assertHolidays(
+            Jersey(years=2020),
+            ("2020-01-01", "New Year's Day"),
+            ("2020-04-10", "Good Friday"),
+            ("2020-04-13", "Easter Monday"),
+            ("2020-05-04", "May Day"),
+            ("2020-05-08", "75th Anniversary of VE Day"),
+            ("2020-05-09", "Liberation Day"),
+            ("2020-05-25", "Spring Bank Holiday"),
+            ("2020-08-31", "Late Summer Bank Holiday"),
+            ("2020-12-25", "Christmas Day"),
+            ("2020-12-26", "Boxing Day"),
+            ("2020-12-28", "Boxing Day (observed)"),
+        )
+
+    def test_2021(self):
+        # Wayback Machine of https://www.gov.je/Leisure/Events/WhatsOn/Pages/BankHolidayDates.aspx
+        self.assertHolidays(
+            Jersey(years=2021),
+            ("2021-01-01", "New Year's Day"),
+            ("2021-04-02", "Good Friday"),
+            ("2021-04-05", "Easter Monday"),
+            ("2021-05-03", "May Day"),
+            ("2021-05-31", "Spring Bank Holiday"),
+            ("2021-08-30", "Late Summer Bank Holiday"),
+            ("2021-09-27", "250th Anniversary of the 1769 Corn Riots"),
+            ("2021-12-25", "Christmas Day"),
+            ("2021-12-26", "Boxing Day"),
+            ("2021-12-27", "Christmas Day (observed)"),
+            ("2021-12-28", "Boxing Day (observed)"),
+        )
+
+    def test_2022(self):
+        # Wayback Machine of https://www.gov.je/Leisure/Events/WhatsOn/Pages/BankHolidayDates.aspx
+        self.assertHolidays(
+            Jersey(years=2022),
+            ("2022-01-01", "New Year's Day"),
+            ("2022-01-03", "New Year's Day (observed)"),
+            ("2022-04-15", "Good Friday"),
+            ("2022-04-18", "Easter Monday"),
+            ("2022-05-02", "May Day"),
+            ("2022-05-09", "Liberation Day"),
+            ("2022-06-02", "Spring Bank Holiday"),
+            ("2022-06-03", "Platinum Jubilee of Elizabeth II"),
+            ("2022-08-29", "Late Summer Bank Holiday"),
+            ("2022-09-19", "State Funeral of Queen Elizabeth II"),
+            ("2022-12-25", "Christmas Day"),
+            ("2022-12-26", "Boxing Day"),
+            ("2022-12-27", "Christmas Day (observed)"),
+        )
+
+    def test_2023(self):
+        # https://www.gov.je/Leisure/Events/WhatsOn/Pages/BankHolidayDates.aspx
+        self.assertHolidays(
+            Jersey(years=2023),
+            ("2023-01-01", "New Year's Day"),
+            ("2023-01-02", "New Year's Day (observed)"),
+            ("2023-04-07", "Good Friday"),
+            ("2023-04-10", "Easter Monday"),
+            ("2023-05-01", "May Day"),
+            ("2023-05-08", "Coronation of Charles III"),
+            ("2023-05-09", "Liberation Day"),
+            ("2023-05-29", "Spring Bank Holiday"),
+            ("2023-08-28", "Late Summer Bank Holiday"),
+            ("2023-12-25", "Christmas Day"),
+            ("2023-12-26", "Boxing Day"),
+        )
+
+    def test_2024(self):
+        # https://www.gov.je/Leisure/Events/WhatsOn/Pages/BankHolidayDates.aspx
+        self.assertHolidays(
+            Jersey(years=2024),
+            ("2024-01-01", "New Year's Day"),
+            ("2024-03-29", "Good Friday"),
+            ("2024-04-01", "Easter Monday"),
+            ("2024-05-06", "May Day"),
+            ("2024-05-09", "Liberation Day"),
+            ("2024-05-27", "Spring Bank Holiday"),
+            ("2024-08-26", "Late Summer Bank Holiday"),
+            ("2024-12-25", "Christmas Day"),
+            ("2024-12-26", "Boxing Day"),
+        )