11import * as O from 'fp-ts/Option' ;
22import * as TE from 'fp-ts/TaskEither' ;
33import * as RA from 'fp-ts/ReadonlyArray' ;
4+ import * as RR from 'fp-ts/ReadonlyRecord' ;
45
56import { Dependencies } from '../../dependencies' ;
67import { SheetDataTable } from '../../sync-worker/google/sheet-data-table' ;
78import { pipe } from 'fp-ts/lib/function' ;
89import { Equipment , MemberCoreInfo } from '../shared-state/return-types' ;
910import { DateTime , Duration } from 'luxon' ;
1011import { ReadonlyRecord } from 'fp-ts/lib/ReadonlyRecord' ;
11- import { UUID } from 'io-ts- types' ;
12+ import { EquipmentId } from '../../ types/equipment-id ' ;
1213
1314export type EquipmentQuizResults = {
1415 passedQuizes : SheetDataTable [ 'rows' ] ;
@@ -29,20 +30,23 @@ export type MemberAwaitingTraining = Pick<
2930 waitingSince : Date ;
3031} ;
3132
33+ const isPassed = ( row : SheetDataTable [ 'rows' ] [ 0 ] ) => row . percentage >= 100 ;
34+ const isFailed = ( row : SheetDataTable [ 'rows' ] [ 0 ] ) => ! isPassed ( row ) ;
35+
3236const extractPassedQuizes = (
3337 sheetData : SheetDataTable [ 'rows' ]
3438) : SheetDataTable [ 'rows' ] =>
3539 pipe (
3640 sheetData ,
37- RA . filter ( row => row . percentage === 100 )
41+ RA . filter ( isPassed )
3842 ) ;
3943
4044const extractFailedQuizes = (
4145 sheetData : SheetDataTable [ 'rows' ]
4246) : SheetDataTable [ 'rows' ] =>
4347 pipe (
4448 sheetData ,
45- RA . filter ( row => row . percentage < 100 )
49+ RA . filter ( isFailed )
4650 ) ;
4751
4852const getQuizResults = (
@@ -128,20 +132,69 @@ export const getFullQuizResultsForEquipment = (
128132 ) ;
129133
130134export type FullQuizResultsForMember = {
131- equipmentQuizPassedAt : ReadonlyRecord < UUID , Date > ,
132- equipmentQuizAttempted : ReadonlyRecord < UUID , {
135+ equipmentQuizPassedAt : ReadonlyRecord < EquipmentId , ReadonlyArray < Date > > ,
136+ equipmentQuizAttempted : ReadonlyRecord < EquipmentId , ReadonlyArray < {
137+ response_submitted : Date ,
138+ sheet_id : string ;
139+ score : number ;
140+ max_score : number ;
141+ percentage : number ;
142+ } > > ,
143+ orphanedQuizAttempts : ReadonlyArray < {
133144 response_submitted : Date ,
134145 sheet_id : string ;
135146 score : number ;
136147 max_score : number ;
137148 percentage : number ;
138- } >
149+ } > ,
139150} ;
140151
141152export const getFullQuizResultsForMember = (
142- deps : Pick < Dependencies , 'sharedReadModel' | 'getSheetData ' > ,
153+ deps : Pick < Dependencies , 'sharedReadModel' | 'getSheetDataByMemberNumber ' > ,
143154 memberNumber : number
144- ) : TE . TaskEither < string , FullQuizResultsForMember > => {
145-
146-
147- } ;
155+ ) : TE . TaskEither < string , FullQuizResultsForMember > => pipe (
156+ deps . getSheetDataByMemberNumber ( memberNumber ) ,
157+ TE . map (
158+ qr => {
159+ const equipmentQuizPassedAt : Record < EquipmentId , Date [ ] > = { } ;
160+ const equipmentQuizAttempted : Record < EquipmentId , {
161+ response_submitted : Date ,
162+ sheet_id : string ;
163+ score : number ;
164+ max_score : number ;
165+ percentage : number ;
166+ } [ ] > = { } ;
167+ const orphanedQuizAttempts : {
168+ response_submitted : Date ,
169+ sheet_id : string ;
170+ score : number ;
171+ max_score : number ;
172+ percentage : number ;
173+ } [ ] = [ ] ;
174+ const trainingSheetMapping = deps . sharedReadModel . equipment . getTrainingSheetIdMapping ( ) ;
175+ for ( const row of qr ) {
176+ const equipmentId = RR . lookup ( row . sheet_id ) ( trainingSheetMapping ) ;
177+ if ( O . isNone ( equipmentId ) ) {
178+ orphanedQuizAttempts . push ( row ) ;
179+ } else {
180+ if ( isPassed ( row ) ) {
181+ if ( ! equipmentQuizPassedAt [ equipmentId . value ] ) {
182+ equipmentQuizPassedAt [ equipmentId . value ] = [ ] ;
183+ }
184+ equipmentQuizPassedAt [ equipmentId . value ] . push ( row . response_submitted ) ;
185+ } else {
186+ if ( ! equipmentQuizAttempted [ equipmentId . value ] ) {
187+ equipmentQuizAttempted [ equipmentId . value ] = [ ] ;
188+ }
189+ equipmentQuizAttempted [ equipmentId . value ] . push ( row ) ;
190+ }
191+ }
192+ }
193+ return {
194+ equipmentQuizPassedAt,
195+ equipmentQuizAttempted,
196+ orphanedQuizAttempts,
197+ }
198+ }
199+ )
200+ ) ;
0 commit comments