Skip to Content
Otras herramientas y adaptadoresAdaptadores de bases de datosSupabase

Adaptador Supabase Postgres

El paquete tracelet_supabase proporciona un adaptador directo para sincronizar sus ubicaciones en segundo plano directamente en Supabase Postgres, a través de una función RPC de Postgres o una función Edge de Supabase.

Instalación

Añade el adaptador a tu pubspec.yaml:

flutter pub add tracelet_supabase

Este adaptador utiliza supabase_flutter. Debe inicializar el cliente Supabase antes de usarlo.

Cómo funciona

El adaptador se conecta al motor de sincronización HTTP nativo de Tracelet que ahorra batería: buildHttpConfig produce un HttpConfig que apunta a su punto final REST de Supabase, ya sea /rest/v1/rpc/<function> (RPC) o /functions/v1/<function> (función de borde), con los encabezados apikey y Authorization: Bearer <token> configurados para usted.

Debido a que la sincronización se ejecuta en el motor nativo, los lotes se cargan con un retraso exponencial y colas fuera de línea incluso cuando se fuerza el cierre de la aplicación. En 401, configureTokenRefresh actualiza la sesión de Supabase (en primer plano y en un aislamiento de fondo sin cabeza) y vuelve a intentarlo. Proporciona exactamente un destino: rpcFunction o edgeFunction.

Instalación y configuración

Crear una tabla y una función de ingesta.

Cree una tabla para recibir las ubicaciones, habilite RLS y agregue una función de Postgres que inserte un lote entrante. Tracelet publica un lote de objetos de ubicación, por lo que la función acepta una matriz jsonb:

-- Table CREATE TABLE public.locations ( id uuid DEFAULT gen_random_uuid() PRIMARY KEY, user_id uuid REFERENCES auth.users NOT NULL DEFAULT auth.uid(), latitude double precision NOT NULL, longitude double precision NOT NULL, accuracy double precision, speed double precision, timestamp timestamptz NOT NULL, is_moving boolean, created_at timestamptz DEFAULT now() ); ALTER TABLE public.locations ENABLE ROW LEVEL SECURITY; CREATE POLICY "Users insert their own locations" ON public.locations FOR INSERT WITH CHECK (auth.uid() = user_id); -- RPC function: receives the batch as a jsonb array and inserts each row. -- (The exact field names come from Tracelet's sync payload — see the -- Tracelet Sync docs for the payload schema.) CREATE OR REPLACE FUNCTION public.insert_tracelet_locations(payload jsonb) RETURNS void LANGUAGE sql SECURITY INVOKER AS $$ INSERT INTO public.locations (latitude, longitude, accuracy, speed, timestamp, is_moving) SELECT (e->'coords'->>'latitude')::double precision, (e->'coords'->>'longitude')::double precision, (e->'coords'->>'accuracy')::double precision, (e->'coords'->>'speed')::double precision, (e->>'timestamp')::timestamptz, (e->>'is_moving')::boolean FROM jsonb_array_elements(payload) AS e; $$;

¿Prefiere un procesamiento más personalizado (validación, distribución, enriquecimiento)? Implemente una Supabase Edge Function en su lugar y pase su nombre como edgeFunction: el adaptador PUBLICARA el lote en /functions/v1/<name>.

Inicializar Supabase

Inicialice el cliente Supabase en su main.dart:

import 'package:supabase_flutter/supabase_flutter.dart'; void main() async { WidgetsFlutterBinding.ensureInitialized(); await Supabase.initialize( url: 'https://xyzcompany.supabase.co', anonKey: 'public-anon-key', ); runApp(const MyApp()); }

Configure la actualización del token y cree la configuración HTTP

Llame a configureTokenRefresh() una vez, cree HttpConfig dirigido a su RPC (o función de borde) y páselo a Tracelet.ready:

import 'package:tracelet_supabase/tracelet_supabase.dart'; import 'package:tracelet/tracelet.dart'; const supabaseUrl = 'https://xyzcompany.supabase.co'; const supabaseAnonKey = 'public-anon-key'; // 1. Keep the Supabase session token fresh in the background (resolves 401s). await TraceletSupabase.configureTokenRefresh(anonKey: supabaseAnonKey); // 2. Build the native HTTP config. Provide EITHER rpcFunction OR edgeFunction. final httpConfig = TraceletSupabase.buildHttpConfig( supabaseUrl: supabaseUrl, anonKey: supabaseAnonKey, rpcFunction: 'insert_tracelet_locations', // ...or: edgeFunction: 'tracelet-ingest' // autoSync: true, batchSync: true, maxBatchSize: 250 are the defaults ); // 3. Start Tracelet with the adapter's HTTP config. await Tracelet.ready(Config( geo: const GeoConfig(distanceFilter: 50), http: httpConfig, )); await Tracelet.start();

Adjuntar metadatos personalizados

Para etiquetar cada ubicación con datos comerciales (por ejemplo, driver_id o trip_id), use setRouteContext(): viaja con cada ubicación a través de la cola SQLite y se incluye en la carga útil que recibe su función:

await Tracelet.setRouteContext(RouteContext( taskId: 'order_123', custom: {'trip_id': 'trip_456'}, ));

Actuación

La sincronización se ejecuta a través del motor por lotes de Tracelet, por lo que una acumulación de puntos fuera de línea se elimina en lotes (maxBatchSize: 250 predeterminado) en lugar de una solicitud por punto. Combinado con el inserto masivo de Postgres dentro de su RPC, esto mantiene el seguimiento de alta frecuencia (por ejemplo, un punto cada 10 m) eficiente tanto en la batería del dispositivo como en los viajes de ida y vuelta de la base de datos.