mirror of
https://github.com/siop-spelev/siop2.git
synced 2026-08-08 12:41:54 +00:00
feat(r2.4): portail public QR — signalement sans compte, suivi par jeton
- 3 routes publiques /portal (les seules @Public métier), throttlées
(@nestjs/throttler : 10 signalements/min, 60 lectures/min) : résolution
du QR, signalement (retourne un jeton de suivi opaque), suivi par
référence + jeton — pas de jeton, pas de lecture, jamais de liste
- migration r2_portail : Request.publicToken (unique)
- page /q/{réf} fidèle à l'écran 6 validé R0 (mobile d'abord) : équipement
prérempli « détecté par le QR », interrupteur personne bloquée,
suivi sans jargon Reçu → Intervention → Résolu (dérivé de l'OT lié),
rejet affiché « Sans suite : {motif} », photo annoncée (upload R3) ;
signalements gardés sur le téléphone (localStorage, 10 max)
- e2e : LA boucle produit — gardien sans compte → traitement → ✓ Résolu ;
11 tests Playwright verts, 50 tests API, 52 opérations au contrat
- générateur OpenAPI : paramètres non-« id » plus typés uuid
Co-Authored-By: Claude Fable 5 <noreply@anthropic.com>
This commit is contained in:
@@ -38,6 +38,12 @@ import {
|
||||
UsersResponseSchema,
|
||||
UserUpdateSchema,
|
||||
} from './schemas/users-admin';
|
||||
import {
|
||||
PortalAssetSchema,
|
||||
PortalRequestCreatedSchema,
|
||||
PortalRequestCreateSchema,
|
||||
PortalRequestStatusSchema,
|
||||
} from './schemas/portail';
|
||||
import {
|
||||
MeterReadingCreateSchema,
|
||||
MetersResponseSchema,
|
||||
@@ -413,6 +419,52 @@ export const API_CONTRACT: ApiOperation[] = [
|
||||
404: { description: 'Inconnue' },
|
||||
},
|
||||
},
|
||||
// ————— R2 · Portail public (QR cabine — aucun compte) —————
|
||||
{
|
||||
operationId: 'getPortalAsset',
|
||||
method: 'get',
|
||||
path: '/portal/assets/{reference}',
|
||||
summary: 'Résoudre le QR scanné (référence → appareil, préremplissage)',
|
||||
tags: ['portal'],
|
||||
isPublic: true,
|
||||
pathParams: ['reference'],
|
||||
responses: {
|
||||
200: { description: 'Appareil', name: 'PortalAsset', schema: PortalAssetSchema },
|
||||
404: { description: 'Référence inconnue' },
|
||||
},
|
||||
},
|
||||
{
|
||||
operationId: 'createPortalRequest',
|
||||
method: 'post',
|
||||
path: '/portal/requests',
|
||||
summary: 'Signaler sans compte — renvoie le jeton de suivi (à garder sur le téléphone)',
|
||||
tags: ['portal'],
|
||||
isPublic: true,
|
||||
request: { name: 'PortalRequestCreate', schema: PortalRequestCreateSchema },
|
||||
responses: {
|
||||
201: {
|
||||
description: 'Signalement enregistré',
|
||||
name: 'PortalRequestCreated',
|
||||
schema: PortalRequestCreatedSchema,
|
||||
},
|
||||
404: { description: 'Référence inconnue' },
|
||||
429: { description: 'Trop de signalements — réessayez dans une minute' },
|
||||
},
|
||||
},
|
||||
{
|
||||
operationId: 'getPortalRequestStatus',
|
||||
method: 'get',
|
||||
path: '/portal/requests/{reference}/{token}',
|
||||
summary: 'Suivi sans jargon (Reçu → Intervention → Résolu) — jeton requis',
|
||||
tags: ['portal'],
|
||||
isPublic: true,
|
||||
pathParams: ['reference', 'token'],
|
||||
responses: {
|
||||
200: { description: 'Avancement', name: 'PortalRequestStatus', schema: PortalRequestStatusSchema },
|
||||
404: { description: 'Signalement inconnu ou jeton invalide' },
|
||||
},
|
||||
},
|
||||
|
||||
// ————— R2 · Préventif & compteurs —————
|
||||
{
|
||||
operationId: 'listTaskTemplates',
|
||||
|
||||
Reference in New Issue
Block a user