site-web-targo/supabase/migrations/20260211141648_b09a13f2-9732-4cbc-998c-e6969a4405c4.sql
louispaulb 88dc3714a1 Initial deploy: gigafibre.ca website with self-hosted address search
React/Vite/shadcn-ui site for Gigafibre ISP.
Address qualification via PostgreSQL (5.2M AQ addresses, pg_trgm fuzzy search).
No Supabase dependency for address search.

Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com>
2026-03-27 14:37:50 -04:00

149 lines
4.7 KiB
PL/PgSQL

-- Enable trigram extension for fuzzy search
CREATE EXTENSION IF NOT EXISTS pg_trgm;
-- Table 1: Adresses CTOP complètes
CREATE TABLE public.addresses (
id BIGINT GENERATED ALWAYS AS IDENTITY PRIMARY KEY,
identifiant_unique_adresse TEXT NOT NULL UNIQUE,
date_diffusion_version TEXT,
date_creation TEXT,
date_modification TEXT,
date_fin TEXT,
numero_municipal TEXT,
numero_municipal_suffixe TEXT,
numero_unite TEXT,
type_unite TEXT,
code_postal TEXT,
seqodo TEXT,
generique_odonyme TEXT,
particule_odonyme TEXT,
specifique_odonyme TEXT,
point_cardinal_odonyme TEXT,
odonyme_recompose_normal TEXT,
odonyme_recompose_court TEXT,
odonyme_recompose_long TEXT,
discriminant_odonyme TEXT,
odonyme_officiel_ctop TEXT,
adresse_formatee TEXT,
qualite_positionnement_geometrique TEXT,
etat TEXT,
code_utilisation TEXT,
categorie TEXT,
nombre_unite INTEGER,
numero_lot TEXT,
matricule_unite_evaluation TEXT,
nosqnocivq TEXT,
caracteristique_adresse TEXT,
code_region_administrative TEXT,
nom_region_administrative TEXT,
code_mrc TEXT,
nom_mrc TEXT,
code_municipalite TEXT,
nom_municipalite TEXT,
nom_municipalite_complet TEXT,
code_arrondissement TEXT,
nom_arrondissement TEXT,
code_communaute_metropolitaine TEXT,
nom_communaute_metropolitaine TEXT,
identifiant_reseau_routier TEXT,
cote_route TEXT,
longitude DOUBLE PRECISION,
latitude DOUBLE PRECISION
);
-- Table 2: Disponibilité fibre
CREATE TABLE public.fiber_availability (
id BIGINT GENERATED ALWAYS AS IDENTITY PRIMARY KEY,
id_placemark TEXT,
id_appart TEXT,
uuidadresse TEXT NOT NULL,
nom TEXT,
civique TEXT,
appartement TEXT,
rue TEXT,
ville TEXT,
code_postal TEXT,
lien_googlemap TEXT,
zone_tarifaire INTEGER NOT NULL DEFAULT 1,
max_speed INTEGER NOT NULL DEFAULT 0,
commentaire TEXT,
CONSTRAINT fk_fiber_address FOREIGN KEY (uuidadresse) REFERENCES public.addresses(identifiant_unique_adresse)
);
-- Index unique sur uuidadresse pour lookup rapide
CREATE INDEX idx_fiber_uuidadresse ON public.fiber_availability(uuidadresse);
-- Indexes trigram pour recherche fuzzy sur adresses
CREATE INDEX idx_addr_odonyme_normal_trgm ON public.addresses USING GIN (odonyme_recompose_normal gin_trgm_ops);
CREATE INDEX idx_addr_odonyme_court_trgm ON public.addresses USING GIN (odonyme_recompose_court gin_trgm_ops);
CREATE INDEX idx_addr_odonyme_long_trgm ON public.addresses USING GIN (odonyme_recompose_long gin_trgm_ops);
CREATE INDEX idx_addr_formatee_trgm ON public.addresses USING GIN (adresse_formatee gin_trgm_ops);
CREATE INDEX idx_addr_municipalite_trgm ON public.addresses USING GIN (nom_municipalite gin_trgm_ops);
CREATE INDEX idx_addr_code_postal ON public.addresses(code_postal);
CREATE INDEX idx_addr_numero_municipal ON public.addresses(numero_municipal);
-- Fonction de recherche d'adresses avec disponibilité fibre
CREATE OR REPLACE FUNCTION public.search_addresses(
search_term TEXT,
result_limit INTEGER DEFAULT 10
)
RETURNS TABLE (
identifiant_unique_adresse TEXT,
adresse_formatee TEXT,
numero_municipal TEXT,
numero_unite TEXT,
code_postal TEXT,
odonyme_recompose_normal TEXT,
nom_municipalite TEXT,
longitude DOUBLE PRECISION,
latitude DOUBLE PRECISION,
fiber_available BOOLEAN,
zone_tarifaire INTEGER,
max_speed INTEGER,
similarity_score REAL
)
LANGUAGE plpgsql
SECURITY DEFINER
SET search_path = public
AS $$
BEGIN
RETURN QUERY
SELECT
a.identifiant_unique_adresse,
a.adresse_formatee,
a.numero_municipal,
a.numero_unite,
a.code_postal,
a.odonyme_recompose_normal,
a.nom_municipalite,
a.longitude,
a.latitude,
(f.id IS NOT NULL) AS fiber_available,
f.zone_tarifaire,
f.max_speed,
GREATEST(
similarity(COALESCE(a.odonyme_recompose_normal, ''), search_term),
similarity(COALESCE(a.odonyme_recompose_court, ''), search_term),
similarity(COALESCE(a.odonyme_recompose_long, ''), search_term),
similarity(COALESCE(a.adresse_formatee, ''), search_term)
) AS similarity_score
FROM public.addresses a
LEFT JOIN public.fiber_availability f ON f.uuidadresse = a.identifiant_unique_adresse
WHERE
a.odonyme_recompose_normal % search_term
OR a.odonyme_recompose_court % search_term
OR a.odonyme_recompose_long % search_term
OR a.adresse_formatee % search_term
ORDER BY similarity_score DESC
LIMIT result_limit;
END;
$$;
-- RLS: lecture publique pour l'auto-suggest
ALTER TABLE public.addresses ENABLE ROW LEVEL SECURITY;
CREATE POLICY "Public read access for addresses" ON public.addresses FOR SELECT USING (true);
ALTER TABLE public.fiber_availability ENABLE ROW LEVEL SECURITY;
CREATE POLICY "Public read access for fiber" ON public.fiber_availability FOR SELECT USING (true);