import { isAmdEnv, isRequireJsEnv } from "../amd-utils";

describe("amd-utils", () => {
  afterEach(() => {
    Object.defineProperty(globalThis, "define", {
      value: undefined,
      writable: true,
    });
  });

  describe("isAmdEnv", () => {
    it("should return true if the environment is AMD", () => {
      // Mock the window object to simulate an AMD environment
      const mockDefine = jest.fn();
      // @ts-expect-error jest.Mock<> does not have properties
      mockDefine.amd = {};
      Object.defineProperty(globalThis, "define", {
        value: mockDefine,
        writable: true,
      });

      expect(isAmdEnv()).toBe(true);
    });

    it("should return false if the environment is not AMD", () => {
      // Mock the window object to simulate a non-AMD environment
      const mockDefine = jest.fn();
      Object.defineProperty(globalThis, "define", {
        value: mockDefine,
        writable: true,
      });

      expect(isAmdEnv()).toBe(false);
    });

    it("should return false if define is not a function", () => {
      // Mock the window object to simulate a non-AMD environment
      const mockDefine = { amd: true };
      Object.defineProperty(globalThis, "define", {
        value: mockDefine,
        writable: true,
      });

      expect(isAmdEnv()).toBe(false);
    });
  });

  describe("isRequireJsEnv", () => {
    it("should return true if the environment is RequireJS", () => {
      // Mock a RequireJS environment
      const mockDefine = jest.fn();
      // @ts-expect-error jest.Mock<> does not have properties
      mockDefine.amd = {};
      Object.defineProperty(globalThis, "define", {
        value: mockDefine,
        writable: true,
      });

      const mockRequirejs = jest.fn();
      // @ts-expect-error jest.Mock<> does not have properties
      mockRequirejs.config = jest.fn();
      Object.defineProperty(globalThis, "requirejs", {
        value: mockRequirejs,
        writable: true,
      });

      expect(isRequireJsEnv()).toBe(true);
    });

    it("should return false if the environment is not RequireJS", () => {
      // Mock a non-RequireJS environment
      const mockDefine = jest.fn();
      // @ts-expect-error jest.Mock<> does not have properties
      mockDefine.amd = {};
      Object.defineProperty(globalThis, "define", {
        value: mockDefine,
        writable: true,
      });

      const mockRequirejs = jest.fn();
      // @ts-expect-error jest.Mock<> does not have properties
      mockRequirejs.config = "not a function";
      Object.defineProperty(globalThis, "requirejs", {
        value: mockRequirejs,
        writable: true,
      });

      expect(isRequireJsEnv()).toBe(false);
    });

    it("should return false if the environment is not AMD", () => {
      // Mock the window object to simulate a non-AMD environment
      const mockDefine = jest.fn();
      Object.defineProperty(globalThis, "define", {
        value: mockDefine,
        writable: true,
      });

      const mockRequirejs = jest.fn();
      // @ts-expect-error jest.Mock<> does not have properties
      mockRequirejs.config = "not a function";
      Object.defineProperty(globalThis, "requirejs", {
        value: mockRequirejs,
        writable: true,
      });

      expect(isRequireJsEnv()).toBe(false);
    });
  });
});
