import { InstallId } from '../../../../src/domain/value-objects/install-id.vo';
import { DomainException } from '../../../../src/shared/exceptions/domain.exception';

describe('InstallId Value Object', () => {
  describe('fromString', () => {
    it('should create InstallId from valid string', () => {
      const installId = InstallId.fromString('abc12345');
      expect(installId.value).toBe('abc12345');
    });

    it('should trim whitespace from input', () => {
      const installId = InstallId.fromString('  abc12345  ');
      expect(installId.value).toBe('abc12345');
    });

    it('should accept UUID format', () => {
      const uuid = '550e8400-e29b-41d4-a716-446655440000';
      const installId = InstallId.fromString(uuid);
      expect(installId.value).toBe(uuid);
    });

    it('should throw DomainException for empty string', () => {
      expect(() => InstallId.fromString('')).toThrow(DomainException);
      expect(() => InstallId.fromString('')).toThrow('InstallId cannot be empty');
    });

    it('should throw DomainException for whitespace only string', () => {
      expect(() => InstallId.fromString('   ')).toThrow(DomainException);
    });

    it('should throw DomainException for too short string', () => {
      expect(() => InstallId.fromString('abc')).toThrow(DomainException);
      expect(() => InstallId.fromString('abc')).toThrow('InstallId length must be between 8 and 128 characters');
    });

    it('should throw DomainException for too long string', () => {
      const longString = 'a'.repeat(129);
      expect(() => InstallId.fromString(longString)).toThrow(DomainException);
    });

    it('should accept exactly 8 characters', () => {
      const installId = InstallId.fromString('12345678');
      expect(installId.value).toBe('12345678');
    });

    it('should accept exactly 128 characters', () => {
      const maxString = 'a'.repeat(128);
      const installId = InstallId.fromString(maxString);
      expect(installId.value).toBe(maxString);
    });
  });

  describe('generate', () => {
    it('should generate a valid InstallId', () => {
      const installId = InstallId.generate();
      expect(installId).toBeInstanceOf(InstallId);
      expect(installId.value.length).toBeGreaterThanOrEqual(8);
    });

    it('should generate unique InstallIds', () => {
      const id1 = InstallId.generate();
      const id2 = InstallId.generate();
      expect(id1.value).not.toBe(id2.value);
    });
  });

  describe('equals', () => {
    it('should return true for same values', () => {
      const id1 = InstallId.fromString('abc12345');
      const id2 = InstallId.fromString('abc12345');
      expect(id1.equals(id2)).toBe(true);
    });

    it('should return false for different values', () => {
      const id1 = InstallId.fromString('abc12345');
      const id2 = InstallId.fromString('xyz98765');
      expect(id1.equals(id2)).toBe(false);
    });
  });

  describe('toString', () => {
    it('should return the string value', () => {
      const installId = InstallId.fromString('abc12345');
      expect(installId.toString()).toBe('abc12345');
    });
  });
});
