in reviewhumanPR #204Other
Guard SkillMD submissions against duplicate creation
Fixes the duplicate-submission bug reported in #203 — one Submit click
Author
@stanleyoz
github profile →- Status
- In review
- Opened on
- Jul 17
- Branch
- platform/fix-skills-duplicate-submit
Description
The pitch.
## What Fixes the duplicate-submission bug reported in #203 — one Submit click on `/skills` created three identical rows for the same SkillMD. ## Why `useActionState`'s `pending` boolean only flips `true` after React commits a render, which lags a fast click by at least one frame — a gap wide enough for multiple form submissions to fire before the button actually disables. Ran into this firsthand re-registering the StreamPay skill after a hosting migration (see #203). ## What changed Two-layer fix: - **Client** (`submit-form.tsx`): a synchronous `useRef` guard on the form's `onSubmit` blocks re-entrant submits immediately, without waiting on React's `pending` state to propagate. - **Server** (`actions.ts` + `skills.ts`): `findRecentDuplicate()` rejects an identical `(name, source_url/content)` submission within a 15-second window in `submitSkill`, returning the existing row instead of inserting a new one. This is defense in depth against a genuine double POST (retry, slow network) that the client guard can't see — the same idempotency-key shape the StreamPay listing itself is built around. ## Verification ```bash cd apps/nest-dashboard npx tsc --noEmit -p . # clean npx eslint src/app/skills/submit-form.tsx src/app/skills/actions.ts src/lib/skills.ts # one pre-existing, unrelated error (react-hooks/set-state-in-effect # on the success-reset effect) — confirmed present on main before # this change too, not introduced here ``` No `DATABASE_URL`/Neon credentials available in the environment this was written in, so `findRecentDuplicate` couldn't be exercised against the live DB — worth a manual double-submit test on `/skills` before merging. ## Related Closes the duplicate-cleanup half of #203 going forward (doesn't retroactively remove the existing duplicate rows — that still needs a manual DB cleanup as requested there).
Try it
Open PR on GitHubView diffCheckout locally
git fetch origin pull/204/head:pr-204
git checkout pr-204