
I've been shipping code with AI assistants sitting in my editor for the better part of three years now. GitHub Copilot, Claude, Cursor, Codeium, the whole crew. They make me faster, no argument there. But somewhere around the time I found a hardcoded AWS key that Copilot had cheerfully autocompleted into a public repo, I started keeping a running log of the security messes these tools quietly introduce.
Here's the stat that should make you nervous: a 2023 Stanford study found that developers using AI code assistants wrote significantly less secure code than those without, yet were more confident their code was safe. That confidence gap is the real danger. The model is optimizing for "code that looks plausible," not "code that survives a penetration test." Those are very different targets.
This article walks through the seven AI coding assistant security mistakes I see most often, with real examples, a before/after fix, and a comparison of how the popular tools stack up. If you write code with an AI in the loop, or you review code that someone else wrote that way, this is for you.
Key Takeaways
- AI assistants confidently suggest outdated, vulnerable patterns because their training data is full of them.
- The most common bugs are injection flaws, hardcoded secrets, and missing input validation, not exotic zero-days.
- Never paste real secrets, tokens, or customer data into a prompt. Assume every prompt could be logged.
- Treat AI output like a pull request from a fast but junior contractor: useful, but it gets reviewed.
- Automated scanning (SAST, dependency audits) catches a large share of AI-introduced flaws cheaply.
- Defense in depth still matters. A hardened server and good backups limit the blast radius when a bug slips through.
Mistake 1: Trusting Autocompleted Database Queries Without Parameterization
This is the big one. SQL injection is old enough to vote, yet AI assistants reintroduce it constantly because so much of their training data uses string concatenation for queries.
Ask an assistant to "write a function to get a user by email" and there's a real chance you get something like this:
const query = "SELECT * FROM users WHERE email = '" + email + "'";
That single line is a textbook injection hole. If email comes from a request body, an attacker sends ' OR '1'='1 and dumps your whole table. The AI didn't warn you, because to the model, that string looks exactly like ten thousand blog snippets it learned from.
Before and after
Before (vulnerable): db.query("SELECT * FROM users WHERE email = '" + email + "'")
After (parameterized): db.query("SELECT * FROM users WHERE email = $1", [email])
The fix is trivial once you know to look. The problem is that AI-generated code often looks finished, so nobody looks. Make it a hard rule: every query that touches user input gets parameterized, and you personally verify it, not the model.
Mistake 2: Letting the Assistant Hardcode Secrets and Keys
AI assistants love to be helpful with placeholders. Ask for code that calls an API and you'll often get const apiKey = "sk-your-real-key-here" sitting right in the source. Developers in a hurry paste in the real key, commit, and push.
GitGuardian's annual report has repeatedly found millions of secrets leaked to public repos every year, and AI autocomplete is accelerating the trend by making it feel normal to inline config.
Do this instead:
- Keep secrets in environment variables or a secrets manager, never in code.
- Reference them as
process.env.API_KEYand load from a.envfile that is git-ignored. - Add a pre-commit hook (git-secrets, gitleaks) that blocks commits containing key-shaped strings.
- If you must move a secret between machines, use an encrypted vault rather than a chat window. Our team leans on a self-hosted approach for this, and the tradeoffs are worth reading in Self-Hosted vs Cloud Password Managers: Which to Choose.
One more thing people forget: if you ever pasted a real secret into an AI prompt, treat it as compromised and rotate it. You have no guarantee about how that prompt was logged or trained on.
Mistake 3: Accepting Vulnerable or Hallucinated Dependencies
Ask an AI to solve a problem and it will happily suggest npm install some-package. Two failure modes hide here.
First, the package version it suggests is often old, pinned to whatever was common in its training window, and may carry known CVEs. Second, and more disturbing, models sometimes hallucinate package names that don't exist. Attackers have started registering those hallucinated names with malware inside, a technique called "slopsquatting." Install the fake package and you've handed over your build environment.
Protect yourself with a simple pre-install checklist:
- Confirm the package actually exists on the official registry and has real download history.
- Check the publish date and maintainer, not just the star count.
- Run
npm auditorpip-auditbefore you build anything. - Skim the source for network calls and post-install scripts.
I wrote a full procedure for this that pairs well with AI-assisted workflows: How to Detect Malicious Code in npm Packages Before Installing. Run through it any time a model hands you a dependency you've never heard of.
Mistake 4: Skipping Input Validation Because the Code "Looks Complete"
AI-generated code has a polished surface. Functions are named well, there are comments, the happy path works. That polish creates a false sense of completeness, so the missing bits get overlooked.
The missing bits are usually the security-relevant ones: input validation, length limits, type checks, output encoding. An AI writing an image upload handler will nail the file-saving logic and completely forget to validate that the file is actually an image, that it's under a size cap, and that the filename can't contain ../ for a path traversal attack.
A worked example
Say you asked for a profile-update endpoint and got 40 lines back. Here's a realistic audit of what a human should add:
- Missing: max length on the
biofield, so someone stores a 2 MB payload 100,000 times and fills your disk. - Missing: rejection of HTML in the
displayName, so a stored XSS payload runs in every visitor's browser. - Missing: authorization check that the logged-in user owns the profile they're editing (IDOR).
- Present but wrong: the email regex accepts
test@testwith no TLD.
Four flaws in 40 lines. That ratio is not unusual. The lesson: read AI code adversarially. Ask "how would I break this?" for every input the function touches.
Mistake 5: Pasting Proprietary or Sensitive Data Into Prompts
This one isn't a code bug, it's a data-exposure bug, and it's arguably the most expensive. To get better answers, developers paste in real config files, production logs, customer records, and internal source. Depending on the tool and plan, that content may be retained, reviewed by humans, or used for training.
Samsung famously banned generative AI internally after engineers leaked confidential source code into a chatbot. Your company's version of that leak is probably one panicked debugging session away.
Practical guardrails:
- Sanitize before you paste: replace real tokens, hostnames, and customer data with fakes.
- Prefer tools with a clear "no training on your data" policy and enterprise data controls.
- For sharing snippets with teammates, use a controlled, self-hostable paste tool rather than a random public pastebin. That's precisely why we built LionPaste, so sensitive snippets stay on infrastructure you control.
- Lock down any AI browser extensions that can read page content. My walkthrough on how to lock down AI browser extension permissions safely covers the settings that matter.
Mistake 6: Copying Insecure Configuration and Auth Code Verbatim
Ask an AI for a quick server setup and you'll get code that prioritizes "works immediately" over "works safely." Common offenders I catch every week:
cors({ origin: "*" })— wide-open CORS that lets any site call your API with credentials.- JWT verification with the algorithm set to
none, or the secret left as"secret". - Cookies without
httpOnly,Secure, orSameSiteflags. - Password hashing with plain MD5 or SHA-256 instead of bcrypt/argon2.
- Debug mode and verbose stack traces left enabled in the generated production config.
Each of these is a one-line change to fix and a full-blown incident to ignore. If your stack includes a CMS, this problem multiplies because AI will suggest theme and plugin snippets with the same bad habits. For WordPress specifically, I run generated code past the checklist in how to audit a WordPress plugin for hidden backdoors and lean on a hardening layer like eDarpan WordPress Protection so a single bad snippet can't hand over the whole site.
Mistake 7: Assuming the AI Understands Your Threat Model
The model has no idea whether your app handles patient records or hosts a hobby blog. It applies the same generic patterns to both. That's the deepest problem: AI produces context-free code, and security is entirely about context.
A rate limiter that's fine for a personal project is negligent for a login endpoint at a bank. An AI won't make that distinction unless you spell it out, and even then it often forgets by the next suggestion. You are the one who knows the stakes, so you own the threat model.
How the popular assistants compare on security
None of these tools is "secure" or "insecure" on its own, but they differ in the safeguards they offer. Here's my hands-on read as of recent testing:
| Tool | Flags known vulns | No-training data option | Secret
Cover image: The Torch Graduate circuit board (bottom) by Chris Whytehead, licensed under BY-SA 3.0 via Openverse. |
|---|








