[OCaml] High Intensity Training Online
refactor build the page viewer in one place
Thirteen handlers each spelled out the same record projecting the signed-in trainee into the page shell's viewer, and one controller had already grown its own local helper. Lift that helper into the shared kit as viewer_of and use it everywhere, so the projection has one definition.
Changed files
lib/web/handlers.ml
@@ -30,12 +30,7 @@
30
30
Dream.any "/**" (fun request ->
31
31
current_trainee t request >>= function
32
32
| Some trainee ->
33
Removed:
let viewer =
34
Removed:
{
35
Removed:
View_model.Viewer.username =
36
Removed:
Trainee.username_to_string trainee.Trainee.username;
37
Removed:
}
38
Removed:
in
33
Added:
let viewer = viewer_of trainee in
39
34
html ~status:`Not_Found
40
35
(Pages.error_page ~viewer ~request ~status:404 ())
41
36
| None -> html ~status:`Not_Found (Pages.error_page ~status:404 ()))
lib/web/handlers_app_feedback.ml
@@ -36,12 +36,7 @@
36
36
}
37
37
38
38
let show t trainee request =
39
Removed:
let viewer =
40
Removed:
{
41
Removed:
View_model.Viewer.username =
42
Removed:
Trainee.username_to_string trainee.Trainee.username;
43
Removed:
}
44
Removed:
in
39
Added:
let viewer = viewer_of trainee in
45
40
Service.in_progress t.service trainee.Trainee.id >>= fun in_progress ->
46
41
Service.app_feedback t.service trainee.Trainee.id >>= fun reports ->
47
42
html
lib/web/handlers_current_workout.ml
@@ -37,12 +37,7 @@
37
37
(* Render the workout-in-progress page, or redirect Home when nothing is in
38
38
progress. Shared by the GET view and the partial responses below. *)
39
39
let render_workout t trainee request =
40
Removed:
let viewer =
41
Removed:
{
42
Removed:
View_model.Viewer.username =
43
Removed:
Trainee.username_to_string trainee.Trainee.username;
44
Removed:
}
45
Removed:
in
40
Added:
let viewer = viewer_of trainee in
46
41
Service.in_progress t.service trainee.Trainee.id >>= function
47
42
| Some workout ->
48
43
Service.workout_log t.service trainee.Trainee.id >>= fun log ->
lib/web/handlers_import.ml
@@ -72,9 +72,6 @@
72
72
workouts = List.map workout_view (Workout_import.batch_workouts batch);
73
73
}
74
74
75
Removed:
let viewer_of (trainee : Trainee.t) =
76
Removed:
{ View_model.Viewer.username = Trainee.username_to_string trainee.username }
77
Removed:
78
75
(* A distinct batch id even when a duplicate override re-imports the same
79
76
source. The fingerprint prefix, the import time in seconds, and a random
80
77
suffix keep two imports of one export apart, so an override never
lib/web/handlers_kit.ml
@@ -260,6 +260,11 @@
260
260
Recovery.timestamp_to_unix_seconds (Evidence.Workout.started_at workout))
261
261
in_progress
262
262
263
Added:
(* The signed-in trainee as the page shell shows them. Every authenticated
264
Added:
page builds this, so it lives here once. *)
265
Added:
let viewer_of (trainee : Trainee.t) : View_model.Viewer.t =
266
Added:
{ View_model.Viewer.username = Trainee.username_to_string trainee.username }
267
Added:
263
268
(* The slot a workout view should open on. An explicit [?slot=] query
264
269
wins when it names a real slot. Otherwise the view defaults to the first
265
270
incomplete slot. A [?slot=] out of range, or absent, falls back to the
lib/web/handlers_logbook.ml
@@ -246,12 +246,7 @@
246
246
: View_model.Logbook_entry.t)
247
247
248
248
let index t trainee request =
249
Removed:
let viewer =
250
Removed:
{
251
Removed:
View_model.Viewer.username =
252
Removed:
Trainee.username_to_string trainee.Trainee.username;
253
Removed:
}
254
Removed:
in
249
Added:
let viewer = viewer_of trainee in
255
250
Service.in_progress t.service trainee.Trainee.id >>= fun in_progress ->
256
251
Service.history t.service trainee.Trainee.id >>= fun records ->
257
252
Service.workout_log t.service trainee.Trainee.id >>= fun log ->
@@ -333,12 +328,7 @@
333
328
| _ -> redirect_with_flash request back Present.form_invalid
334
329
335
330
let show t trainee request id =
336
Removed:
let viewer =
337
Removed:
{
338
Removed:
View_model.Viewer.username =
339
Removed:
Trainee.username_to_string trainee.Trainee.username;
340
Removed:
}
341
Removed:
in
331
Added:
let viewer = viewer_of trainee in
342
332
Service.in_progress t.service trainee.Trainee.id >>= fun in_progress ->
343
333
Service.workout_log t.service trainee.Trainee.id >>= fun log ->
344
334
record_target t trainee.Trainee.id id >>= function
@@ -436,12 +426,7 @@
436
426
too little to draw a line are omitted. There is no search. The page shows
437
427
every chartable exercise. *)
438
428
let progress t trainee request =
439
Removed:
let viewer =
440
Removed:
{
441
Removed:
View_model.Viewer.username =
442
Removed:
Trainee.username_to_string trainee.Trainee.username;
443
Removed:
}
444
Removed:
in
429
Added:
let viewer = viewer_of trainee in
445
430
let point_of o : View_model.Progress_page.point =
446
431
let effort = Evidence.Observation.effort o in
447
432
let at =
lib/web/handlers_overview.ml
@@ -99,12 +99,7 @@
99
99
}
100
100
101
101
let page t trainee request =
102
Removed:
let viewer =
103
Removed:
{
104
Removed:
View_model.Viewer.username =
105
Removed:
Trainee.username_to_string trainee.Trainee.username;
106
Removed:
}
107
Removed:
in
102
Added:
let viewer = viewer_of trainee in
108
103
Service.in_progress t.service trainee.Trainee.id >>= function
109
104
| Some workout ->
110
105
let workout_name =
@@ -147,12 +142,7 @@
147
142
let home t trainee request = page t trainee request >>= html
148
143
149
144
let routines t trainee request =
150
Removed:
let viewer =
151
Removed:
{
152
Removed:
View_model.Viewer.username =
153
Removed:
Trainee.username_to_string trainee.Trainee.username;
154
Removed:
}
155
Removed:
in
145
Added:
let viewer = viewer_of trainee in
156
146
Service.in_progress t.service trainee.Trainee.id >>= fun in_progress ->
157
147
html
158
148
(Pages.choose_routine request
@@ -178,12 +168,7 @@
178
168
| Error _ -> not_found Present.unknown_routine)
179
169
180
170
let routine t trainee request =
181
Removed:
let viewer =
182
Removed:
{
183
Removed:
View_model.Viewer.username =
184
Removed:
Trainee.username_to_string trainee.Trainee.username;
185
Removed:
}
186
Removed:
in
171
Added:
let viewer = viewer_of trainee in
187
172
Service.in_progress t.service trainee.Trainee.id >>= fun in_progress ->
188
173
Service.active_routine t.service trainee.Trainee.id >>= function
189
174
| Some (_, routine) ->
lib/web/handlers_profile.ml
@@ -12,12 +12,7 @@
12
12
(* The profile page. A [?changed=] query set by a successful redirect shows
13
13
a confirmation notice, so a refresh never re-posts a change. *)
14
14
let show t trainee request =
15
Removed:
let viewer =
16
Removed:
{
17
Removed:
View_model.Viewer.username =
18
Removed:
Trainee.username_to_string trainee.Trainee.username;
19
Removed:
}
20
Removed:
in
15
Added:
let viewer = viewer_of trainee in
21
16
Service.in_progress t.service trainee.Trainee.id >>= fun in_progress ->
22
17
let notice =
23
18
match Dream.query request "changed" with
@@ -31,12 +26,7 @@
31
26
~viewer ?notice ())
32
27
33
28
let render_error t trainee request ?username_error ?password_error () =
34
Removed:
let viewer =
35
Removed:
{
36
Removed:
View_model.Viewer.username =
37
Removed:
Trainee.username_to_string trainee.Trainee.username;
38
Removed:
}
39
Removed:
in
29
Added:
let viewer = viewer_of trainee in
40
30
Service.in_progress t.service trainee.Trainee.id >>= fun in_progress ->
41
31
html ~status:`Bad_Request
42
32
(Pages.profile request
lib/web/handlers_settings.ml
@@ -17,12 +17,7 @@
17
17
| _ -> "light"
18
18
19
19
let show t trainee request =
20
Removed:
let viewer =
21
Removed:
{
22
Removed:
View_model.Viewer.username =
23
Removed:
Trainee.username_to_string trainee.Trainee.username;
24
Removed:
}
25
Removed:
in
20
Added:
let viewer = viewer_of trainee in
26
21
Service.in_progress t.service trainee.Trainee.id >>= fun in_progress ->
27
22
html
28
23
(Pages.settings request