Merge branch 'createNewLicenseType' of https://github.com/Tria-plc/emaui into createNewLicenseType

This commit is contained in:
Estifo77
2026-09-02 13:54:24 +03:00
26 changed files with 929 additions and 378 deletions

View File

@@ -1,5 +1,6 @@
import { baseApi } from '../../base-api';
import type {
ExamStateView,
AppNotification,
ApplicationDetail,
ApplicationKind,
@@ -27,7 +28,6 @@ import type {
CompletionEffect,
DocumentDecision,
DocumentReview,
EligibleExam,
ExportResult,
LicenseTemplate,
Paginated,
@@ -867,44 +867,22 @@ export const licensingApi = baseApi
}),
/**
* Exam sittings valid for this application's rank — what the
* schedule-exam picker offers, instead of every exam in the system.
* The examination leg behind one application, as the server reads it.
*
* The COC detail page used to infer this from the application status
* alone, which is how it kept offering "Schedule exam" for a paper the
* candidate had already sat and passed.
*/
getEligibleExams: builder.query<EligibleExam[], string>({
query: (id) => ({ url: `/license-application-review/${id}/eligible-exams` }),
getExamStateForApplication: builder.query<ExamStateView, string>({
query: (id) => ({ url: `/exams/applications/${id}/state` }),
providesTags: (_r, _e, id) => [itemTag('LicenseApplication', id)],
}),
/** Places a candidate who has paid the examination fee into a sitting. */
scheduleExam: builder.mutation<
LicenseApplication,
{ id: string; examId: string; admissionNumber?: string; examDate?: string }
>({
query: ({ id, examDate: _examDate, ...body }) => ({
// Matches the controller's `:id/exam-scheduled` route — `examDate`
// is UI-only context for the confirmation toast, not part of
// `MarkExamScheduledDto`, so it never goes on the wire.
url: `/license-application-review/${id}/exam-scheduled`,
method: 'POST',
body,
}),
invalidatesTags: (_r, error, { id }) =>
error ? [] : [itemTag('LicenseApplication', id), listTag('ApplicationQueue')],
}),
/** Records a published examination result (pass or fail). */
recordExamOutcome: builder.mutation<
LicenseApplication,
{ id: string; passed: boolean; score?: number }
>({
query: ({ id, ...body }) => ({
url: `/license-application-review/${id}/exam-outcome`,
method: 'POST',
body,
}),
invalidatesTags: (_r, error, { id }) =>
error ? [] : [itemTag('LicenseApplication', id), listTag('ApplicationQueue')],
}),
// No `getEligibleExams`, `scheduleExam` or `recordExamOutcome`: the
// endpoints behind them are gone. Sittings are published as master
// schedules and candidates register for one themselves, and an outcome
// is what the exam engine computed and a supervisor approved — neither
// is the COC queue's to write.
/**
* A failed candidate asks for another sitting. Re-opens the examination
@@ -1212,8 +1190,17 @@ export const licensingApi = baseApi
url: `/license-application-review/${id}/issue-certificate`,
method: 'POST',
}),
// The certificate this writes is what `License` lists read, so the
// issued register and the holder's own licences refresh with it —
// without them an officer issues a certificate that nobody's list shows.
invalidatesTags: (_r, error, id) =>
error ? [] : [itemTag('LicenseApplication', id), listTag('ApplicationQueue')],
error
? []
: [
itemTag('LicenseApplication', id),
listTag('ApplicationQueue'),
listTag('License'),
],
}),
// ------------------------------------------------------------- pickup
@@ -1434,6 +1421,7 @@ export const {
useUpdateLicenseValidityMutation,
useGetLicenseTypeRequirementsQuery,
useCreateApplicationMutation,
useGetExamStateForApplicationQuery,
useDiscardApplicationMutation,
useGetMyApplicationsQuery,
useGetApplicationQuery,
@@ -1493,9 +1481,6 @@ export const {
useApproveDocumentsMutation,
useFinalApproveMutation,
useRejectApplicationMutation,
useGetEligibleExamsQuery,
useScheduleExamMutation,
useRecordExamOutcomeMutation,
useRetakeExamMutation,
useConfirmPaymentMutation,
useScheduleIssuanceMutation,