Files
gridpilot.gg/tests/integration/teams/membership/team-membership.test.ts
Marc Mintel 09632d004d
Some checks failed
CI / lint-typecheck (pull_request) Failing after 12s
CI / tests (pull_request) Has been skipped
CI / contract-tests (pull_request) Has been skipped
CI / e2e-tests (pull_request) Has been skipped
CI / comment-pr (pull_request) Has been skipped
CI / commit-types (pull_request) Has been skipped
code quality
2026-01-26 22:16:33 +01:00

202 lines
7.8 KiB
TypeScript

import { describe, it, expect, beforeEach } from 'vitest';
import { TeamsTestContext } from '../TeamsTestContext';
import { Driver } from '../../../../core/racing/domain/entities/Driver';
import { Team } from '../../../../core/racing/domain/entities/Team';
describe('Team Membership Use Cases', () => {
const context = new TeamsTestContext();
const joinTeamUseCase = context.createJoinTeamUseCase();
const leaveTeamUseCase = context.createLeaveTeamUseCase();
const getTeamMembershipUseCase = context.createGetTeamMembershipUseCase();
const getTeamMembersUseCase = context.createGetTeamMembersUseCase();
const getTeamJoinRequestsUseCase = context.createGetTeamJoinRequestsUseCase();
const approveTeamJoinRequestUseCase = context.createApproveTeamJoinRequestUseCase();
beforeEach(() => {
context.clear();
});
describe('JoinTeamUseCase', () => {
it('should create a join request for a team', async () => {
const driverId = 'd1';
const driver = Driver.create({ id: driverId, iracingId: '1', name: 'Driver 1', country: 'US' });
await context.driverRepository.create(driver);
const teamId = 't1';
const team = Team.create({ id: teamId, name: 'Team 1', tag: 'T1', description: 'Test Team', ownerId: 'owner', leagues: [] });
await context.teamRepository.create(team);
const result = await joinTeamUseCase.execute({ teamId, driverId });
expect(result.isOk()).toBe(true);
const { membership } = result.unwrap();
expect(membership.status).toBe('active');
expect(membership.role).toBe('driver');
const savedMembership = await context.membershipRepository.getMembership(teamId, driverId);
expect(savedMembership).toBeDefined();
expect(savedMembership?.status).toBe('active');
});
it('should reject join request when driver is already a member', async () => {
const driverId = 'd3';
const teamId = 't3';
const team = Team.create({ id: teamId, name: 'Team 3', tag: 'T3', description: 'Test Team', ownerId: 'owner', leagues: [] });
await context.teamRepository.create(team);
await context.membershipRepository.saveMembership({
teamId,
driverId,
role: 'driver',
status: 'active',
joinedAt: new Date()
});
const result = await joinTeamUseCase.execute({ teamId, driverId });
expect(result.isErr()).toBe(true);
// JoinTeamUseCase returns ALREADY_IN_TEAM if driver is in ANY team,
// and ALREADY_MEMBER if they are already in THIS team.
// In this case, they are already in this team.
expect(result.unwrapErr().code).toBe('ALREADY_IN_TEAM');
});
});
describe('LeaveTeamUseCase', () => {
it('should allow driver to leave team', async () => {
const driverId = 'd7';
const teamId = 't7';
const team = Team.create({ id: teamId, name: 'Team 7', tag: 'T7', description: 'Test Team', ownerId: 'owner', leagues: [] });
await context.teamRepository.create(team);
await context.membershipRepository.saveMembership({
teamId,
driverId,
role: 'driver',
status: 'active',
joinedAt: new Date()
});
const result = await leaveTeamUseCase.execute({ teamId, driverId });
expect(result.isOk()).toBe(true);
const savedMembership = await context.membershipRepository.getMembership(teamId, driverId);
expect(savedMembership).toBeNull();
});
it('should reject leave when driver is team owner', async () => {
const driverId = 'd9';
const teamId = 't9';
const team = Team.create({ id: teamId, name: 'Team 9', tag: 'T9', description: 'Test Team', ownerId: driverId, leagues: [] });
await context.teamRepository.create(team);
await context.membershipRepository.saveMembership({
teamId,
driverId,
role: 'owner',
status: 'active',
joinedAt: new Date()
});
const result = await leaveTeamUseCase.execute({ teamId, driverId });
expect(result.isErr()).toBe(true);
expect(result.unwrapErr().code).toBe('OWNER_CANNOT_LEAVE');
});
});
describe('GetTeamMembershipUseCase', () => {
it('should retrieve driver membership in team', async () => {
const driverId = 'd10';
const teamId = 't10';
const team = Team.create({ id: teamId, name: 'Team 10', tag: 'T10', description: 'Test Team', ownerId: 'owner', leagues: [] });
await context.teamRepository.create(team);
await context.membershipRepository.saveMembership({
teamId,
driverId,
role: 'driver',
status: 'active',
joinedAt: new Date()
});
const result = await getTeamMembershipUseCase.execute({ teamId, driverId });
expect(result.isOk()).toBe(true);
const { membership } = result.unwrap();
expect(membership?.role).toBe('member');
});
});
describe('GetTeamMembersUseCase', () => {
it('should retrieve all team members', async () => {
const teamId = 't12';
const team = Team.create({ id: teamId, name: 'Team 12', tag: 'T12', description: 'Test Team', ownerId: 'owner', leagues: [] });
await context.teamRepository.create(team);
const driver1 = Driver.create({ id: 'd12', iracingId: '12', name: 'Driver 12', country: 'US' });
const driver2 = Driver.create({ id: 'd13', iracingId: '13', name: 'Driver 13', country: 'UK' });
await context.driverRepository.create(driver1);
await context.driverRepository.create(driver2);
await context.membershipRepository.saveMembership({ teamId, driverId: 'd12', role: 'owner', status: 'active', joinedAt: new Date() });
await context.membershipRepository.saveMembership({ teamId, driverId: 'd13', role: 'driver', status: 'active', joinedAt: new Date() });
const result = await getTeamMembersUseCase.execute({ teamId });
expect(result.isOk()).toBe(true);
const { members } = result.unwrap();
expect(members).toHaveLength(2);
});
});
describe('GetTeamJoinRequestsUseCase', () => {
it('should retrieve pending join requests', async () => {
const teamId = 't14';
const team = Team.create({ id: teamId, name: 'Team 14', tag: 'T14', description: 'Test Team', ownerId: 'owner', leagues: [] });
await context.teamRepository.create(team);
const driver1 = Driver.create({ id: 'd14', iracingId: '14', name: 'Driver 14', country: 'US' });
await context.driverRepository.create(driver1);
await context.membershipRepository.saveJoinRequest({
id: 'jr2',
teamId,
driverId: 'd14',
requestedAt: new Date()
});
const result = await getTeamJoinRequestsUseCase.execute({ teamId });
expect(result.isOk()).toBe(true);
const { joinRequests } = result.unwrap();
expect(joinRequests).toHaveLength(1);
});
});
describe('ApproveTeamJoinRequestUseCase', () => {
it('should approve a pending join request', async () => {
const teamId = 't16';
const team = Team.create({ id: teamId, name: 'Team 16', tag: 'T16', description: 'Test Team', ownerId: 'owner', leagues: [] });
await context.teamRepository.create(team);
const driverId = 'd16';
const driver = Driver.create({ id: driverId, iracingId: '16', name: 'Driver 16', country: 'US' });
await context.driverRepository.create(driver);
await context.membershipRepository.saveJoinRequest({
id: 'jr4',
teamId,
driverId,
requestedAt: new Date()
});
const result = await approveTeamJoinRequestUseCase.execute({ teamId, requestId: 'jr4' });
expect(result.isOk()).toBe(true);
const savedMembership = await context.membershipRepository.getMembership(teamId, driverId);
expect(savedMembership?.status).toBe('active');
});
});
});