108 lines
3.5 KiB
TypeScript
108 lines
3.5 KiB
TypeScript
import { PrismaClient } from '@prisma/client';
|
||
|
||
const prisma = new PrismaClient();
|
||
|
||
// Lundi (UTC) de la semaine courante
|
||
function mondayOfThisWeekUTC(now = new Date()) {
|
||
const d = new Date(Date.UTC(now.getUTCFullYear(), now.getUTCMonth(), now.getUTCDate()));
|
||
const day = d.getUTCDay(); // 0=Dim, 1=Lun, ...
|
||
const diffToMonday = (day + 6) % 7; // 0 si lundi
|
||
d.setUTCDate(d.getUTCDate() - diffToMonday);
|
||
d.setUTCHours(0, 0, 0, 0);
|
||
return d;
|
||
}
|
||
|
||
// Dates Lundi→Vendredi (UTC minuit)
|
||
function currentWeekDates() {
|
||
const monday = mondayOfThisWeekUTC();
|
||
return Array.from({ length: 5 }, (_, i) => {
|
||
const d = new Date(monday);
|
||
d.setUTCDate(monday.getUTCDate() + i);
|
||
return d;
|
||
});
|
||
}
|
||
|
||
function rndInt(min: number, max: number) {
|
||
return Math.floor(Math.random() * (max - min + 1)) + min;
|
||
}
|
||
function rndAmount(minCents: number, maxCents: number) {
|
||
const cents = rndInt(minCents, maxCents);
|
||
return (cents / 100).toFixed(2); // string "123.45"
|
||
}
|
||
|
||
async function main() {
|
||
// Codes autorisés (aléatoires à chaque dépense)
|
||
const BANKS = ['G517', 'G57', 'G502', 'G202', 'G234'] as const;
|
||
const bcRows = await prisma.bankCodes.findMany({
|
||
where: { bank_code: { in: BANKS as unknown as string[] } },
|
||
select: { id: true, bank_code: true },
|
||
});
|
||
const bcMap = new Map(bcRows.map(c => [c.bank_code, c.id]));
|
||
for (const c of BANKS) {
|
||
if (!bcMap.has(c)) throw new Error(`Bank code manquant: ${c}`);
|
||
}
|
||
|
||
const employees = await prisma.employees.findMany({ select: { id: true } });
|
||
if (!employees.length) {
|
||
console.warn('Aucun employé — rien à insérer.');
|
||
return;
|
||
}
|
||
|
||
const weekDays = currentWeekDates();
|
||
const monday = weekDays[0];
|
||
const friday = weekDays[4];
|
||
|
||
let created = 0;
|
||
|
||
for (const e of employees) {
|
||
// Choisir un timesheet (le plus ancien, ou change 'asc'→'desc' si tu préfères le plus récent)
|
||
const ts = await prisma.timesheets.findFirst({
|
||
where: { employee_id: e.id },
|
||
select: { id: true },
|
||
orderBy: { id: 'asc' },
|
||
});
|
||
if (!ts) continue;
|
||
|
||
// Si l’employé a déjà une dépense cette semaine, on n’en recrée pas (≥1 garanti)
|
||
const already = await prisma.expenses.findFirst({
|
||
where: {
|
||
timesheet_id: ts.id,
|
||
date: { gte: monday, lte: friday },
|
||
},
|
||
select: { id: true },
|
||
});
|
||
if (already) continue;
|
||
|
||
// Choix aléatoire du code + jour
|
||
const randomCode = BANKS[Math.floor(Math.random() * BANKS.length)];
|
||
const bank_code_id = bcMap.get(randomCode)!;
|
||
const date = weekDays[Math.floor(Math.random() * weekDays.length)];
|
||
|
||
// Montant aléatoire (ranges par défaut en $ — ajuste au besoin)
|
||
// (ex.: G57 plus petit, G517 remboursement plus large)
|
||
const amount =
|
||
randomCode === 'G57'
|
||
? rndAmount(1000, 7500) // 10.00..75.00
|
||
: rndAmount(2000, 25000); // 20.00..250.00 pour les autres
|
||
|
||
await prisma.expenses.create({
|
||
data: {
|
||
timesheet_id: ts.id,
|
||
bank_code_id,
|
||
date,
|
||
amount, // stocké en string
|
||
attachement: null, // garde le champ tel quel si typo volontaire
|
||
description: `Expense ${randomCode} ${amount}$ (emp ${e.id})`,
|
||
is_approved: Math.random() < 0.6,
|
||
supervisor_comment: Math.random() < 0.2 ? 'OK' : null,
|
||
},
|
||
});
|
||
created++;
|
||
}
|
||
|
||
const total = await prisma.expenses.count();
|
||
console.log(`✓ Expenses: ${created} nouvelles lignes, ${total} total rows (≥1 expense/employee pour la semaine courante)`);
|
||
}
|
||
|
||
main().finally(() => prisma.$disconnect());
|