Bicyblex Store relies entirely on Supabase for its database, file storage, and user authentication. Every admin action — publishing products, managing categories, uploading images, and writing news articles — flows through a single Supabase project. This guide walks through setting up all required resources in a new or existing Supabase project so the application is fully operational from day one.Documentation Index
Fetch the complete documentation index at: https://mintlify.com/bicyblex/bicyblexStore/llms.txt
Use this file to discover all available pages before exploring further.
Go to supabase.com, sign in, and click New project. Choose an organisation, give the project a name (e.g.
bicyblex-store), set a strong database password, and select the region closest to your users.Once the project finishes provisioning, open Project Settings → API and note down two values — you will need them in the next step:
Add both to your
.env.local file as described in Environment Variables.The
categories table is the foundation of the product catalogue. Every product references a category via a foreign key, and the category’s slug drives the dynamic specification fields rendered in the product form.The application expects four specific category slugs —
bicicletas, bicimotos-electricas, kits-electricos, and accesorios — because ProductForm.jsx maps each slug to a set of dynamic technical-spec fields via its CONFIG object:bicicletasaro, material, frenobicimotos-electricasautonomia, potencia, velocidadkits-electricosdescripcionaccesoriosDato 1, Dato 2, Dato 3INSERT INTO categories (name, slug) VALUES
('Bicicletas', 'bicicletas'),
('Bicimotos Eléctricas', 'bicimotos-electricas'),
('Kits Eléctricos', 'kits-electricos'),
('Accesorios', 'accesorios');
You can add extra categories through the dashboard’s category manager, which
auto-generates slugs from the category name. Only the four slugs above trigger
predefined spec field sets in the product form — new slugs will produce no
spec fields until the
CONFIG object in ProductForm.jsx is updated.The
products table stores the full inventory. It references categories via a foreign key and uses a JSONB column for flexible, per-category technical specifications.CREATE TABLE products (
id SERIAL PRIMARY KEY,
name TEXT NOT NULL,
price NUMERIC(10, 2) NOT NULL DEFAULT 0,
stock INTEGER NOT NULL DEFAULT 0,
category_id INTEGER REFERENCES categories(id),
specs JSONB DEFAULT '{}',
image TEXT,
tag TEXT DEFAULT 'general'
);
price — stored as NUMERIC(10, 2); the application reads and writes it as a JavaScript float via parseFloat().stock — read and written as an integer via parseInt().category_id — foreign key to categories.id; the product manager queries it with .select("*, categories(name)") to join the category name in a single round-trip.specs — a JSONB object whose keys vary by category (e.g. { "aro": "29\"", "material": "Aluminio", "freno": "Disco" } for bicicletas).image — stores the full public URL of the image uploaded to the products storage bucket.tag — a free-text label; defaults to 'general'.The
news table backs the newsletter / blog section managed from the /dashboard/newsletter panel. Slugs and excerpts are auto-generated by the application at save time.CREATE TABLE news (
id SERIAL PRIMARY KEY,
title TEXT NOT NULL,
content TEXT NOT NULL,
image TEXT,
slug TEXT NOT NULL UNIQUE,
excerpt TEXT,
created_at TIMESTAMPTZ DEFAULT NOW()
);
The
slug is derived from the article title by lower-casing, stripping accents, and replacing spaces with hyphens. The excerpt is the first 150 characters of content, both computed client-side before the INSERT.Bicyblex Store uses two Supabase Storage buckets — one for product images and one for news cover images. In your Supabase dashboard, go to Storage and create each bucket:
products bucket
Bucket name:
productsSet the bucket to Public so that the CDN URLs returned by
getPublicUrl() are accessible to all storefront visitors without
authentication.Product images are converted to WebP format client-side before upload
and stored with a timestamp-randomised filename.news bucket
Bucket name:
newsSet the bucket to Public for the same reason — news cover images are
displayed on the public-facing storefront.Files are stored inside a news/ prefix path within the bucket (e.g.
news/1720000000000-abc123.jpg).For each bucket, after creation go to Storage → Policies and verify that the
anon role has at minimum SELECT access so that public image URLs resolve correctly. For admin upload/delete operations, ensure the authenticated role has INSERT, UPDATE, and DELETE permissions, or disable bucket-level RLS entirely for a simple setup (see Step 7).The
/dashboard route is protected by Supabase Auth. The application calls supabase.auth.getSession() on load to verify the session and supabase.auth.signOut() on logout. You must create at least one admin user manually:Use these credentials to sign in to the
/dashboard page of your deployed or local Bicyblex Store instance. No further role configuration is required — any authenticated Supabase user has access to the admin dashboard.Supabase enables Row Level Security (RLS) by default on all new tables. With
RLS active and no policies defined, all reads and writes from the client
will be silently blocked, causing the dashboard to display empty tables and
all save operations to fail without an obvious error. You must either define
appropriate policies or disable RLS before the application will function
correctly.
For a simple admin-only deployment where the
anon key is only used by trusted operators, you can disable RLS on all three tables:ALTER TABLE categories DISABLE ROW LEVEL SECURITY;
ALTER TABLE products DISABLE ROW LEVEL SECURITY;
ALTER TABLE news DISABLE ROW LEVEL SECURITY;
For a production deployment with public storefront access, consider keeping RLS enabled and adding a permissive
SELECT policy for the anon role on products, categories, and news, while restricting INSERT, UPDATE, and DELETE to the authenticated role:-- Allow public read access
CREATE POLICY "Public read" ON products FOR SELECT USING (true);
CREATE POLICY "Public read" ON categories FOR SELECT USING (true);
CREATE POLICY "Public read" ON news FOR SELECT USING (true);
-- Allow authenticated users full write access
CREATE POLICY "Auth write" ON products FOR ALL TO authenticated USING (true);
CREATE POLICY "Auth write" ON categories FOR ALL TO authenticated USING (true);
CREATE POLICY "Auth write" ON news FOR ALL TO authenticated USING (true);
Storage bucket policies
When a bucket is set to public in Supabase, its files are accessible via their public URL with no authentication required — this is the correct setting for Bicyblex Store since product and news images are displayed on the public storefront. For upload and delete operations (triggered from the admin dashboard), Supabase Storage uses the same RLS policy model as the database. Ensure theauthenticated role has the following permissions on both the products and news buckets:
| Operation | Role | Required |
|---|---|---|
| SELECT | anon | Yes — for public image URL resolution |
| INSERT | authenticated | Yes — for uploading new images |
| UPDATE | authenticated | Yes — for replacing existing images |
| DELETE | authenticated | Yes — for removing old images |
INSERT INTO storage.policies statements via the SQL editor.
Once all resources are created, return to Environment Variables to add your Project URL and anon key to
.env.local, then start the dev server with npm run dev.