course creation

This commit is contained in:
OnlyPapy98
2025-12-19 18:00:50 +01:00
parent dde2e8aebf
commit 169b5ca412
39 changed files with 1250 additions and 2258 deletions

View File

@@ -16,7 +16,7 @@ import { ZardCardComponent } from '@shared/components/card/card.component';
import { ZardButtonComponent } from '@shared/components/button/button.component';
import { Course as CourseType } from 'src/app/core/interfaces/course';
import { SortDir } from '@shared/paging/paging';
import { CourseService } from 'src/app/core/services/course';
import { CourseApiResponse, CourseService } from 'src/app/core/services/course';
import { ResultatService } from 'src/app/core/services/resultat';
import { Resultat } from 'src/app/core/interfaces/resultat';
import { A11yModule } from '@angular/cdk/a11y';
@@ -77,23 +77,19 @@ export class Course {
key: 'type',
label: 'Type',
sortable: true,
cell: (c) => `<span class="font-medium">${c.type}</span>`,
cell: (c) => `<span class="font-medium">${c.discipline}</span>`,
},
{
key: 'dateDepartCourse',
label: 'Date et Heure Départ',
sortable: true,
cell: (c) =>
new Date(c.dateDepartCourse).toLocaleDateString('fr-FR', {
hour: '2-digit',
minute: '2-digit',
}),
cell: (c) => c.heureDepartPrevue
},
{
key: 'partants',
label: 'Partants',
cell: (c) =>
`<span>${c.partants}</span> <span class="text-xs text-red-500">(${
`<span>${c.nombrePartants}</span> <span class="text-xs text-red-500">(${
c.nonPartants?.length ?? 0
} NP)</span>`,
},
@@ -148,20 +144,24 @@ export class Course {
sortable: true,
cell: (c) => {
const colorMap: Record<string, string> = {
PROGRAMMEE: 'bg-purple-100 text-purple-700 dark:bg-purple-900/30 dark:text-purple-300',
CREATED: 'bg-gray-100 text-gray-700 dark:bg-gray-900/30 dark:text-gray-300',
VALIDATED: 'bg-blue-100 text-blue-700 dark:bg-blue-900/30 dark:text-blue-300',
RUNNING: 'bg-amber-100 text-amber-700 dark:bg-amber-900/30 dark:text-amber-300',
CLOSED: 'bg-green-100 text-green-700 dark:bg-green-900/30 dark:text-green-300',
CANCELED: 'bg-red-100 text-red-700 dark:bg-red-900/30 dark:text-red-300',
OUVERT: 'bg-purple-100 text-purple-700 dark:bg-purple-900/30 dark:text-purple-300',
RESULTAT_PROVISOIRE: 'bg-cyan-100 text-purple-700 dark:bg-cyan-900/30 dark:text-cyan-300',
RESULTAT_OFFICIEL: 'bg-amber-100 text-purple-700 dark:bg-amber-900/30 dark:text-amber-300',
BROUILLON: 'bg-gray-100 text-gray-700 dark:bg-gray-900/30 dark:text-gray-300',
VALIDE: 'bg-blue-100 text-blue-700 dark:bg-blue-900/30 dark:text-blue-300',
REGLEE: 'bg-amber-100 text-amber-700 dark:bg-amber-900/30 dark:text-amber-300',
FERME: 'bg-green-100 text-green-700 dark:bg-green-900/30 dark:text-green-300',
ANNULEE: 'bg-red-100 text-red-700 dark:bg-red-900/30 dark:text-red-300',
};
const labelMap: Record<string, string> = {
PROGRAMMEE: 'Programmée',
CREATED: 'Créée',
VALIDATED: 'Validée',
RUNNING: 'En cours',
CLOSED: 'Clôturée',
CANCELED: 'Annulée',
OUVERT: 'Ouvert',
RESULTAT_PROVISOIRE: 'Résultat provisoire',
RESULTAT_OFFICIEL: 'Résultat officiel',
BROUILLON: 'Brouillon',
VALIDE: 'Validé',
REGLEE: 'Réglée',
FERME: 'Fermé',
ANNULEE: 'Annulée'
};
return `<span class="px-2 py-1 rounded-full text-xs font-semibold ${colorMap[c.statut]}">${
labelMap[c.statut]
@@ -171,31 +171,13 @@ export class Course {
{
key: 'reunion.hippodrome.nom',
label: 'Hippodrome',
cell: (c) => (c.reunion?.hippodrome ? `${c.reunion.hippodrome.nom}` : '—'),
},
{
key: 'reunion.nom',
label: 'Réunion',
cell: (c) => c.reunion?.nom ?? '—',
cell: (c) => (c?.hippodrome ? `${c.hippodrome.nom}` : '—'),
},
{
key: 'distance',
label: 'Distance (m)',
sortable: true,
cell: (c) => c.distance.toLocaleString('fr-FR'),
},
{
key: 'createdAt',
label: 'Créée le',
cell: (c) =>
c.createdAt
? new Date(c.createdAt).toLocaleDateString('fr-FR', {
day: '2-digit',
month: 'short',
year: 'numeric',
})
: '—',
cell: (c) => c.distanceMetres.toLocaleString('fr-FR'),
},
];
@@ -224,14 +206,14 @@ export class Course {
this.loading.set(true);
this.api.list(params).subscribe({
next: (res) => {
this.rows.set(res.data);
this.total.set(res.meta.total);
this.totalRunning.set(res.meta['totalRunning'] ?? 0);
this.totalClosed.set(res.meta['totalClosed'] ?? 0);
this.totalByType.set(res.meta['totalByType'] ?? {});
this.rows.set(res.content);
this.total.set(res.totalElements);
this.totalRunning.set(0);
this.totalClosed.set(0);
this.totalByType.set({});
// Fetch resultats for all courses in parallel
const courseIds = res.data.map((c) => c.id);
const courseIds = res.content.map((c) => c.id);
if (courseIds.length > 0) {
const resultatRequests = courseIds.map((id) =>
this.resultatService.getByCourseId(id).pipe(catchError(() => of(undefined)))
@@ -305,7 +287,7 @@ export class Course {
const current = this.editingItem();
const req$ = current?.id
? this.api.update(current.id, payload)
: this.api.create(payload as Omit<CourseType, 'id'>);
: this.api.create(payload as Omit<CourseApiResponse, 'id'>);
req$.subscribe(() => {
this.closeModal();
@@ -412,7 +394,7 @@ export class Course {
return 3; // Default
};
const requiredHorses = getRequiredHorses(c.type);
const requiredHorses = 3;
// Collect all selected horses (flatten the places array)
const allHorses: number[] = places