feat: version history as 10th feature flag, richer upgrade prompts, close unguarded photo-import tab (v0.80.0)

Recipe version history is now gated like the other 9 per-tier features (enabled by default, locked-vs-hidden treatment via isFeatureAvailableAnyTier). UpgradeDialog now shows a tagline + concrete bullet list per feature instead of one generic sentence.

Also closes a real gap: the AI-generate dialog's Photo tab hit /api/v1/ai/import-photo directly with no tier check in the UI (server route was already correctly gated) — a locked-out user could fill it in and hit a dead-end error instead of an upgrade prompt. Now threaded through the same lock/hide props as the dedicated PhotoImportButton.

Co-Authored-By: Claude Sonnet 5 <noreply@anthropic.com>
This commit is contained in:
Arnaud
2026-07-24 14:04:27 +02:00
parent 1dd8abfd52
commit 1fe379bcdc
15 changed files with 240 additions and 32 deletions
@@ -2,12 +2,17 @@ import { NextRequest, NextResponse } from "next/server";
import { db, recipes, recipeSnapshots } from "@epicure/db";
import { eq, and, desc } from "@epicure/db";
import { requireSessionOrApiKey } from "@/lib/api-auth";
import { requireFeatureEnabledResponse } from "@/lib/feature-flags";
type Params = { params: Promise<{ id: string }> };
export async function GET(req: NextRequest, { params }: Params) {
const { session, response } = await requireSessionOrApiKey(req, { rateLimit: { limit: 60, windowSeconds: 60 } });
if (response) return response;
const featureDenied = await requireFeatureEnabledResponse(session!.user.id, "version_history");
if (featureDenied) return featureDenied;
const { id } = await params;
// Verify ownership