-
Notifications
You must be signed in to change notification settings - Fork 1.1k
feat: prevent duplicate action name #879
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
Conversation
WalkthroughAdded a duplicate-name validation feature to InterpretationLog by introducing a Changes
Sequence DiagramsequenceDiagram
actor User
participant InterpretationLog
participant checkForDuplicateName
participant useGlobalInfoStore
User->>InterpretationLog: Attempt to save/edit step with new name
InterpretationLog->>checkForDuplicateName: checkForDuplicateName(stepId, type, newName)
alt Duplicate Found
checkForDuplicateName->>useGlobalInfoStore: notify(error message)
useGlobalInfoStore-->>InterpretationLog: Error emitted
InterpretationLog-->>User: Update aborted
else No Duplicate
checkForDuplicateName-->>InterpretationLog: Validation passed
InterpretationLog->>InterpretationLog: Apply edits
InterpretationLog-->>User: Update successful
end
Estimated code review effort🎯 3 (Moderate) | ⏱️ ~20 minutes
Possibly related PRs
Suggested labels
Suggested reviewers
Poem
Pre-merge checks and finishing touches✅ Passed checks (3 passed)
✨ Finishing touches
🧪 Generate unit tests (beta)
Thanks for using CodeRabbit! It's free for OSS, and your support helps us grow. If you like it, consider giving us a shout-out. Comment |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Actionable comments posted: 1
📜 Review details
Configuration used: CodeRabbit UI
Review profile: CHILL
Plan: Pro
📒 Files selected for processing (1)
src/components/run/InterpretationLog.tsx(3 hunks)
🧰 Additional context used
🧬 Code graph analysis (1)
src/components/run/InterpretationLog.tsx (1)
src/context/globalInfo.tsx (1)
useGlobalInfoStore(186-186)
| const checkForDuplicateName = (stepId: number, type: 'list' | 'text' | 'screenshot', newName: string): boolean => { | ||
| const trimmedName = newName.trim(); | ||
|
|
||
| if (type === 'list') { | ||
| const listSteps = browserSteps.filter(step => step.type === 'list' && step.id !== stepId); | ||
| const duplicate = listSteps.find(step => step.name === trimmedName); | ||
| if (duplicate) { | ||
| notify('error', `A list with the name "${trimmedName}" already exists. Please choose a different name.`); | ||
| return true; | ||
| } | ||
| } else if (type === 'screenshot') { | ||
| const screenshotSteps = browserSteps.filter(step => step.type === 'screenshot' && step.id !== stepId); | ||
| const duplicate = screenshotSteps.find(step => step.name === trimmedName); | ||
| if (duplicate) { | ||
| notify('error', `A screenshot with the name "${trimmedName}" already exists. Please choose a different name.`); | ||
| return true; | ||
| } | ||
| } | ||
|
|
||
| return false; | ||
| }; |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Handle duplicate text labels too
checkForDuplicateName short-circuits only for lists and screenshots. When editing a text step, it always falls through and returns false, so two text captures can still share the same label—failing the “unique per capture action type” requirement and the helper’s own 'text' signature. Add a text-specific guard before returning.
} else if (type === 'screenshot') {
const screenshotSteps = browserSteps.filter(step => step.type === 'screenshot' && step.id !== stepId);
const duplicate = screenshotSteps.find(step => step.name === trimmedName);
if (duplicate) {
notify('error', `A screenshot with the name "${trimmedName}" already exists. Please choose a different name.`);
return true;
}
+ } else if (type === 'text') {
+ const textSteps = browserSteps.filter(step => step.type === 'text' && step.id !== stepId);
+ const duplicate = textSteps.find(step => step.label?.trim() === trimmedName);
+ if (duplicate) {
+ notify('error', `A text entry with the name "${trimmedName}" already exists. Please choose a different name.`);
+ return true;
+ }
}📝 Committable suggestion
‼️ IMPORTANT
Carefully review the code before committing. Ensure that it accurately replaces the highlighted code, contains no missing lines, and has no issues with indentation. Thoroughly test & benchmark the code to ensure it meets the requirements.
| const checkForDuplicateName = (stepId: number, type: 'list' | 'text' | 'screenshot', newName: string): boolean => { | |
| const trimmedName = newName.trim(); | |
| if (type === 'list') { | |
| const listSteps = browserSteps.filter(step => step.type === 'list' && step.id !== stepId); | |
| const duplicate = listSteps.find(step => step.name === trimmedName); | |
| if (duplicate) { | |
| notify('error', `A list with the name "${trimmedName}" already exists. Please choose a different name.`); | |
| return true; | |
| } | |
| } else if (type === 'screenshot') { | |
| const screenshotSteps = browserSteps.filter(step => step.type === 'screenshot' && step.id !== stepId); | |
| const duplicate = screenshotSteps.find(step => step.name === trimmedName); | |
| if (duplicate) { | |
| notify('error', `A screenshot with the name "${trimmedName}" already exists. Please choose a different name.`); | |
| return true; | |
| } | |
| } | |
| return false; | |
| }; | |
| const checkForDuplicateName = (stepId: number, type: 'list' | 'text' | 'screenshot', newName: string): boolean => { | |
| const trimmedName = newName.trim(); | |
| if (type === 'list') { | |
| const listSteps = browserSteps.filter(step => step.type === 'list' && step.id !== stepId); | |
| const duplicate = listSteps.find(step => step.name === trimmedName); | |
| if (duplicate) { | |
| notify('error', `A list with the name "${trimmedName}" already exists. Please choose a different name.`); | |
| return true; | |
| } | |
| } else if (type === 'screenshot') { | |
| const screenshotSteps = browserSteps.filter(step => step.type === 'screenshot' && step.id !== stepId); | |
| const duplicate = screenshotSteps.find(step => step.name === trimmedName); | |
| if (duplicate) { | |
| notify('error', `A screenshot with the name "${trimmedName}" already exists. Please choose a different name.`); | |
| return true; | |
| } | |
| } else if (type === 'text') { | |
| const textSteps = browserSteps.filter(step => step.type === 'text' && step.id !== stepId); | |
| const duplicate = textSteps.find(step => step.label?.trim() === trimmedName); | |
| if (duplicate) { | |
| notify('error', `A text entry with the name "${trimmedName}" already exists. Please choose a different name.`); | |
| return true; | |
| } | |
| } | |
| return false; | |
| }; |
🤖 Prompt for AI Agents
In src/components/run/InterpretationLog.tsx around lines 157 to 177, the
duplicate-name check only handles 'list' and 'screenshot' so 'text' edits can
create non-unique labels; add a branch for type === 'text' that filters
browserSteps for type 'text' excluding the current stepId, checks for an
existing step with the same trimmed name, calls notify('error', `A text capture
with the name "${trimmedName}" already exists. Please choose a different name.`)
if found, and returns true; keep the existing return false at the end.
What this PR does?
Adds a validity check to ensure unique names among each capture action type.
2025-11-07.14-17-34.mp4
Summary by CodeRabbit
Release Notes