chore: heygermany customer project
Some checks failed
Main / Setup and Test (push) Has been cancelled
Main / Build Website (push) Has been cancelled

This commit is contained in:
e2e
2026-07-11 09:28:50 +02:00
commit aae77ea31e
398 changed files with 38345 additions and 0 deletions

View File

@@ -0,0 +1,189 @@
'use client'
import {
Container,
Stack,
Group,
Paper,
ThemeIcon,
Box,
Grid,
Flex,
Text,
rem,
useMantineTheme,
} from '@pikku/mantine/core'
import {
IconIdBadge2,
IconWorld,
IconBriefcase,
IconSchool,
} from '@tabler/icons-react'
import { Qualification } from './Qualification'
import { QualificationSectionStatusCard } from './QualificationSectionStatusCard'
import { CandidateResults } from '@heygermany/sdk'
import { useI18n } from '@/context/i18n-provider'
import { asI18n } from '@pikku/react'
interface QualificationData {
title: string
description: string
status: string
requirements: string[]
steps?: string[]
progress?: number
}
type SectionOut = {
key: "education" | "license" | "language" | "additional"
title: string
color: "education" | "license" | "language" | "additional"
icon: string
qualifications: QualificationData[]
}
const ICONS: Record<string, React.ReactElement> = {
school: <IconSchool size={38} />,
"id-badge": <IconIdBadge2 size={38} />,
world: <IconWorld size={38} />,
briefcase: <IconBriefcase size={38} />,
};
const getQualificationSectionStatus = (
title: string,
qualifications: QualificationData[]
) => {
const statuses = qualifications.map((q) => q.status)
if (statuses.includes('in-progress')) return 'in-progress'
if (statuses.every((s) => s === 'completed')) return 'completed'
if (statuses.every((s) => s === 'required')) return 'required'
if (statuses.includes('optional')) return 'optional'
return 'required'
}
function buildSections(candidateResults: CandidateResults, t: any): SectionOut[] {
return [
{
key: "education",
title: t('enums.qualificationsections.education'),
color: "education",
icon: "school",
qualifications: [candidateResults.education],
},
{
key: "license",
title: t('enums.qualificationsections.license'),
color: "license",
icon: "id-badge",
qualifications: [candidateResults.license],
},
{
key: "language",
title: t('enums.qualificationsections.language'),
color: "language",
icon: "world",
qualifications: [candidateResults.language],
},
{
key: "additional",
title: t('enums.qualificationsections.additional'),
color: "additional",
icon: "briefcase",
qualifications: [candidateResults.experience, candidateResults.copies, candidateResults.originals],
},
]
}
export const QualificationsSection: React.FunctionComponent<{ candidateResults: CandidateResults }> = ({ candidateResults }) => {
const t = useI18n()
const sections = buildSections(candidateResults, t)
const theme = useMantineTheme()
const mainSections = sections.slice(0, 3) // Education, License, Language
const additionalSection = sections[3] // Additional Requirements
return (
<>
<Container size="xl" py="xl" maw="full">
<Stack gap="xl">
<Flex wrap="wrap" gap="md" justify="center">
{sections.map((section, i) => (
<QualificationSectionStatusCard
key={i}
label={section.title}
status={section.color === 'additional' ? 'required' : getQualificationSectionStatus(section.title, section.qualifications)}
color={`var(--mantine-color-${section.color}-6)`}
icon={ICONS[section.icon]}
/>
))}
</Flex>
</Stack>
</Container>
<Box bg={theme.colors.gray[0]}>
<Container bg={theme.colors.gray[0]} size="xl" py="xl" maw="full">
<Grid mt="xl" grow>
{mainSections.map((section, sectionIndex) => (
<Grid.Col key={sectionIndex} span={{ base: 12, md: 4 }} mt="xl">
<Group align="center" mb="lg">
<ThemeIcon variant="transparent" color={section.color} size="xl" radius="md">{ICONS[section.icon]}</ThemeIcon>
<Text c={`${theme.colors.gray[7]}`} size="xl" fw={700}>
{asI18n(section.title)}
</Text>
</Group>
<Flex
gap="md"
flex={1}
align="stretch"
h='full'
>
{section.qualifications.map((qualification, qualIndex) => (
<Qualification
key={qualIndex}
title={qualification.title}
description={qualification.description}
status={qualification.status}
requirements={qualification.requirements}
steps={qualification.steps}
progress={qualification.progress}
/>
))}
</Flex>
</Grid.Col>
))}
</Grid>
<Box mb="md" mt={rem(80)}>
<Group align="center" mb="lg" gap="sm">
{ICONS[additionalSection.icon]}
<Text fw={700} size="xl">
{asI18n(additionalSection.title)}
</Text>
</Group>
<Grid>
{additionalSection.qualifications.map(
(qualification, qualIndex) => (
<Grid.Col key={qualIndex} span={{ base: 12, md: 4 }}>
<Paper shadow="xs" radius="lg" h="100%">
<Qualification
title={qualification.title}
description={qualification.description}
status={qualification.status}
requirements={qualification.requirements}
steps={qualification.steps}
progress={qualification.progress}
/>
</Paper>
</Grid.Col>
)
)}
</Grid>
</Box>
</Container>
</Box>
</>
)
}