fix(cli): extend holiday tagline dates through 2030

Extend the CLI holiday tagline tables for Lunar New Year, Eid al-Fitr, Easter, Diwali, and Hanukkah through 2030 so those taglines do not silently disappear after 2027.

Maintainer fixup: corrected the 2030 Diwali row to October 25 and added explicit regression coverage for that date.

Verification:
- node scripts/run-vitest.mjs src/cli/tagline.test.ts
- Direct pickTagline() probe confirmed 2030-10-25 activates Diwali and 2030-10-26 does not.

Co-authored-by: alkor2000 <200923177@qq.com>
This commit is contained in:
alkor2000
2026-06-01 00:59:43 +08:00
committed by GitHub
parent 0ee5f47fba
commit 723d09ff85
2 changed files with 64 additions and 0 deletions

View File

@@ -31,3 +31,52 @@ describe("pickTagline", () => {
).toBe("Your terminal just grew claws\u2014type something and let the bot pinch the busywork.");
});
});
describe("future holiday tagline windows (2028-2030)", () => {
// Regression coverage for the 2028-2030 floating-holiday rows. Before those
// rows existed, the holiday rule returned false for these dates and the
// tagline was silently filtered out of the active pool. activeTaglines is no
// longer exported, so we sample the public pickTagline() across every pool
// index (by sweeping the injected random()) to recover the full active pool
// for a given date, then assert the matching holiday tagline is present.
// UTC dates are used because the holiday rules compare in UTC.
const activePoolOn = (year: number, monthIndex: number, day: number): string[] => {
const now = () => new Date(Date.UTC(year, monthIndex, day, 12, 0, 0));
const seen = new Set<string>();
for (let i = 0; i < 200; i++) {
const r = i / 200;
seen.add(pickTagline({ mode: "random", now, random: () => r }));
}
return [...seen];
};
const poolHas = (pool: string[], term: string) =>
pool.some((t) => t.toLowerCase().includes(term));
it("activates the Lunar New Year tagline on 2028-01-26", () => {
expect(poolHas(activePoolOn(2028, 0, 26), "lunar new year")).toBe(true);
});
it("activates the Diwali tagline on 2029-11-05", () => {
expect(poolHas(activePoolOn(2029, 10, 5), "diwali")).toBe(true);
});
it("activates the Diwali tagline on 2030-10-25", () => {
expect(poolHas(activePoolOn(2030, 9, 25), "diwali")).toBe(true);
});
it("activates the Easter tagline on 2030-04-21", () => {
expect(poolHas(activePoolOn(2030, 3, 21), "easter")).toBe(true);
});
it("activates the Hanukkah tagline across its full 2028 window (Dec 13 and Dec 20)", () => {
expect(poolHas(activePoolOn(2028, 11, 13), "hanukkah")).toBe(true);
expect(poolHas(activePoolOn(2028, 11, 20), "hanukkah")).toBe(true);
});
it("does not activate floating holiday taglines on a plain date (2028-07-15)", () => {
const pool = activePoolOn(2028, 6, 15);
for (const term of ["lunar new year", "diwali", "easter", "hanukkah", "eid al-fitr"]) {
expect(poolHas(pool, term)).toBe(false);
}
});
});

View File

@@ -187,6 +187,9 @@ const HOLIDAY_RULES = new Map<string, HolidayRule>([
[2025, 0, 29],
[2026, 1, 17],
[2027, 1, 6],
[2028, 0, 26],
[2029, 1, 13],
[2030, 1, 3],
],
1,
),
@@ -199,6 +202,9 @@ const HOLIDAY_RULES = new Map<string, HolidayRule>([
[2025, 2, 31],
[2026, 2, 20],
[2027, 2, 10],
[2028, 1, 27],
[2029, 1, 15],
[2030, 1, 5],
],
1,
),
@@ -210,6 +216,9 @@ const HOLIDAY_RULES = new Map<string, HolidayRule>([
[2025, 9, 20],
[2026, 10, 8],
[2027, 9, 28],
[2028, 9, 17],
[2029, 10, 5],
[2030, 9, 25],
],
1,
),
@@ -221,6 +230,9 @@ const HOLIDAY_RULES = new Map<string, HolidayRule>([
[2025, 3, 20],
[2026, 3, 5],
[2027, 2, 28],
[2028, 3, 16],
[2029, 3, 1],
[2030, 3, 21],
],
1,
),
@@ -231,6 +243,9 @@ const HOLIDAY_RULES = new Map<string, HolidayRule>([
{ year: 2025, month: 11, day: 15, duration: 8 },
{ year: 2026, month: 11, day: 5, duration: 8 },
{ year: 2027, month: 11, day: 25, duration: 8 },
{ year: 2028, month: 11, day: 13, duration: 8 },
{ year: 2029, month: 11, day: 2, duration: 8 },
{ year: 2030, month: 11, day: 21, duration: 8 },
]),
],
[HOLIDAY_TAGLINES.halloween, onMonthDay(9, 31)],