When Your AI Duplicates Every Field: A Story About Idempotency A developer building a form with Claude Desktop encountered a bug where the AI duplicated every field after a session crash, resulting in 24 fields instead of 12. The root cause is that the `field_add` command is not idempotent, so the AI re-added fields without checking for existing ones. The developer fixed it by enforcing a read-before-write pattern: always check if a field exists before adding it. I had a form with 12 fields. Then my Claude Desktop session crashed. I restarted it, asked Claude to "continue building the form," and ended up with 24 fields. Half of them were exact duplicates — same IDs, same titles, same types. The form rendered with two "Email" fields, two "Name" fields, and two of every radio button. This is the story of how field add isn't idempotent, why that matters when an AI is driving, and the pattern I adopted to fix it. Update v0.2.0 : The field add command is now accessed via formlm exec . The formlm generate smart pipeline eliminates this entire class of problem — the server-side AssessAgent handles field creation atomically and idempotently. The find-before-add pattern remains useful when using formlm exec for manual field operations. Here's the sequence: app list , found the existing app, and started adding fields againThe result was a form with 20 fields total 8 original + 12 duplicate . The duplicate field IDs were auto-suffixed by the server email became email , email 1 , email 2 ... . To the user filling out the form, it looked like the form had been designed by someone who really, really wanted your email address. field add Isn't Idempotent Here's the thing about field add — it's a create operation, not an upsert. If you call it twice with the same field ID, the server creates two fields. The field ID isn't a unique constraint; it's a label. Looking at the MCP tool definition: server.tool 'field add', 'Add a new field', { appId: z.string .describe 'App ID' , id: z.string .describe 'Field ID' , type: z.string .default 'input' .describe 'Field type default: input ' , title: z.string .optional .describe 'Field title / question text' , // ... }, async params = { let cmd = assess form add --app ${params.appId} --id ${params.id} --type ${params.type} ; // ... } ; There's no check for "does this field ID already exist?" The tool just sends the add command and the server creates a new field. If a field with that ID already exists, the server either appends a suffix or creates a duplicate. From a CLI perspective, this is fine. A human running formlm-cli field add knows whether they've already added a field. They don't need the CLI to check for them. From an AI perspective, this is a problem. The AI doesn't remember what it did in a previous session. It doesn't check whether fields exist before adding them. It just executes the plan, and if the plan says "add 12 fields," it adds 12 fields — regardless of whether 8 of them are already there. The pattern I now enforce is: always check before adding . Before calling field add , call field find to see if a field with that ID already exists: Step 1: Check if the field already exists field find --app