271 lines
7.9 KiB
TypeScript
271 lines
7.9 KiB
TypeScript
/**
|
|
* License Entity Tests
|
|
*
|
|
* Unit tests for the License domain entity
|
|
*/
|
|
|
|
import { License } from './license.entity';
|
|
|
|
describe('License Entity', () => {
|
|
const createValidLicense = () => {
|
|
return License.create({
|
|
id: 'license-123',
|
|
subscriptionId: 'sub-123',
|
|
userId: 'user-123',
|
|
});
|
|
};
|
|
|
|
describe('create', () => {
|
|
it('should create a license with valid data', () => {
|
|
const license = createValidLicense();
|
|
|
|
expect(license.id).toBe('license-123');
|
|
expect(license.subscriptionId).toBe('sub-123');
|
|
expect(license.userId).toBe('user-123');
|
|
expect(license.status.value).toBe('ACTIVE');
|
|
expect(license.assignedAt).toBeInstanceOf(Date);
|
|
expect(license.revokedAt).toBeNull();
|
|
});
|
|
|
|
it('should create a license with different user', () => {
|
|
const license = License.create({
|
|
id: 'license-456',
|
|
subscriptionId: 'sub-123',
|
|
userId: 'user-456',
|
|
});
|
|
|
|
expect(license.userId).toBe('user-456');
|
|
});
|
|
});
|
|
|
|
describe('fromPersistence', () => {
|
|
it('should reconstitute an active license from persistence data', () => {
|
|
const assignedAt = new Date('2024-01-15');
|
|
const license = License.fromPersistence({
|
|
id: 'license-123',
|
|
subscriptionId: 'sub-123',
|
|
userId: 'user-123',
|
|
status: 'ACTIVE',
|
|
assignedAt,
|
|
revokedAt: null,
|
|
});
|
|
|
|
expect(license.id).toBe('license-123');
|
|
expect(license.status.value).toBe('ACTIVE');
|
|
expect(license.assignedAt).toEqual(assignedAt);
|
|
expect(license.revokedAt).toBeNull();
|
|
});
|
|
|
|
it('should reconstitute a revoked license from persistence data', () => {
|
|
const revokedAt = new Date('2024-02-01');
|
|
const license = License.fromPersistence({
|
|
id: 'license-123',
|
|
subscriptionId: 'sub-123',
|
|
userId: 'user-123',
|
|
status: 'REVOKED',
|
|
assignedAt: new Date('2024-01-15'),
|
|
revokedAt,
|
|
});
|
|
|
|
expect(license.status.value).toBe('REVOKED');
|
|
expect(license.revokedAt).toEqual(revokedAt);
|
|
});
|
|
});
|
|
|
|
describe('isActive', () => {
|
|
it('should return true for active license', () => {
|
|
const license = createValidLicense();
|
|
expect(license.isActive()).toBe(true);
|
|
});
|
|
|
|
it('should return false for revoked license', () => {
|
|
const license = License.fromPersistence({
|
|
id: 'license-123',
|
|
subscriptionId: 'sub-123',
|
|
userId: 'user-123',
|
|
status: 'REVOKED',
|
|
assignedAt: new Date('2024-01-15'),
|
|
revokedAt: new Date('2024-02-01'),
|
|
});
|
|
|
|
expect(license.isActive()).toBe(false);
|
|
});
|
|
});
|
|
|
|
describe('isRevoked', () => {
|
|
it('should return false for active license', () => {
|
|
const license = createValidLicense();
|
|
expect(license.isRevoked()).toBe(false);
|
|
});
|
|
|
|
it('should return true for revoked license', () => {
|
|
const license = License.fromPersistence({
|
|
id: 'license-123',
|
|
subscriptionId: 'sub-123',
|
|
userId: 'user-123',
|
|
status: 'REVOKED',
|
|
assignedAt: new Date('2024-01-15'),
|
|
revokedAt: new Date('2024-02-01'),
|
|
});
|
|
|
|
expect(license.isRevoked()).toBe(true);
|
|
});
|
|
});
|
|
|
|
describe('revoke', () => {
|
|
it('should revoke an active license', () => {
|
|
const license = createValidLicense();
|
|
const revoked = license.revoke();
|
|
|
|
expect(revoked.status.value).toBe('REVOKED');
|
|
expect(revoked.revokedAt).toBeInstanceOf(Date);
|
|
expect(revoked.isActive()).toBe(false);
|
|
});
|
|
|
|
it('should throw when revoking an already revoked license', () => {
|
|
const license = License.fromPersistence({
|
|
id: 'license-123',
|
|
subscriptionId: 'sub-123',
|
|
userId: 'user-123',
|
|
status: 'REVOKED',
|
|
assignedAt: new Date('2024-01-15'),
|
|
revokedAt: new Date('2024-02-01'),
|
|
});
|
|
|
|
expect(() => license.revoke()).toThrow('License is already revoked');
|
|
});
|
|
|
|
it('should preserve original data when revoking', () => {
|
|
const license = License.fromPersistence({
|
|
id: 'license-123',
|
|
subscriptionId: 'sub-456',
|
|
userId: 'user-789',
|
|
status: 'ACTIVE',
|
|
assignedAt: new Date('2024-01-15'),
|
|
revokedAt: null,
|
|
});
|
|
|
|
const revoked = license.revoke();
|
|
|
|
expect(revoked.id).toBe('license-123');
|
|
expect(revoked.subscriptionId).toBe('sub-456');
|
|
expect(revoked.userId).toBe('user-789');
|
|
expect(revoked.assignedAt).toEqual(new Date('2024-01-15'));
|
|
});
|
|
});
|
|
|
|
describe('reactivate', () => {
|
|
it('should reactivate a revoked license', () => {
|
|
const license = License.fromPersistence({
|
|
id: 'license-123',
|
|
subscriptionId: 'sub-123',
|
|
userId: 'user-123',
|
|
status: 'REVOKED',
|
|
assignedAt: new Date('2024-01-15'),
|
|
revokedAt: new Date('2024-02-01'),
|
|
});
|
|
|
|
const reactivated = license.reactivate();
|
|
|
|
expect(reactivated.status.value).toBe('ACTIVE');
|
|
expect(reactivated.revokedAt).toBeNull();
|
|
});
|
|
|
|
it('should throw when reactivating an active license', () => {
|
|
const license = createValidLicense();
|
|
|
|
expect(() => license.reactivate()).toThrow('License is already active');
|
|
});
|
|
});
|
|
|
|
describe('getActiveDuration', () => {
|
|
it('should calculate duration for active license', () => {
|
|
const assignedAt = new Date();
|
|
assignedAt.setHours(assignedAt.getHours() - 1); // 1 hour ago
|
|
|
|
const license = License.fromPersistence({
|
|
id: 'license-123',
|
|
subscriptionId: 'sub-123',
|
|
userId: 'user-123',
|
|
status: 'ACTIVE',
|
|
assignedAt,
|
|
revokedAt: null,
|
|
});
|
|
|
|
const duration = license.getActiveDuration();
|
|
// Should be approximately 1 hour in milliseconds (allow some variance)
|
|
expect(duration).toBeGreaterThan(3600000 - 1000);
|
|
expect(duration).toBeLessThan(3600000 + 1000);
|
|
});
|
|
|
|
it('should calculate duration for revoked license', () => {
|
|
const assignedAt = new Date('2024-01-15T10:00:00Z');
|
|
const revokedAt = new Date('2024-01-15T12:00:00Z'); // 2 hours later
|
|
|
|
const license = License.fromPersistence({
|
|
id: 'license-123',
|
|
subscriptionId: 'sub-123',
|
|
userId: 'user-123',
|
|
status: 'REVOKED',
|
|
assignedAt,
|
|
revokedAt,
|
|
});
|
|
|
|
const duration = license.getActiveDuration();
|
|
expect(duration).toBe(2 * 60 * 60 * 1000); // 2 hours in ms
|
|
});
|
|
});
|
|
|
|
describe('toObject', () => {
|
|
it('should convert to plain object for persistence', () => {
|
|
const license = createValidLicense();
|
|
const obj = license.toObject();
|
|
|
|
expect(obj.id).toBe('license-123');
|
|
expect(obj.subscriptionId).toBe('sub-123');
|
|
expect(obj.userId).toBe('user-123');
|
|
expect(obj.status).toBe('ACTIVE');
|
|
expect(obj.assignedAt).toBeInstanceOf(Date);
|
|
expect(obj.revokedAt).toBeNull();
|
|
});
|
|
|
|
it('should include revokedAt for revoked license', () => {
|
|
const revokedAt = new Date('2024-02-01');
|
|
const license = License.fromPersistence({
|
|
id: 'license-123',
|
|
subscriptionId: 'sub-123',
|
|
userId: 'user-123',
|
|
status: 'REVOKED',
|
|
assignedAt: new Date('2024-01-15'),
|
|
revokedAt,
|
|
});
|
|
|
|
const obj = license.toObject();
|
|
expect(obj.status).toBe('REVOKED');
|
|
expect(obj.revokedAt).toEqual(revokedAt);
|
|
});
|
|
});
|
|
|
|
describe('property accessors', () => {
|
|
it('should correctly expose all properties', () => {
|
|
const assignedAt = new Date('2024-01-15');
|
|
|
|
const license = License.fromPersistence({
|
|
id: 'license-123',
|
|
subscriptionId: 'sub-456',
|
|
userId: 'user-789',
|
|
status: 'ACTIVE',
|
|
assignedAt,
|
|
revokedAt: null,
|
|
});
|
|
|
|
expect(license.id).toBe('license-123');
|
|
expect(license.subscriptionId).toBe('sub-456');
|
|
expect(license.userId).toBe('user-789');
|
|
expect(license.status.value).toBe('ACTIVE');
|
|
expect(license.assignedAt).toEqual(assignedAt);
|
|
expect(license.revokedAt).toBeNull();
|
|
});
|
|
});
|
|
});
|