Tier model: registered=basic (recipes, 12 photos, QR), PRO=verified or admin-activated (HSL, tools/gradient mask, RAW, export > source longest edge); admin users table gets Activated Pro column

This commit is contained in:
2026-09-30 11:50:28 +07:00
parent 35d8d57984
commit 74c0b2747f
10 changed files with 264 additions and 122 deletions
+13 -6
View File
@@ -1,12 +1,18 @@
// One table for the guest/user split, so the policy can change without touching
// the UI. Guest = the landing + a capped, watermarked demo; user = full tools,
// full-resolution export, saved recipes.
// One table for the three tiers, so the policy can change without touching the
// UI. guest = the landing + a capped, watermarked demo; member = any signed-in
// account, which is the basic tier: recipes, the photo folder and a clean export
// of the photo it is editing; pro = the operator's Activated Pro box, which adds
// the PRO tools (HSL, TOOLS and GRADIENT MASK, RAW) and lets the export run past
// the photo's own pixels.
//
// `maxExportDim` here is the tier's own ceiling. The basic tier's ceiling is the
// photo being edited, which only the caller knows — see `exportCap` in App.
export type TierId = 'guest' | 'user';
export type TierId = 'guest' | 'member' | 'pro';
export interface Tier {
id: TierId;
/** Longest edge of an exported photo, or null for the original size. */
/** Longest edge of an exported photo, or null for the caller's own ceiling. */
maxExportDim: number | null;
/** Text burned into every export, or null for a clean file. */
watermark: string | null;
@@ -15,5 +21,6 @@ export interface Tier {
export const TIERS: Record<TierId, Tier> = {
guest: { id: 'guest', maxExportDim: 2048, watermark: 'RecipesCam demo', batchExport: false },
user: { id: 'user', maxExportDim: null, watermark: null, batchExport: true },
member: { id: 'member', maxExportDim: null, watermark: null, batchExport: false },
pro: { id: 'pro', maxExportDim: null, watermark: null, batchExport: true },
};