Skip to content

Commit 6f5423f

Browse files
committed
Clean up dynamic select component
1 parent 0a28c00 commit 6f5423f

File tree

2 files changed

+58
-37
lines changed

2 files changed

+58
-37
lines changed

src/components/ui/dashboard/dynamic-api-select.tsx

Lines changed: 10 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -10,6 +10,8 @@ interface DynamicApiSelectProps<T> {
1010
placeholder?: string;
1111
getOptionLabel: (item: T) => string;
1212
getOptionValue: (item: T) => string;
13+
elementId: string;
14+
groupByDate?: boolean;
1315
}
1416

1517
interface ApiResponse<T> {
@@ -24,7 +26,9 @@ export function DynamicApiSelect<T>({
2426
onChange,
2527
placeholder = "Select an organization",
2628
getOptionLabel,
27-
getOptionValue
29+
getOptionValue,
30+
elementId,
31+
groupByDate
2832
}: DynamicApiSelectProps<T>) {
2933
const { data: response, isLoading, error } = useApiData<ApiResponse<T>>(url, { method, params });
3034
const [value, setValue] = useState<string>('');
@@ -41,11 +45,13 @@ export function DynamicApiSelect<T>({
4145
const items = response.data;
4246

4347
return (
44-
<Select value={value} onValueChange={handleValueChange}>
45-
<SelectTrigger className="w-[180px]">
48+
<Select
49+
value={value}
50+
onValueChange={handleValueChange}>
51+
<SelectTrigger id={elementId} className='w-auto'>
4652
<SelectValue placeholder={placeholder} />
4753
</SelectTrigger>
48-
<SelectContent>
54+
<SelectContent className='w-full'>
4955
{items.map((item, index) => (
5056
<SelectItem key={index} value={getOptionValue(item)}>
5157
{getOptionLabel(item)}

src/components/ui/dashboard/join-coaching-session.tsx

Lines changed: 48 additions & 33 deletions
Original file line numberDiff line numberDiff line change
@@ -1,75 +1,90 @@
1-
import React, { useState } from 'react';
1+
import React, { MouseEventHandler, useState } from 'react';
22
import { Id } from "@/types/general";
3+
import Link from 'next/link';
34
import { DynamicApiSelect } from './dynamic-api-select';
45
import { Card, CardContent, CardHeader, CardTitle } from "@/components/ui/card";
56
import { Organization } from '@/types/organization';
67
import { CoachingRelationshipWithUserNames } from '@/types/coaching_relationship_with_user_names';
78
import { CoachingSession } from '@/types/coaching-session';
89
import { DateTime } from 'ts-luxon';
10+
import { Label } from "@/components/ui/label";
11+
import { Button } from '../button';
12+
913

1014
export interface CoachingSessionCardProps {
1115
userId: Id;
1216
}
1317

1418
export function JoinCoachingSession({ userId: userId }: CoachingSessionCardProps) {
15-
const [organization, setOrganizations] = useState<string | null>(null);
16-
const [relationship, setRelationships] = useState<string | null>(null);
17-
const [sessions, setSessions] = useState<string | null>(null);
18-
19-
const handleOrganizationSelection = (value: string) => {
20-
setOrganizations(value)
21-
setRelationships(null) // Reset second selection when first changes
22-
}
23-
24-
const handleRelationshipSelection = (value: string) => {
25-
setRelationships(value);
26-
setSessions(null);
27-
}
28-
29-
const handleSessionSelection = (value: string) => {
30-
setSessions(value);
31-
}
19+
const [organizationId, setOrganizationId] = useState<string | null>(null);
20+
const [relationshipId, setRelationshipId] = useState<string | null>(null);
21+
const [sessionId, setSessionId] = useState<string | null>(null);
3222

3323
return (
3424
<Card className="w-[300px]">
3525
<CardHeader>
36-
<CardTitle>Make Your Selection</CardTitle>
26+
<CardTitle>Join a Coaching Session</CardTitle>
3727
</CardHeader>
38-
<CardContent>
39-
<div className="space-y-4">
28+
<CardContent className='grid gap-6'>
29+
<div className="grid gap-2">
30+
<Label htmlFor='organization-selector'>Organization</Label>
31+
4032
<DynamicApiSelect<Organization>
4133
url="/organizations"
4234
params={{ userId }}
43-
onChange={handleOrganizationSelection}
35+
onChange={setOrganizationId}
4436
placeholder="Select an organization"
4537
getOptionLabel={(org) => org.name}
4638
getOptionValue={(org) => org.id.toString()}
39+
elementId='organization-selector'
4740
/>
48-
{organization && (
41+
</div>
42+
{organizationId && (
43+
<div className="grid gap-2">
44+
<Label htmlFor='relationship-selector'>Relationship</Label>
45+
4946
<DynamicApiSelect<CoachingRelationshipWithUserNames>
50-
url={`/organizations/${organization}/coaching_relationships`}
51-
params={{ organization }}
52-
onChange={handleRelationshipSelection}
47+
url={`/organizations/${organizationId}/coaching_relationships`}
48+
params={{ organizationId }}
49+
onChange={setRelationshipId}
5350
placeholder="Select coaching relationship"
54-
getOptionLabel={(relationship) => relationship.coach_first_name}
51+
getOptionLabel={
52+
(relationship) =>
53+
`${relationship.coach_first_name} ${relationship.coach_last_name} -> ${relationship.coachee_first_name} ${relationship.coach_last_name}`
54+
}
5555
getOptionValue={(relationship) => relationship.id.toString()}
56+
elementId='relationship-selector'
5657
/>
57-
)}
58-
{relationship && (
58+
</div>
59+
)}
60+
{relationshipId && (
61+
<div className="grid gap-2">
62+
<Label htmlFor='session-selector'>Coaching Session</Label>
63+
5964
<DynamicApiSelect<CoachingSession>
6065
url="/coaching_sessions"
6166
params={{
62-
coaching_relationship_id: relationship,
67+
coaching_relationship_id: relationshipId,
6368
from_date: DateTime.now().minus({ month: 1 }).toISODate(),
6469
to_Date: DateTime.now().plus({ month: 1 }).toISODate()
6570
}}
66-
onChange={handleRelationshipSelection}
71+
onChange={setSessionId}
6772
placeholder="Select coaching session"
6873
getOptionLabel={(session) => session.date.toString()}
6974
getOptionValue={(session) => session.id.toString()}
75+
elementId='session-selector'
7076
/>
71-
)}
72-
</div>
77+
</div>
78+
)}
79+
{sessionId && (
80+
<div className='grid gap-2'>
81+
<Button variant='outline' className='w-full'>
82+
<Link href={`/coaching-sessions/${sessionId}`}>
83+
Join Session
84+
</Link>
85+
</Button>
86+
</div>
87+
)}
7388
</CardContent>
7489
</Card>
7590
)

0 commit comments

Comments
 (0)