diff --git a/test/common/datetime/check_time.test.ts b/test/common/datetime/check_time.test.ts new file mode 100644 index 0000000000..7a33dd126f --- /dev/null +++ b/test/common/datetime/check_time.test.ts @@ -0,0 +1,164 @@ +import { describe, it, expect, vi, beforeEach, afterEach } from "vitest"; +import { checkTimeInRange } from "../../../src/common/datetime/check_time"; +import type { HomeAssistant } from "../../../src/types"; +import { + NumberFormat, + TimeFormat, + FirstWeekday, + DateFormat, + TimeZone, +} from "../../../src/data/translation"; + +describe("checkTimeInRange", () => { + let mockHass: HomeAssistant; + + beforeEach(() => { + mockHass = { + locale: { + language: "en-US", + number_format: NumberFormat.language, + time_format: TimeFormat.language, + date_format: DateFormat.language, + time_zone: TimeZone.local, + first_weekday: FirstWeekday.language, + }, + config: { + time_zone: "America/Los_Angeles", + }, + } as HomeAssistant; + }); + + afterEach(() => { + vi.useRealTimers(); + }); + + describe("time ranges within same day", () => { + it("should return true when current time is within range", () => { + // Set time to 10:00 AM + vi.setSystemTime(new Date(2024, 0, 15, 10, 0, 0)); + + expect(checkTimeInRange(mockHass, "08:00", "17:00")).toBe(true); + }); + + it("should return false when current time is before range", () => { + // Set time to 7:00 AM + vi.setSystemTime(new Date(2024, 0, 15, 7, 0, 0)); + + expect(checkTimeInRange(mockHass, "08:00", "17:00")).toBe(false); + }); + + it("should return false when current time is after range", () => { + // Set time to 6:00 PM + vi.setSystemTime(new Date(2024, 0, 15, 18, 0, 0)); + + expect(checkTimeInRange(mockHass, "08:00", "17:00")).toBe(false); + }); + }); + + describe("time ranges crossing midnight", () => { + it("should return true when current time is before midnight", () => { + // Set time to 11:00 PM + vi.setSystemTime(new Date(2024, 0, 15, 23, 0, 0)); + + expect(checkTimeInRange(mockHass, "22:00", "06:00")).toBe(true); + }); + + it("should return true when current time is after midnight", () => { + // Set time to 3:00 AM + vi.setSystemTime(new Date(2024, 0, 15, 3, 0, 0)); + + expect(checkTimeInRange(mockHass, "22:00", "06:00")).toBe(true); + }); + + it("should return false when outside the range", () => { + // Set time to 10:00 AM + vi.setSystemTime(new Date(2024, 0, 15, 10, 0, 0)); + + expect(checkTimeInRange(mockHass, "22:00", "06:00")).toBe(false); + }); + }); + + describe("only 'after' condition", () => { + it("should return true when after specified time", () => { + vi.setSystemTime(new Date(2024, 0, 15, 10, 0, 0)); + expect(checkTimeInRange(mockHass, "08:00")).toBe(true); + }); + + it("should return false when before specified time", () => { + vi.setSystemTime(new Date(2024, 0, 15, 6, 0, 0)); + expect(checkTimeInRange(mockHass, "08:00")).toBe(false); + }); + }); + + describe("only 'before' condition", () => { + it("should return true when before specified time", () => { + vi.setSystemTime(new Date(2024, 0, 15, 10, 0, 0)); + expect(checkTimeInRange(mockHass, undefined, "17:00")).toBe(true); + }); + + it("should return false when after specified time", () => { + vi.setSystemTime(new Date(2024, 0, 15, 18, 0, 0)); + expect(checkTimeInRange(mockHass, undefined, "17:00")).toBe(false); + }); + }); + + describe("weekday filtering", () => { + it("should return true on matching weekday", () => { + // January 15, 2024 is a Monday + vi.setSystemTime(new Date(2024, 0, 15, 10, 0, 0)); + + expect(checkTimeInRange(mockHass, undefined, undefined, ["mon"])).toBe( + true + ); + }); + + it("should return false on non-matching weekday", () => { + // January 15, 2024 is a Monday + vi.setSystemTime(new Date(2024, 0, 15, 10, 0, 0)); + + expect(checkTimeInRange(mockHass, undefined, undefined, ["tue"])).toBe( + false + ); + }); + + it("should work with multiple weekdays", () => { + // January 15, 2024 is a Monday + vi.setSystemTime(new Date(2024, 0, 15, 10, 0, 0)); + + expect( + checkTimeInRange(mockHass, undefined, undefined, ["mon", "wed", "fri"]) + ).toBe(true); + }); + }); + + describe("combined time and weekday conditions", () => { + it("should return true when both match", () => { + // January 15, 2024 is a Monday at 10:00 AM + vi.setSystemTime(new Date(2024, 0, 15, 10, 0, 0)); + + expect(checkTimeInRange(mockHass, "08:00", "17:00", ["mon"])).toBe(true); + }); + + it("should return false when time matches but weekday doesn't", () => { + // January 15, 2024 is a Monday at 10:00 AM + vi.setSystemTime(new Date(2024, 0, 15, 10, 0, 0)); + + expect(checkTimeInRange(mockHass, "08:00", "17:00", ["tue"])).toBe(false); + }); + + it("should return false when weekday matches but time doesn't", () => { + // January 15, 2024 is a Monday at 6:00 AM + vi.setSystemTime(new Date(2024, 0, 15, 6, 0, 0)); + + expect(checkTimeInRange(mockHass, "08:00", "17:00", ["mon"])).toBe(false); + }); + }); + + describe("no conditions", () => { + it("should return true when no conditions specified", () => { + vi.setSystemTime(new Date(2024, 0, 15, 10, 0, 0)); + + expect(checkTimeInRange(mockHass)).toBe(true); + }); + }); +});