Skip to content

Commit 30a2c92

Browse files
committed
Added Batch API endpoint
1 parent cd81aba commit 30a2c92

File tree

3 files changed

+116
-62
lines changed

3 files changed

+116
-62
lines changed

src/API/Types.ts

+7
Original file line numberDiff line numberDiff line change
@@ -42,3 +42,10 @@ export interface IntroEvalsForm {
4242
social_events: string | null,
4343
comments: string | null,
4444
}
45+
46+
export interface Batch {
47+
name: string,
48+
members: string[],
49+
creator: string,
50+
conditions: string[]
51+
}

src/pages/Slideshow/BatchSlide.tsx

+64-48
Original file line numberDiff line numberDiff line change
@@ -1,63 +1,79 @@
11
import { useState } from "react";
22
import { Button, Col, Container, Row } from "reactstrap"
3+
import { Batch } from "../../API/Types";
34

45
const BatchSlide = (props: {
5-
name: string,
6-
names: string[],
6+
batch: Batch,
77
onPassFail: (passed: boolean) => void
88
}) => {
99

1010
const [passed, setPassed] = useState<string | null>(null);
1111

1212
return (
13-
<section data-transition="slide" className="vw-100">
14-
<Container className="d-flex flex-column vh-100 px-0 w-100">
15-
<Row>
16-
<Col className="text-center">
17-
<h2>{props.name}</h2>
18-
</Col>
19-
</Row>
20-
<Row>
13+
<section data-transition="slide">
14+
<section data-transition="slide" className="vw-100">
15+
<Container className="d-flex flex-column vh-100 px-0 w-100">
16+
<Row>
17+
<Col className="text-center">
18+
<h2>{props.batch.name}</h2>
19+
</Col>
20+
</Row>
21+
<Row>
22+
{
23+
props.batch.members.map((f, i) =>
24+
<Col key={i} className="py-0 m-0 col-2">
25+
<p className="batch-name py-1 m-0">{f}</p>
26+
</Col>
27+
)
28+
}
29+
</Row>
2130
{
22-
props.names.map((f, i) =>
23-
<Col key={i} className="py-0 m-0 col-2">
24-
<p className="batch-name py-1 m-0">{f}</p>
25-
</Col>
26-
)
31+
passed == null ?
32+
<Row className="text-center m-3 py-3 align-self-center">
33+
<Button
34+
className="mr-3 shadow-none border-success border rounded pf-button"
35+
onClick={_ => {
36+
props.onPassFail(true);
37+
setPassed("Passed");
38+
}}
39+
>
40+
<h1 className="text-success px-5">Pass</h1>
41+
</Button>
42+
<Button
43+
className="mr-3 shadow-none disband-gray border rounded pf-button"
44+
onClick={_ => setPassed("Disbanded")}
45+
>
46+
<h1 className="px-5 disband-gray">Disband</h1>
47+
</Button>
48+
<Button
49+
className="mr-3 shadow-none border-danger border rounded pf-button"
50+
onClick={_ => {
51+
props.onPassFail(false);
52+
setPassed("Failed");
53+
}}
54+
>
55+
<h1 className="text-danger px-5">Fail</h1>
56+
</Button>
57+
</Row>
58+
:
59+
<h3 className={`py-3 my-3 ${passed === "Passed" ? "text-success" : (passed == "Failed" ? "text-danger" : "")}`}>{passed}</h3>
2760
}
28-
</Row>
29-
{
30-
passed == null ?
31-
<Row className="text-center m-3 py-3 align-self-center">
32-
<Button
33-
className="mr-3 shadow-none border-success border rounded pf-button"
34-
onClick={_ => {
35-
props.onPassFail(true);
36-
setPassed("Passed");
37-
}}
38-
>
39-
<h1 className="text-success px-5">Pass</h1>
40-
</Button>
41-
<Button
42-
className="mr-3 shadow-none disband-gray border rounded pf-button"
43-
onClick={_ => setPassed("Disbanded")}
44-
>
45-
<h1 className="px-5 disband-gray">Disband</h1>
46-
</Button>
47-
<Button
48-
className="mr-3 shadow-none border-danger border rounded pf-button"
49-
onClick={_ => {
50-
props.onPassFail(false);
51-
setPassed("failed");
52-
}}
53-
>
54-
<h1 className="text-danger px-5">Fail</h1>
55-
</Button>
56-
</Row>
57-
:
58-
<h3 className={`py-3 my-3 ${passed === "Success" ? "text-success" : (passed == "Failed" ? "text-danger" : "")}`}>{passed}</h3>
59-
}
60-
</Container>
61+
</Container>
62+
</section>
63+
<section data-transition="slide" className="vw-100">
64+
<Container className="d-flex flex-column vh-100 px-0 w-100">
65+
<Row>
66+
<Col>
67+
<h2>Creator: {props.batch.creator}</h2>
68+
</Col>
69+
</Row>
70+
<Row className="py-3">
71+
<Col>
72+
{props.batch.conditions.map(c => <p>{c}</p>)}
73+
</Col>
74+
</Row>
75+
</Container>
76+
</section>
6177
</section>
6278
)
6379
}

src/pages/Slideshow/IntroEvalsSlideshow.tsx

+45-14
Original file line numberDiff line numberDiff line change
@@ -5,10 +5,11 @@ import 'reveal.js/dist/reset.css'
55
import 'reveal.js/dist/reveal.css'
66
import 'reveal.js/dist/theme/white.css'
77
import './index.css'
8-
import { IntroEvalsSummary } from "../../API/Types";
8+
import { Batch, IntroEvalsSummary } from "../../API/Types";
99
import { getJSON, toastError } from "../../API/API";
10-
import { Container } from "reactstrap";
10+
import { Col, Container, Row } from "reactstrap";
1111
import BatchSlide from "./BatchSlide";
12+
import NumberBox from "./NumberBox";
1213

1314
const IntroEvalsSlideshow = () => {
1415

@@ -20,38 +21,68 @@ const IntroEvalsSlideshow = () => {
2021
slides.initialize();
2122
}
2223

24+
const [removedMembers, setRemovedMembers] = useState<string[]>([]);
25+
2326
const [frosh, setFrosh] = useState<IntroEvalsSummary[]>([]);
2427

2528
useEffect(() => {
2629
getJSON<IntroEvalsSummary[]>("/api/evals/intro")
27-
.then(setFrosh).then(initSlides)
30+
.then(setFrosh)
31+
.then(initSlides)
2832
.catch(toastError("Unable to fetch Intro Evals data"));
2933
}, [])
3034

31-
interface Batch {
32-
name: string,
33-
names: string[],
34-
}
35+
const [batches, setBatches] = useState<Batch[]>([]);
36+
37+
useEffect(() => {
38+
getJSON<Batch[]>("/api/batch")
39+
.then(e => setBatches(e.map(b => ({
40+
...b,
41+
members: b.members.map(m => m.split(",")[0]),
42+
}))))
43+
.catch(toastError("Unable to fetch Batches"))
44+
}, []);
3545

36-
const batches: Batch[] = [];
46+
const passFailBatch = (batch: Batch) => (pass: boolean) => {
47+
setRemovedMembers([...removedMembers, ...batch.members])
48+
}
3749

3850
return (
3951
<div className="reveal vh-100 vw-100">
4052
<div className="slides w-100" data-transition="slide">
53+
{/* placeholder, because slideshow doesn't work unless at least one slide is present from the beginning*/}
4154
<section data-transition="slide" className="vw-100">
42-
<Container className="d-flex flex-column vh-100 px-0 d-xl-flex w-100">
43-
<h2>Intro Evals Slideshow</h2>
44-
{/* placeholder, because slideshow doesn't work unless at least one slide is present from the beginning*/}
45-
</Container>
55+
<section data-transition="slide" className="vw-100">
56+
<Container className="d-flex flex-column vh-100 px-0 d-xl-flex w-100">
57+
<h2>Intro Evals Slideshow</h2>
58+
<Row className="text-center align-self-center w-100 justify-content-center py-3">
59+
<Col className="col-3">
60+
<NumberBox text={`${frosh.length}`} subtext="Intro Members" success={true} />
61+
</Col>
62+
<Col className="col-3">
63+
<NumberBox text={`${batches.length}`} subtext="Batches" success={true} />
64+
</Col>
65+
</Row>
66+
</Container>
67+
</section>
68+
<section data-transition="slide" className="vw-100">
69+
<Container className="d-flex flex-column vh-100 px-0 d-xl-flex w-100">
70+
<p>Hi :)</p>
71+
</Container>
72+
</section>
4673
</section>
4774
{
4875
batches.map((b, i) =>
49-
<BatchSlide key={i} name={b.name} names={b.names} onPassFail={(pass) => setFrosh(frosh.filter(f => !b.names.includes(f.name)))} />
76+
<BatchSlide
77+
key={i}
78+
batch={b}
79+
onPassFail={passFailBatch(b)}
80+
/>
5081
)
5182
}
5283

5384
{
54-
frosh.sort((a, b) => a.name.localeCompare(b.name)).map((f, i) =>
85+
frosh.filter(f => !removedMembers.includes(f.name)).sort((a, b) => a.name.localeCompare(b.name)).map((f, i) =>
5586
<Slide
5687
key={i}
5788
uid={f.uid}

0 commit comments

Comments
 (0)