SkateSpots/src/lib/becomeRoles.tsx

383 lines
23 KiB
TypeScript
Raw Blame History

This file contains ambiguous Unicode characters

This file contains Unicode characters that might be confused with other characters. If you think that this is intentional, you can safely ignore this warning. Use the Escape button to reveal them.

import { lazy, type ComponentType, type LazyExoticComponent } from 'react';
import {
Palette, SprayCan, Music, Gavel, Brush, Dumbbell, Tent, Sparkles,
} from 'lucide-react';
import { pickRateUnits } from '@/lib/labExtras';
import type { CraftFormConfig } from '@/components/CraftProfileForm';
import {
SKATE_ARTIST_KIND, ARTIST_SERVICE_LABELS, ARTIST_MEDIUM_LABELS, ARTIST_TOOL_LABELS,
SKATE_GRAFFITI_KIND, GRAFFITI_STYLE_LABELS, GRAFFITI_MEDIUM_LABELS, GRAFFITI_CONTEXT_LABELS,
SKATE_MUSICIAN_KIND, MUSICIAN_GENRE_LABELS, MUSICIAN_INSTRUMENT_LABELS,
SKATE_JUDGE_KIND, JUDGE_FORMAT_LABELS, JUDGE_SPECIALTY_LABELS, JUDGE_LEVEL_LABELS,
SKATE_ORGANIZER_KIND, ORGANIZER_EVENT_LABELS, ORGANIZER_SERVICE_LABELS, ORGANIZER_SCALE_LABELS,
SKATE_TATTOO_KIND, TATTOO_STYLE_LABELS, TATTOO_METHOD_LABELS,
SKATE_TRAINER_KIND, TRAINER_FOCUS_LABELS, TRAINER_INJURY_LABELS, TRAINER_CREDENTIAL_LABELS,
SKATE_BARBER_KIND, BARBER_SERVICE_LABELS, BARBER_STYLE_LABELS, BARBER_SETTING_LABELS,
} from '@/lib/types';
import {
ARTIST_SERVICE_KEYS, ARTIST_MEDIUM_KEYS, ARTIST_TOOL_KEYS,
GRAFFITI_STYLE_KEYS, GRAFFITI_MEDIUM_KEYS, GRAFFITI_CONTEXT_KEYS,
MUSICIAN_GENRE_KEYS, MUSICIAN_INSTRUMENT_KEYS,
JUDGE_FORMAT_KEYS, JUDGE_SPECIALTY_KEYS, JUDGE_LEVEL_KEYS,
ORGANIZER_EVENT_KEYS, ORGANIZER_SERVICE_KEYS, ORGANIZER_SCALE_KEYS,
TATTOO_STYLE_KEYS, TATTOO_METHOD_KEYS,
TRAINER_FOCUS_KEYS, TRAINER_INJURY_KEYS, TRAINER_CREDENTIAL_KEYS,
BARBER_SERVICE_KEYS, BARBER_STYLE_KEYS, BARBER_SETTING_KEYS,
} from '@/lib/labelKeys';
/**
* Single source of truth for every "become a …" role.
*
* There are two flavours:
* 1. `craft` roles — thin config over the shared <CraftProfileForm>. All the
* per-role difference lives here in data, not in 7 near-identical files.
* 2. `page` roles — genuinely bespoke pages (Coach, Filmer, Editor,
* Photographer, Skater, Builder) that carry extra machinery
* (SpotPicker, wallet/Pro logic, geohashing, etc.). Forcing these into a
* config would create a monster; instead they stay as their own lazy
* components and are simply *routed* through the same /become/:role slug.
*
* The router uses this map so the whole feature is one param route + redirects
* from the legacy /become-<slug> URLs, instead of 12 hardcoded route lines.
*/
interface CraftRole {
kind: 'craft';
seoTitle: string;
seoDescription: string;
/** Optional i18n keys (take precedence over the raw English fallbacks). */
seoTitleKey?: string;
seoDescriptionKey?: string;
config: CraftFormConfig;
}
interface PageRole {
kind: 'page';
/** Lazily-loaded bespoke page component (default export). */
component: LazyExoticComponent<ComponentType>;
}
export type BecomeRole = CraftRole | PageRole;
export const BECOME_ROLES: Record<string, BecomeRole> = {
// ── Bespoke pages (unchanged — just registered here for routing) ──
coach: { kind: 'page', component: lazy(() => import('@/pages/BecomeCoachPage')) },
filmer: { kind: 'page', component: lazy(() => import('@/pages/BecomeFilmerPage')) },
editor: { kind: 'page', component: lazy(() => import('@/pages/BecomeEditorPage')) },
photographer: { kind: 'page', component: lazy(() => import('@/pages/BecomePhotographerPage')) },
builder: { kind: 'page', component: lazy(() => import('@/pages/BecomeBuilderPage')) },
skater: { kind: 'page', component: lazy(() => import('@/pages/BecomeSkaterPage')) },
// ── Craft roles (data-driven over CraftProfileForm) ──
artist: {
kind: 'craft',
seoTitle: 'Become a Designer / Artist - SkateSpots',
seoDescription: 'List your skate design & art — board graphics, logos, posters, merch and more.',
seoTitleKey: 'becomeRolesUi.artist.seoTitle',
seoDescriptionKey: 'becomeRolesUi.artist.seoDescription',
config: {
kind: SKATE_ARTIST_KIND,
selfTag: 'skateartist',
identifier: 'artist-profile',
heading: 'Designer / Artist',
headingKey: 'becomeRolesUi.artist.heading',
tagline: 'Board graphics, logos, posters, merch — put your art on the scene',
taglineKey: 'becomeRolesUi.artist.tagline',
noun: 'artist',
nounKey: 'becomeRolesUi.artist.noun',
accentText: 'text-fuchsia-400',
accentBg: 'bg-fuchsia-600',
accentChip: 'bg-fuchsia-600 text-white border-fuchsia-600',
accentChipHover: 'hover:border-fuchsia-500/60 hover:text-fuchsia-400',
icon: Palette,
rateUnits: pickRateUnits('piece', 'project', 'hour', 'day'),
extraFields: [
{ tag: 'deliverables', label: 'Deliverables', labelKey: 'labUi.craftFields.deliverables', placeholder: 'e.g. print-ready files, source files, deck graphics', placeholderKey: 'becomeRolesUi.artist.deliverablesPlaceholder' },
{ tag: 'turnaround', label: 'Turnaround', labelKey: 'labUi.craftFields.turnaround', placeholder: 'e.g. 3–5 days', placeholderKey: 'becomeRolesUi.artist.turnaroundPlaceholder' },
],
rateLabel: 'Rate',
rateLabelKey: 'becomeRolesUi.artist.rateLabel',
portfolioLabel: 'Portfolio / Shop link',
portfolioLabelKey: 'becomeRolesUi.artist.portfolioLabel',
skillSections: [
{ title: 'What You Make', titleKey: 'becomeRolesUi.artist.sectionWhatYouMake', entries: Object.entries(ARTIST_SERVICE_LABELS), keyMap: ARTIST_SERVICE_KEYS, required: true },
{ title: 'Medium', titleKey: 'becomeRolesUi.artist.sectionMedium', entries: Object.entries(ARTIST_MEDIUM_LABELS), keyMap: ARTIST_MEDIUM_KEYS },
{ title: 'Software & Tools', titleKey: 'becomeRolesUi.artist.sectionSoftwareTools', entries: Object.entries(ARTIST_TOOL_LABELS), keyMap: ARTIST_TOOL_KEYS },
],
},
},
graffiti: {
kind: 'craft',
seoTitle: 'Offer Graffiti / Murals - SkateSpots',
seoDescription: 'List your graffiti & mural work — pieces, murals, skatepark art and more.',
seoTitleKey: 'becomeRolesUi.graffiti.seoTitle',
seoDescriptionKey: 'becomeRolesUi.graffiti.seoDescription',
config: {
kind: SKATE_GRAFFITI_KIND,
selfTag: 'skategraffiti',
identifier: 'graffiti-profile',
heading: 'Graffiti / Mural Artist',
headingKey: 'becomeRolesUi.graffiti.heading',
tagline: 'Pieces, murals, skatepark art — paint the scene',
taglineKey: 'becomeRolesUi.graffiti.tagline',
noun: 'graffiti artist',
nounKey: 'becomeRolesUi.graffiti.noun',
accentText: 'text-lime-400',
accentBg: 'bg-lime-500',
accentChip: 'bg-lime-500 text-black border-lime-500',
accentChipHover: 'hover:border-lime-500/60 hover:text-lime-400',
icon: SprayCan,
rateUnits: pickRateUnits('piece', 'project', 'day', 'hour'),
rateLabel: 'Rate',
rateLabelKey: 'becomeRolesUi.graffiti.rateLabel',
portfolioLabel: 'Portfolio link (IG, site)',
portfolioLabelKey: 'becomeRolesUi.graffiti.portfolioLabel',
skillSections: [
{ title: 'Style', titleKey: 'becomeRolesUi.graffiti.sectionStyle', entries: Object.entries(GRAFFITI_STYLE_LABELS), keyMap: GRAFFITI_STYLE_KEYS, required: true },
{ title: 'Medium', titleKey: 'becomeRolesUi.graffiti.sectionMedium', entries: Object.entries(GRAFFITI_MEDIUM_LABELS), keyMap: GRAFFITI_MEDIUM_KEYS },
{ title: 'Work Context', titleKey: 'becomeRolesUi.graffiti.sectionWorkContext', entries: Object.entries(GRAFFITI_CONTEXT_LABELS), keyMap: GRAFFITI_CONTEXT_KEYS },
],
extraFields: [
{ tag: 'crew', label: 'Graffiti Crew', labelKey: 'becomeRolesUi.graffiti.crewLabel', placeholder: 'Your writing crew (optional)', placeholderKey: 'becomeRolesUi.graffiti.crewPlaceholder', helper: 'Separate from your skate crew — the writers you paint with.', helperKey: 'becomeRolesUi.graffiti.crewHelper' },
{ tag: 'surfaces', label: 'Surfaces / Walls', labelKey: 'labUi.craftFields.surfaces', placeholder: 'e.g. concrete, brick, permitted walls', placeholderKey: 'becomeRolesUi.graffiti.surfacesPlaceholder' },
{ tag: 'max_size', label: 'Max Size', labelKey: 'labUi.craftFields.maxSize', placeholder: 'e.g. up to 10 m', placeholderKey: 'becomeRolesUi.graffiti.maxSizePlaceholder' },
],
},
},
musician: {
kind: 'craft',
seoTitle: 'Add a Music Profile - SkateSpots',
seoDescription: 'Skate and make music? List your band or solo project — genres, instruments and links.',
seoTitleKey: 'becomeRolesUi.musician.seoTitle',
seoDescriptionKey: 'becomeRolesUi.musician.seoDescription',
config: {
kind: SKATE_MUSICIAN_KIND,
selfTag: 'skatemusician',
identifier: 'musician-profile',
heading: 'Musician / Band',
headingKey: 'becomeRolesUi.musician.heading',
tagline: 'Skate and make music? Get booked for demos, jams & after-parties',
taglineKey: 'becomeRolesUi.musician.tagline',
noun: 'musician',
nounKey: 'becomeRolesUi.musician.noun',
accentText: 'text-sky-400',
accentBg: 'bg-sky-500',
accentChip: 'bg-sky-500 text-white border-sky-500',
accentChipHover: 'hover:border-sky-500/60 hover:text-sky-400',
icon: Music,
rateUnits: pickRateUnits('gig', 'event', 'hour', 'day'),
rateLabel: 'Booking Rate',
rateLabelKey: 'becomeRolesUi.musician.rateLabel',
portfolioLabel: 'Website / EPK link',
portfolioLabelKey: 'becomeRolesUi.musician.portfolioLabel',
skillSections: [
{ title: 'Genre', titleKey: 'becomeRolesUi.musician.sectionGenre', entries: Object.entries(MUSICIAN_GENRE_LABELS), keyMap: MUSICIAN_GENRE_KEYS, required: true },
{ title: 'Instruments & Role', titleKey: 'becomeRolesUi.musician.sectionInstruments', entries: Object.entries(MUSICIAN_INSTRUMENT_LABELS), keyMap: MUSICIAN_INSTRUMENT_KEYS },
],
extraFields: [
{ tag: 'act', label: 'Act Type', labelKey: 'becomeRolesUi.musician.actLabel', placeholder: 'solo / band / dj / producer', placeholderKey: 'becomeRolesUi.musician.actPlaceholder' },
{ tag: 'spotify', label: 'Spotify', labelKey: 'becomeRolesUi.musician.spotifyLabel', type: 'url', placeholder: 'https://open.spotify.com/…', placeholderKey: 'becomeRolesUi.musician.spotifyPlaceholder' },
{ tag: 'bandcamp', label: 'Bandcamp', labelKey: 'becomeRolesUi.musician.bandcampLabel', type: 'url', placeholder: 'https://…bandcamp.com', placeholderKey: 'becomeRolesUi.musician.bandcampPlaceholder' },
{ tag: 'soundcloud', label: 'SoundCloud', labelKey: 'becomeRolesUi.musician.soundcloudLabel', type: 'url', placeholder: 'https://soundcloud.com/…', placeholderKey: 'becomeRolesUi.musician.soundcloudPlaceholder' },
{ tag: 'youtube', label: 'YouTube', labelKey: 'becomeRolesUi.musician.youtubeLabel', type: 'url', placeholder: 'https://youtube.com/…', placeholderKey: 'becomeRolesUi.musician.youtubePlaceholder' },
{ tag: 'set_length', label: 'Set Length', labelKey: 'labUi.craftFields.setLength', placeholder: 'e.g. 30–45 min', placeholderKey: 'becomeRolesUi.musician.setLengthPlaceholder' },
{ tag: 'tech_rider', label: 'Tech Rider', labelKey: 'labUi.craftFields.techRider', placeholder: 'e.g. PA, mics, backline', placeholderKey: 'becomeRolesUi.musician.techRiderPlaceholder' },
],
},
},
judge: {
kind: 'craft',
seoTitle: 'Judge Skate Events - SkateSpots',
seoDescription: 'List yourself as a skate event judge — Game of S.K.A.T.E., best trick jams, contests, am series and world tour stops. Get booked to run fair, credible events.',
seoTitleKey: 'becomeRolesUi.judge.seoTitle',
seoDescriptionKey: 'becomeRolesUi.judge.seoDescription',
config: {
kind: SKATE_JUDGE_KIND,
selfTag: 'skatejudge',
identifier: 'judge-profile',
heading: 'Skate Event Judge',
headingKey: 'becomeRolesUi.judge.heading',
tagline: 'From flat-ground Game of S.K.A.T.E. to the World Destruction Tour — run it fair, run it credible',
taglineKey: 'becomeRolesUi.judge.tagline',
noun: 'judge',
nounKey: 'becomeRolesUi.judge.noun',
accentText: 'text-yellow-400',
accentBg: 'bg-yellow-500',
accentChip: 'bg-yellow-500 text-black border-yellow-500',
accentChipHover: 'hover:border-yellow-500/60 hover:text-yellow-400',
icon: Gavel,
rateUnits: pickRateUnits('event', 'day', 'hour'),
rateLabel: 'Day Rate / Fee',
rateLabelKey: 'becomeRolesUi.judge.rateLabel',
portfolioLabel: 'Results archive / profile link',
portfolioLabelKey: 'becomeRolesUi.judge.portfolioLabel',
skillSections: [
{ title: 'Event Formats', titleKey: 'becomeRolesUi.judge.sectionEventFormats', entries: Object.entries(JUDGE_FORMAT_LABELS), keyMap: JUDGE_FORMAT_KEYS, required: true },
{ title: 'Specialty', titleKey: 'becomeRolesUi.judge.sectionSpecialty', entries: Object.entries(JUDGE_SPECIALTY_LABELS), keyMap: JUDGE_SPECIALTY_KEYS },
{ title: 'Level / Circuit', titleKey: 'becomeRolesUi.judge.sectionLevelCircuit', entries: Object.entries(JUDGE_LEVEL_LABELS), keyMap: JUDGE_LEVEL_KEYS },
],
extraFields: [
{ tag: 'events_judged', label: 'Events Judged', labelKey: 'becomeRolesUi.judge.eventsJudgedLabel', placeholder: 'e.g. 40+ contests, 3 World Tour stops', placeholderKey: 'becomeRolesUi.judge.eventsJudgedPlaceholder', helper: 'Notable events, comps or tours you have officiated.', helperKey: 'becomeRolesUi.judge.eventsJudgedHelper' },
{ tag: 'travel', label: 'Travel', labelKey: 'labUi.craftFields.travel', placeholder: 'e.g. regional / nationwide / international', placeholderKey: 'becomeRolesUi.judge.travelPlaceholder' },
{ tag: 'certifications', label: 'Certifications', labelKey: 'labUi.craftFields.certifications', placeholder: 'e.g. national judging course', placeholderKey: 'becomeRolesUi.judge.certificationsPlaceholder' },
],
},
},
organizer: {
kind: 'craft',
seoTitle: 'Organize Skate Events - SkateSpots',
seoDescription: 'List yourself as a skate event organizer — street jams, best trick, contests, meetups, demos and tour stops. Get discovered and booked to run the session.',
seoTitleKey: 'becomeRolesUi.organizer.seoTitle',
seoDescriptionKey: 'becomeRolesUi.organizer.seoDescription',
config: {
kind: SKATE_ORGANIZER_KIND,
selfTag: 'skateorganizer',
identifier: 'organizer-profile',
heading: 'Event Organizer',
headingKey: 'becomeRolesUi.organizer.heading',
tagline: 'Jams, contests, meetups & demos — put on the session and bring the scene together',
taglineKey: 'becomeRolesUi.organizer.tagline',
noun: 'organizer',
nounKey: 'becomeRolesUi.organizer.noun',
accentText: 'text-teal-400',
accentBg: 'bg-teal-600',
accentChip: 'bg-teal-600 text-white border-teal-600',
accentChipHover: 'hover:border-teal-500/60 hover:text-teal-400',
icon: Tent,
rateUnits: pickRateUnits('event', 'day', 'project'),
rateLabel: 'Event Fee / Budget',
rateLabelKey: 'becomeRolesUi.organizer.rateLabel',
portfolioLabel: 'Past events / results link',
portfolioLabelKey: 'becomeRolesUi.organizer.portfolioLabel',
skillSections: [
{ title: 'Event Types', titleKey: 'becomeRolesUi.organizer.sectionEventTypes', entries: Object.entries(ORGANIZER_EVENT_LABELS), keyMap: ORGANIZER_EVENT_KEYS, required: true },
{ title: 'What You Handle', titleKey: 'becomeRolesUi.organizer.sectionWhatYouHandle', entries: Object.entries(ORGANIZER_SERVICE_LABELS), keyMap: ORGANIZER_SERVICE_KEYS },
{ title: 'Scale', titleKey: 'becomeRolesUi.organizer.sectionScale', entries: Object.entries(ORGANIZER_SCALE_LABELS), keyMap: ORGANIZER_SCALE_KEYS },
],
extraFields: [
{ tag: 'events_hosted', label: 'Events Organized', labelKey: 'becomeRolesUi.organizer.eventsHostedLabel', placeholder: 'e.g. 25 jams, 3 city comps', placeholderKey: 'becomeRolesUi.organizer.eventsHostedPlaceholder', helper: 'Notable events, comps or meetups you have run.', helperKey: 'becomeRolesUi.organizer.eventsHostedHelper' },
{ tag: 'insurance', label: 'Insurance', labelKey: 'labUi.craftFields.insurance', placeholder: 'e.g. public liability included', placeholderKey: 'becomeRolesUi.organizer.insurancePlaceholder' },
{ tag: 'permits', label: 'Permits', labelKey: 'labUi.craftFields.permits', placeholder: 'e.g. council permits handled', placeholderKey: 'becomeRolesUi.organizer.permitsPlaceholder' },
],
},
},
tattoo: {
kind: 'craft',
seoTitle: 'Become a Tattoo Artist - SkateSpots',
seoDescription: 'List your tattoo work for the skate scene — styles, flash, custom and more.',
seoTitleKey: 'becomeRolesUi.tattoo.seoTitle',
seoDescriptionKey: 'becomeRolesUi.tattoo.seoDescription',
config: {
kind: SKATE_TATTOO_KIND,
selfTag: 'skatetattoo',
identifier: 'tattoo-profile',
heading: 'Tattoo Artist',
headingKey: 'becomeRolesUi.tattoo.heading',
tagline: 'Ink for the scene — flash, custom, fine line & more',
taglineKey: 'becomeRolesUi.tattoo.tagline',
noun: 'tattoo artist',
nounKey: 'becomeRolesUi.tattoo.noun',
accentText: 'text-rose-400',
accentBg: 'bg-rose-600',
accentChip: 'bg-rose-600 text-white border-rose-600',
accentChipHover: 'hover:border-rose-500/60 hover:text-rose-400',
icon: Brush,
rateUnits: pickRateUnits('hour', 'piece', 'session'),
rateLabel: 'Rate / Hourly',
rateLabelKey: 'becomeRolesUi.tattoo.rateLabel',
portfolioLabel: 'Portfolio link (IG, site)',
portfolioLabelKey: 'becomeRolesUi.tattoo.portfolioLabel',
skillSections: [
{ title: 'Styles', titleKey: 'becomeRolesUi.tattoo.sectionStyles', entries: Object.entries(TATTOO_STYLE_LABELS), keyMap: TATTOO_STYLE_KEYS, required: true },
{ title: 'Method', titleKey: 'becomeRolesUi.tattoo.sectionMethod', entries: Object.entries(TATTOO_METHOD_LABELS), keyMap: TATTOO_METHOD_KEYS },
],
extraFields: [
{ tag: 'studio', label: 'Studio / Shop', labelKey: 'becomeRolesUi.tattoo.studioLabel', placeholder: 'Studio name (optional)', placeholderKey: 'becomeRolesUi.tattoo.studioPlaceholder' },
{ tag: 'books_open', label: 'Books Open', labelKey: 'becomeRolesUi.tattoo.booksOpenLabel', type: 'toggle', helper: 'Are you currently taking bookings?', helperKey: 'becomeRolesUi.tattoo.booksOpenHelper' },
{ tag: 'deposit', label: 'Deposit', labelKey: 'labUi.craftFields.deposit', placeholder: 'e.g. 50 EUR non-refundable', placeholderKey: 'becomeRolesUi.tattoo.depositPlaceholder' },
{ tag: 'minimum', label: 'Minimum', labelKey: 'labUi.craftFields.minimum', placeholder: 'e.g. 80 EUR', placeholderKey: 'becomeRolesUi.tattoo.minimumPlaceholder' },
],
},
},
trainer: {
kind: 'craft',
seoTitle: 'Become a Trainer / Physio - SkateSpots',
seoDescription: 'Help skaters get strong and stay healthy — strength, mobility, injury prevention and recovery.',
seoTitleKey: 'becomeRolesUi.trainer.seoTitle',
seoDescriptionKey: 'becomeRolesUi.trainer.seoDescription',
config: {
kind: SKATE_TRAINER_KIND,
selfTag: 'skatetrainer',
identifier: 'trainer-profile',
heading: 'Trainer / Physio',
headingKey: 'becomeRolesUi.trainer.heading',
tagline: 'Strength, mobility, injury prevention & recovery for skaters',
taglineKey: 'becomeRolesUi.trainer.tagline',
noun: 'trainer',
nounKey: 'becomeRolesUi.trainer.noun',
accentText: 'text-emerald-400',
accentBg: 'bg-emerald-600',
accentChip: 'bg-emerald-600 text-white border-emerald-600',
accentChipHover: 'hover:border-emerald-500/60 hover:text-emerald-400',
icon: Dumbbell,
rateUnits: pickRateUnits('session', 'month', 'hour'),
rateLabel: 'Rate / Session',
rateLabelKey: 'becomeRolesUi.trainer.rateLabel',
portfolioLabel: 'Profile / booking link',
portfolioLabelKey: 'becomeRolesUi.trainer.portfolioLabel',
skillSections: [
{ title: 'Focus', titleKey: 'becomeRolesUi.trainer.sectionFocus', entries: Object.entries(TRAINER_FOCUS_LABELS), keyMap: TRAINER_FOCUS_KEYS, required: true },
{ title: 'Injuries You Work With', titleKey: 'becomeRolesUi.trainer.sectionInjuries', entries: Object.entries(TRAINER_INJURY_LABELS), keyMap: TRAINER_INJURY_KEYS },
{ title: 'Credentials & Setting', titleKey: 'becomeRolesUi.trainer.sectionCredentialsSetting', entries: Object.entries(TRAINER_CREDENTIAL_LABELS), keyMap: TRAINER_CREDENTIAL_KEYS },
],
extraFields: [
{ tag: 'credentials', label: 'Certifications', labelKey: 'labUi.craftFields.certifications', placeholder: 'e.g. BSc Physiotherapy, CSCS…', placeholderKey: 'becomeRolesUi.trainer.credentialsPlaceholder', helper: 'List real qualifications — skaters trust verifiable credentials.', helperKey: 'becomeRolesUi.trainer.credentialsHelper' },
{ tag: 'remote', label: 'Remote / Online', labelKey: 'becomeRolesUi.trainer.remoteLabel', type: 'toggle', helper: 'Do you offer online coaching or consultations?', helperKey: 'becomeRolesUi.trainer.remoteHelper' },
{ tag: 'modalities', label: 'Modalities', labelKey: 'labUi.craftFields.modalities', placeholder: 'e.g. hands-on, S&C, dry needling', placeholderKey: 'becomeRolesUi.trainer.modalitiesPlaceholder' },
],
},
},
barber: {
kind: 'craft',
seoTitle: 'Become a Barber / Hairstylist - SkateSpots',
seoDescription: 'List your barbershop or chair for the skate scene — cuts, fades, beard trims, colour and more. Get booked by skaters.',
seoTitleKey: 'becomeRolesUi.barber.seoTitle',
seoDescriptionKey: 'becomeRolesUi.barber.seoDescription',
config: {
kind: SKATE_BARBER_KIND,
selfTag: 'skatebarber',
identifier: 'barber-profile',
heading: 'Barber / Hairstylist',
headingKey: 'becomeRolesUi.barber.heading',
tagline: 'Cuts, fades & beard trims for the scene — shop chair or mobile',
taglineKey: 'becomeRolesUi.barber.tagline',
noun: 'barber',
nounKey: 'becomeRolesUi.barber.noun',
accentText: 'text-cyan-400',
accentBg: 'bg-cyan-600',
accentChip: 'bg-cyan-600 text-white border-cyan-600',
accentChipHover: 'hover:border-cyan-500/60 hover:text-cyan-400',
icon: Sparkles,
rateUnits: pickRateUnits('cut', 'hour', 'session'),
rateLabel: 'Price / Cut',
rateLabelKey: 'becomeRolesUi.barber.rateLabel',
portfolioLabel: 'Cuts gallery / IG link',
portfolioLabelKey: 'becomeRolesUi.barber.portfolioLabel',
skillSections: [
{ title: 'What You Offer', titleKey: 'becomeRolesUi.barber.sectionWhatYouOffer', entries: Object.entries(BARBER_SERVICE_LABELS), keyMap: BARBER_SERVICE_KEYS, required: true },
{ title: 'Signature Styles', titleKey: 'becomeRolesUi.barber.sectionSignatureStyles', entries: Object.entries(BARBER_STYLE_LABELS), keyMap: BARBER_STYLE_KEYS },
{ title: 'Setting', titleKey: 'becomeRolesUi.barber.sectionSetting', entries: Object.entries(BARBER_SETTING_LABELS), keyMap: BARBER_SETTING_KEYS },
],
extraFields: [
{ tag: 'studio', label: 'Shop / Studio', labelKey: 'becomeRolesUi.barber.studioLabel', placeholder: 'Shop or studio name (optional)', placeholderKey: 'becomeRolesUi.barber.studioPlaceholder' },
{ tag: 'books_open', label: 'Books Open', labelKey: 'becomeRolesUi.barber.booksOpenLabel', type: 'toggle', helper: 'Are you currently taking bookings?', helperKey: 'becomeRolesUi.barber.booksOpenHelper' },
{ tag: 'duration', label: 'Appointment Length', labelKey: 'labUi.craftFields.duration', placeholder: 'e.g. 30–45 min', placeholderKey: 'becomeRolesUi.barber.durationPlaceholder' },
],
},
},
};
export function getBecomeRole(slug: string | undefined): BecomeRole | undefined {
if (!slug) return undefined;
return BECOME_ROLES[slug.toLowerCase()];
}