import Shortify, { DatabaseConfig } from "../src/index";

describe("SQLite Database Support", () => {
  let shortify: Shortify;

  beforeAll(async () => {
    const dbConfig: DatabaseConfig = {
      type: "sqlite",
      database: ":memory:", // Use in-memory database for testing
      maxRetries: 1,
      retryDelay: 100,
    };

    shortify = new Shortify("https://test.com", dbConfig);
    await shortify.connect();
  });

  afterAll(async () => {
    if (shortify) {
      await shortify.disconnect();
    }
  });

  it("should create SQLite adapter correctly", () => {
    expect(shortify).toBeDefined();
    expect(shortify.isReady()).toBe(true);
  });

  it("should shorten and resolve URLs with SQLite", async () => {
    const result = await shortify.shorten(
      "https://example.com/test-url-sqlite"
    );
    expect(result.shortUrl).toContain("https://test.com/");
    expect(result.originalUrl).toBe("https://example.com/test-url-sqlite");

    const resolved = await shortify.resolve(result.urlId);
    expect(resolved).toBe("https://example.com/test-url-sqlite");
  });

  it("should handle URL expiration with SQLite", async () => {
    const result = await shortify.shorten("https://example.com/expiring-url", {
      expiresInDays: 1,
    });
    expect(result.expiresAt).toBeDefined();

    const stats = await shortify.getStats(result.urlId);
    expect(stats?.expiresAt).toBeDefined();
  });

  it("should handle custom URL IDs", async () => {
    const result = await shortify.shorten("https://example.com/custom-url", {
      customUrlId: "custom123",
    });
    expect(result.urlId).toBe("custom123");
    expect(result.shortUrl).toBe("https://test.com/custom123");
  });

  it("should generate unique URL IDs for each request", async () => {
    const url = "https://example.com/duplicate-test";

    const result1 = await shortify.shorten(url);
    const result2 = await shortify.shorten(url);

    // Each request should get a unique URL ID
    expect(result1.urlId).not.toBe(result2.urlId);
    expect(result1.shortUrl).not.toBe(result2.shortUrl);

    // Both should resolve to the same original URL
    const resolved1 = await shortify.resolve(result1.urlId);
    const resolved2 = await shortify.resolve(result2.urlId);
    expect(resolved1).toBe(url);
    expect(resolved2).toBe(url);
  });

  it("should track click statistics", async () => {
    const result = await shortify.shorten("https://example.com/stats-test");

    // Initial stats
    let stats = await shortify.getStats(result.urlId);
    expect(stats?.clicks).toBe(0);

    // Resolve URL (should increment clicks)
    await shortify.resolve(result.urlId);

    // Check updated stats
    stats = await shortify.getStats(result.urlId);
    expect(stats?.clicks).toBe(1);
  });

  it("should delete URLs", async () => {
    const result = await shortify.shorten("https://example.com/delete-test");

    // Verify URL exists
    const resolved = await shortify.resolve(result.urlId);
    expect(resolved).toBe("https://example.com/delete-test");

    // Delete URL
    const deleted = await shortify.delete(result.urlId);
    expect(deleted).toBe(true);

    // Verify URL is gone
    const resolvedAfterDelete = await shortify.resolve(result.urlId);
    expect(resolvedAfterDelete).toBeNull();
  });
});
