Most common security mistakes in Lovable, Bolt, and v0 apps
Lovable, Bolt, and v0 are all trained on the same corpus of public open-source code — code written by developers whose primary goal was functionality, not security hardening. The result is that all three tools produce predictably similar security gaps regardless of what you ask them to build. This is not a coincidence or a product failure; it is a structural characteristic of how large language models learn to generate code. They learn the patterns that appear most frequently in their training data, and most code on the internet does not include robust security controls. Understanding which specific gaps appear most often is the fastest way to close them before a user or an attacker finds them for you.
The most widespread single issue across all three platforms is Supabase anon keys appearing in client-side JavaScript bundles. When an AI builder scaffolds a Supabase integration, it often places the project URL and anon key in environment variables prefixed with NEXT_PUBLIC_, which causes Next.js to include them in the browser bundle. This is sometimes intentional — the anon key is designed to be used from the client — but it creates a critical problem when Row Level Security is not enabled. Anyone who extracts the anon key from your bundle can use it to query your database directly using the Supabase JavaScript client, bypassing your application layer entirely. They do not need your login form. They do not need your API routes. They just need your key and your project URL, both of which are visible in your page source.
Missing Row Level Security is the second major issue, and it is the one that turns an exposed anon key from a minor problem into a catastrophic one. RLS is a Postgres-level policy that controls which rows a given database role can access. By default in new Supabase projects, RLS is disabled on every table, which means the anon role — the role associated with your public anon key — has unrestricted read and write access to everything. An AI builder that scaffolds tables and queries will not enable RLS unless you explicitly ask it to. It does not know your authorization model. It does not know which rows belong to which users. It generates working queries and leaves the access control layer empty.
Security headers are the third category of consistent failures. Content-Security-Policy, X-Frame-Options, Strict-Transport-Security, and X-Content-Type-Options are not something any of the three platforms configure by default. Without X-Frame-Options, your app can be embedded in an iframe on a malicious site and used for clickjacking attacks. Without CSP, any cross-site scripting vulnerability in your app can be escalated to full session compromise. Without HSTS, connections to your site can be downgraded from HTTPS to HTTP by a network-level attacker. These are well-understood attacks with decades of documented mitigations, and none of those mitigations ship out of the box with any AI builder.
Hard-coded secrets in source code committed to public GitHub repositories represent the fourth major pattern. This happens most often when a developer iterates quickly: they add a key to a file to test something, it works, they commit the file, and the key is now in public git history permanently. Even if you delete the file in a subsequent commit, the key remains recoverable from the history. Automated scanners — run by both security researchers and attackers — index GitHub continuously and find these keys within minutes of the commit. Stripe secret keys, OpenAI API keys, Supabase service role keys, and signing secrets are all common targets.
The fix for all five of these issues is tractable. Enable RLS on every Supabase table and write a deny-by-default policy before adding more permissive rules. Add security headers to your next.config.ts in a headers() block. Audit every environment variable and confirm that nothing with sk_, service_role, or SECRET in its name is prefixed with NEXT_PUBLIC_. Rotate any key that has ever appeared in a public repository, even if you believe you deleted it. None of these require specialized security knowledge — they require knowing to look.