import { useState } from 'react' import { ChevronRight, SkipForward, Info, Check } from 'lucide-react' import { cn } from '@/lib/utils' import { Input } from '@/components/ui/Input' import type { ParameterCandidate, ScriptParameter } from '@/types' const PARAM_TYPES: { value: ScriptParameter['type']; label: string }[] = [ { value: 'text', label: 'Text' }, { value: 'password', label: 'Password' }, { value: 'textarea', label: 'Textarea' }, { value: 'number', label: 'Number' }, { value: 'boolean', label: 'Boolean' }, { value: 'select', label: 'Select' }, { value: 'multi_text', label: 'Multi-text' }, ] interface Props { candidates: ParameterCandidate[] existingKeys: string[] onAccept: (candidate: ParameterCandidate, overrides: { key: string label: string type: ScriptParameter['type'] sensitive: boolean required: boolean defaultValue: string | boolean | number | null }) => void onSkip: (candidate: ParameterCandidate) => void onFinish: (acceptedCount: number, totalCount: number) => void } export function ParameterDetectorStepper({ candidates, existingKeys, onAccept, onSkip, onFinish, }: Props) { const [currentIndex, setCurrentIndex] = useState(0) const [acceptedCount, setAcceptedCount] = useState(0) const [showInferenceInfo, setShowInferenceInfo] = useState(false) const current = candidates[currentIndex] const [key, setKey] = useState(current.suggestedKey) const [label, setLabel] = useState(current.suggestedLabel) const [type, setType] = useState(current.suggestedType) const [sensitive, setSensitive] = useState(current.sensitive) const [required, setRequired] = useState(true) const [defaultValue, setDefaultValue] = useState( current.defaultValue !== null ? String(current.defaultValue) : '' ) const isLast = currentIndex === candidates.length - 1 const resetFieldsForIndex = (index: number) => { const c = candidates[index] setKey(c.suggestedKey) setLabel(c.suggestedLabel) setType(c.suggestedType) setSensitive(c.sensitive) setRequired(true) setDefaultValue(c.defaultValue !== null ? String(c.defaultValue) : '') setShowInferenceInfo(false) } const handleAccept = () => { const parsedDefault = type === 'boolean' ? defaultValue === 'true' : type === 'number' ? (defaultValue ? Number(defaultValue) : null) : (defaultValue || null) onAccept(current, { key, label, type, sensitive, required, defaultValue: parsedDefault, }) const newAccepted = acceptedCount + 1 setAcceptedCount(newAccepted) if (isLast) { onFinish(newAccepted, candidates.length) } else { const nextIndex = currentIndex + 1 setCurrentIndex(nextIndex) resetFieldsForIndex(nextIndex) } } const handleSkip = () => { onSkip(current) if (isLast) { onFinish(acceptedCount, candidates.length) } else { const nextIndex = currentIndex + 1 setCurrentIndex(nextIndex) resetFieldsForIndex(nextIndex) } } return (
{/* Progress */}

Variable {currentIndex + 1} of {candidates.length}

{candidates.map((_, i) => (
))}
{/* Matched line */}

{current.matchedLine}

Line {current.lineNumber} · {current.source === 'param_block' ? 'param() block' : 'variable assignment'}

{/* Editable fields */}
setKey(e.target.value.replace(/[^a-zA-Z0-9_]/g, ''))} placeholder="param_key" /> {existingKeys.includes(key) && (

Key already exists — consider a different name

)}
setLabel(e.target.value)} placeholder="Display Label" />
{showInferenceInfo && (

{current.inferenceReason}

)}
setDefaultValue(e.target.value)} placeholder="Original value preserved" />
{/* Actions */}
) }