All posts
VibeZero Team6 min read

Lovable vs Bolt.new: security compared

Same database, same default-off row security, two different ways to leak a key. What each platform gets right, what each gets wrong, and which risk is yours.

  • security
  • vibe coding
  • lovable
  • bolt

Comparisons like this usually get written to produce a winner, which is why most of them are useless. Lovable and Bolt.new put you on the same database with the same default, so the biggest risk in both is identical and does not distinguish them at all. The differences are real, and they are narrower and more specific than a scorecard would suggest.

Here is what actually differs, in both directions.

What they share, which is most of it

Both generate apps backed by Supabase. Supabase exposes your Postgres tables over a REST API, the anon key that authorizes it ships in your frontend bundle by design, and Row Level Security is the only thing deciding what that public key can read. Newly created tables have RLS off.

Both generators create tables without turning it on. So on both platforms, the default outcome is a table that anyone on the internet can read with a key they copy out of your JavaScript, while your login screen works perfectly and gives you no reason to suspect anything.

That is CVE-2025-48757, the CVSS 9.3 disclosure covering 170-plus exposed production apps. It was filed against Lovable because that is where the researcher found it, and the mechanism belongs to the backend rather than the builder, so a Bolt project on Supabase has the same exposure with none of the press.

Where Bolt is riskier: the documented prefix

Bolt scaffolds Vite projects, and Vite publishes any environment variable prefixed with VITE_ into the client bundle. Its documentation says so plainly and warns that such variables “should not contain sensitive information such as API keys.”

Bolt’s own introduction to databases tells new builders that “environment variables keep these values private” and then lists VITE_SUPABASE_SERVICE_ROLE_KEY among the variables to use. The service role key, per Supabase, “uses the BYPASSRLS attribute, skipping any and all Row Level Security policies you attach.”

So the path to publishing your master database credential runs through following the instructions correctly. That is a meaningfully worse failure than a generator producing insecure code, because there is no moment where the builder did something wrong. It also compounds the shared RLS problem rather than sitting beside it: with that key public, fixing your policies changes nothing.

Lovable’s equivalent failure exists but requires the model to make a choice rather than the docs to give an instruction: asked to call a third-party API, Lovable will often write the call in the frontend, which puts that provider’s key in the bundle. Real, common, and one prompt away from being written correctly into an Edge Function instead.

Where Lovable is riskier: a check that cannot fail

Lovable ships built-in security scanning, which its CEO lists among the things that make the product stand out: “catch security issues before publishing.” Bolt ships nothing equivalent.

On a naive reading that is a point for Lovable. The disclosure record says otherwise, and this is the most interesting difference between the two products.

The scanner shipped with Lovable 2.0 on 24 April 2025, during the 45-day disclosure window for the CVE. In the researcher’s assessment, it “merely checks for the existence of any RLS policy, not its correctness or alignment with application logic,” which he describes as providing “a false sense of security, failing to detect the misconfigurations that expose data.” On 24 May, a month after it shipped, he bypassed access controls on a live Lovable site by removing the Authorization header and inserted records including one setting "payment_status": "paid".

A table with the policy for all using (true) passes that scan. So does a table with a policy that scopes the wrong column. The property being certified is not the property that matters, and a green result on an exposed table is worse for a non-specialist builder than no result at all, because no result prompts a question.

The disclosure handling is part of the same picture. Lovable confirmed receipt on 24 March 2025 and, per the researcher’s account, published nothing meaningful to users before the CVE went out on 29 May. Bolt has no comparable public incident, and it is worth saying clearly that this is not evidence of a better security posture: nobody has published a comparable audit of Bolt-generated apps. Absence of a CVE is absence of research, not absence of bugs.

Where each is genuinely better

Bolt: a deployment target with a server. Bolt publishes to Netlify, so the place to put a secret and a server-side call already exists and costs nothing. Moving a leaked key into a Netlify function is a ten-minute change. That matters, because the most common reason a key stays in the frontend is that there is no obvious server to move it to.

Bolt: an open-source reference implementation. bolt.diy is the official open-source version, developed with StackBlitz. You can read how the generator behaves rather than inferring it from output, which is a real advantage for anyone trying to reason about systematic failure modes.

Lovable: the code is in your GitHub, continuously. Lovable’s two-way GitHub sync commits every AI change to your repository and syncs commits back. For security this is underrated and possibly the single most useful difference in the comparison: your app is a normal repository, so normal tooling applies. Secret scanning over the full history, static analysis on every push, dependency alerts, branch protection, and code review all work without an export step. Bolt supports pushing to GitHub too, and the difference is whether it is the default state or a thing you remember to do.

Lovable: Edge Functions are the idiomatic path. Because Supabase Edge Functions are the natural place for a server-side call in a Lovable app, the correct pattern is the one the model reaches for when asked. Bolt’s idiomatic path for a quick integration is a frontend fetch, with the function as the correction.

How to actually choose

Not on this comparison. Both give you a real Postgres with real row-level access control, real auth, and a place to put a secret, and both leave the same work to you. The differentiators above change which mistake you are most likely to make, not whether you have to check.

If you are on Bolt, your first check is the bundle. If you are on Lovable, your first check is that the policy denies rather than merely exists. Both then share the same second, third, and fourth checks. The Bolt fix list and the Lovable one run in a different order for that reason and cover the same ground.

The comparison that matters is with unverified

The useful lesson from putting these two side by side is not that one is safer. It is that the platform with a security feature had a documented failure the feature reported as fine, and the platform without one has had no published audit at all. Neither of those is information about your app.

Both questions collapse into the same one, which is whether Lovable is safe and whether Bolt is safe in the only sense that has an answer: does the specific thing you deployed enforce access control at the database and keep its credentials off the client. That is checkable in ten minutes on either platform, by something that is not the tool that wrote the code, across all five layers.

ShareXLinkedIn