4.8 KiB
Customer Domain - Final Cleanup
Problems Identified
1. Unnecessary Infra Mapper (BFF)
Current:
BFF: @prisma/client User → user.mapper.ts → domain/customer/providers/portal → UserAuth
Problem: Double mapping! BFF adapter just converts Prisma type to domain raw type, then calls domain mapper.
Better:
BFF: @prisma/client User → directly use domain/customer/providers/portal/mapper → UserAuth
The BFF mapper is redundant - we should use the domain mapper directly.
2. Unused Legacy WHMCS Types
Never used in BFF:
- ❌
CustomerEmailPreferences(0 occurrences) - ❌
CustomerUser(sub-users, 0 occurrences) - ❌
CustomerStats(billing stats, 0 occurrences) - ❌
Customer(full WHMCS schema - only used internally in WHMCS mapper)
Schemas for unused types:
- ❌
customerEmailPreferencesSchema(~40 lines) - ❌
customerUserSchema(~25 lines) - ❌
customerStatsSchema(~50 lines) - ❌
customerSchema(~35 lines)
Total bloat: ~150 lines of unused code!
3. Not Following Schema-First in Domain Mapper
Current: packages/domain/customer/providers/portal/mapper.ts
// Manually constructs object - NO SCHEMA!
export function mapPrismaUserToUserAuth(raw: PrismaUserRaw): UserAuth {
return {
id: raw.id,
email: raw.email,
// ... manual construction
};
}
Should be:
// Use schema for validation!
export function mapPrismaUserToUserAuth(raw: PrismaUserRaw): UserAuth {
return userAuthSchema.parse({
id: raw.id,
email: raw.email,
// ...
});
}
Cleanup Plan
Step 1: Remove Unused Types
File: packages/domain/customer/types.ts
Remove:
customerEmailPreferencesSchema+ typecustomerUserSchema+ typecustomerStatsSchema+ typecustomerSchema+ type (full WHMCS schema)- Helper functions for these types
Keep only:
userAuthSchema→UserAuthuserSchema→UsercustomerDataSchema→CustomerDatacustomerAddressSchema→CustomerAddressaddressFormSchema→AddressFormData
Step 2: Update Customer Index Exports
File: packages/domain/customer/index.ts
Remove exports:
CustomerEmailPreferencesCustomerUserCustomerStatsCustomer- All related schemas
Step 3: Clean WHMCS Mapper (Internal Use Only)
File: packages/domain/customer/providers/whmcs/mapper.ts
Since Customer type is removed, the WHMCS mapper can:
- Either define types inline (internal to mapper)
- Or export minimal
WhmcsCustomertype just for mapper use
Step 4: Use Schema in Portal Mapper
File: packages/domain/customer/providers/portal/mapper.ts
import { userAuthSchema } from "../../types";
import type { PrismaUserRaw } from "./types";
import type { UserAuth } from "../../types";
export function mapPrismaUserToUserAuth(raw: PrismaUserRaw): UserAuth {
return userAuthSchema.parse({
id: raw.id,
email: raw.email,
role: raw.role,
mfaEnabled: !!raw.mfaSecret,
emailVerified: raw.emailVerified,
lastLoginAt: raw.lastLoginAt?.toISOString(),
createdAt: raw.createdAt.toISOString(),
updatedAt: raw.updatedAt.toISOString(),
});
}
Step 5: Eliminate BFF Infra Mapper
Delete: apps/bff/src/infra/mappers/user.mapper.ts
Update all 7 usages to directly import from domain:
// OLD (double mapping - BAD!)
import { mapPrismaUserToDomain } from "@bff/infra/mappers";
const userAuth = mapPrismaUserToDomain(prismaUser);
// NEW (direct - GOOD!)
import { mapPrismaUserToUserAuth } from "@customer-portal/domain/customer/providers/portal";
const userAuth = mapPrismaUserToUserAuth(prismaUser);
Files to update (7 total):
apps/bff/src/modules/auth/presentation/strategies/jwt.strategy.tsapps/bff/src/modules/auth/infra/workflows/workflows/whmcs-link-workflow.service.tsapps/bff/src/modules/auth/infra/workflows/workflows/signup-workflow.service.tsapps/bff/src/modules/auth/infra/workflows/workflows/password-workflow.service.tsapps/bff/src/modules/auth/infra/token/token.service.tsapps/bff/src/modules/auth/application/auth.facade.ts- Any other imports of
mapPrismaUserToDomain
Result
Before:
- 342 lines in types.ts (lots of unused code)
- BFF infra mapper (unnecessary layer)
- Manual object construction (no schema validation)
After:
- ~190 lines in types.ts (lean, only what's used)
- Direct domain mapper usage (proper architecture)
- Schema-validated mapping (type safe + runtime safe)
Types kept:
// User entity types
User // Complete user
UserAuth // Auth state
UserRole // Role enum
// Address
CustomerAddress // Address structure
AddressFormData // Form validation
// Profile data (internal)
CustomerData // WHMCS profile fields
Clean, minimal, schema-first! 🎯