Files
root-org/supabase/migrations/046_map_layers_pins.sql

109 lines
3.8 KiB
SQL

-- ============================================================
-- Map Layers & Pins: persistent map data for department map module
-- ============================================================
-- 1. Map Layers (each department can have multiple map layers)
CREATE TABLE map_layers (
id UUID PRIMARY KEY DEFAULT gen_random_uuid(),
department_id UUID NOT NULL REFERENCES event_departments(id) ON DELETE CASCADE,
name TEXT NOT NULL DEFAULT 'Map',
layer_type TEXT NOT NULL DEFAULT 'osm' CHECK (layer_type IN ('osm', 'image')),
image_url TEXT,
image_width INT,
image_height INT,
center_lat DOUBLE PRECISION DEFAULT 0,
center_lng DOUBLE PRECISION DEFAULT 0,
zoom_level INT DEFAULT 13,
sort_order INT NOT NULL DEFAULT 0,
created_by UUID REFERENCES auth.users(id) ON DELETE SET NULL,
created_at TIMESTAMPTZ DEFAULT now(),
updated_at TIMESTAMPTZ DEFAULT now()
);
CREATE INDEX idx_map_layers_dept ON map_layers(department_id);
-- 2. Map Pins (belong to a layer)
CREATE TABLE map_pins (
id UUID PRIMARY KEY DEFAULT gen_random_uuid(),
layer_id UUID NOT NULL REFERENCES map_layers(id) ON DELETE CASCADE,
label TEXT NOT NULL,
description TEXT DEFAULT '',
color TEXT NOT NULL DEFAULT '#EF4444',
lat DOUBLE PRECISION NOT NULL,
lng DOUBLE PRECISION NOT NULL,
bounds_north DOUBLE PRECISION,
bounds_south DOUBLE PRECISION,
bounds_east DOUBLE PRECISION,
bounds_west DOUBLE PRECISION,
sort_order INT NOT NULL DEFAULT 0,
created_by UUID REFERENCES auth.users(id) ON DELETE SET NULL,
created_at TIMESTAMPTZ DEFAULT now(),
updated_at TIMESTAMPTZ DEFAULT now()
);
CREATE INDEX idx_map_pins_layer ON map_pins(layer_id);
-- 3. RLS
ALTER TABLE map_layers ENABLE ROW LEVEL SECURITY;
ALTER TABLE map_pins ENABLE ROW LEVEL SECURITY;
-- Map Layers: org members can view
CREATE POLICY "Org members can view map layers" ON map_layers FOR SELECT
USING (EXISTS (
SELECT 1 FROM event_departments ed
JOIN events e ON ed.event_id = e.id
JOIN org_members om ON e.org_id = om.org_id
WHERE ed.id = map_layers.department_id AND om.user_id = auth.uid()
));
-- Map Layers: dept members + editors can manage
CREATE POLICY "Dept members and editors can manage map layers" ON map_layers FOR ALL
USING (EXISTS (
SELECT 1 FROM event_departments ed
JOIN events e ON ed.event_id = e.id
JOIN org_members om ON e.org_id = om.org_id
WHERE ed.id = map_layers.department_id
AND om.user_id = auth.uid()
AND (
om.role IN ('owner', 'admin', 'editor')
OR EXISTS (
SELECT 1 FROM event_member_departments emd
JOIN event_members em ON emd.event_member_id = em.id
WHERE emd.department_id = ed.id AND em.user_id = auth.uid()
)
)
));
-- Map Pins: org members can view
CREATE POLICY "Org members can view map pins" ON map_pins FOR SELECT
USING (EXISTS (
SELECT 1 FROM map_layers ml
JOIN event_departments ed ON ml.department_id = ed.id
JOIN events e ON ed.event_id = e.id
JOIN org_members om ON e.org_id = om.org_id
WHERE ml.id = map_pins.layer_id AND om.user_id = auth.uid()
));
-- Map Pins: dept members + editors can manage
CREATE POLICY "Dept members and editors can manage map pins" ON map_pins FOR ALL
USING (EXISTS (
SELECT 1 FROM map_layers ml
JOIN event_departments ed ON ml.department_id = ed.id
JOIN events e ON ed.event_id = e.id
JOIN org_members om ON e.org_id = om.org_id
WHERE ml.id = map_pins.layer_id
AND om.user_id = auth.uid()
AND (
om.role IN ('owner', 'admin', 'editor')
OR EXISTS (
SELECT 1 FROM event_member_departments emd
JOIN event_members em ON emd.event_member_id = em.id
WHERE emd.department_id = ed.id AND em.user_id = auth.uid()
)
)
));
-- 4. Realtime
ALTER PUBLICATION supabase_realtime ADD TABLE map_layers;
ALTER PUBLICATION supabase_realtime ADD TABLE map_pins;