primeiras_alteracoes
This commit is contained in:
275
migrate_rdo_schema.sql
Normal file
275
migrate_rdo_schema.sql
Normal file
@@ -0,0 +1,275 @@
|
|||||||
|
-- ============================================================================
|
||||||
|
-- MIGRAÇÃO COMPLETA DO SCHEMA 'rdo' PARA SUPABASE
|
||||||
|
-- Executar este script no SQL Editor do Supabase
|
||||||
|
-- ============================================================================
|
||||||
|
|
||||||
|
-- 1. CRIAR ESQUEMA
|
||||||
|
-- ============================================================================
|
||||||
|
CREATE SCHEMA IF NOT EXISTS rdo;
|
||||||
|
|
||||||
|
-- 2. GARANTIR EXTENSÕES
|
||||||
|
-- ============================================================================
|
||||||
|
CREATE EXTENSION IF NOT EXISTS "uuid-ossp";
|
||||||
|
|
||||||
|
-- 3. CRIAR TABELAS NO ESQUEMA 'rdo'
|
||||||
|
-- ============================================================================
|
||||||
|
|
||||||
|
-- Tabela: Organizacoes
|
||||||
|
CREATE TABLE IF NOT EXISTS rdo.organizacoes (
|
||||||
|
id UUID DEFAULT gen_random_uuid() PRIMARY KEY,
|
||||||
|
nome TEXT NOT NULL,
|
||||||
|
slug TEXT UNIQUE NOT NULL,
|
||||||
|
razao_social TEXT,
|
||||||
|
cnpj TEXT,
|
||||||
|
status TEXT DEFAULT 'ativa' CHECK (status IN ('ativa', 'inativa', 'suspensa')),
|
||||||
|
plano TEXT DEFAULT 'trial' CHECK (plano IN ('trial', 'basico', 'profissional', 'enterprise')),
|
||||||
|
max_usuarios INTEGER DEFAULT 5,
|
||||||
|
max_obras INTEGER DEFAULT 10,
|
||||||
|
max_rdos_mes INTEGER DEFAULT 100,
|
||||||
|
max_storage_mb INTEGER DEFAULT 1024,
|
||||||
|
created_at TIMESTAMPTZ DEFAULT NOW(),
|
||||||
|
updated_at TIMESTAMPTZ DEFAULT NOW()
|
||||||
|
);
|
||||||
|
|
||||||
|
-- Tabela: Usuarios
|
||||||
|
CREATE TABLE IF NOT EXISTS rdo.usuarios (
|
||||||
|
id UUID PRIMARY KEY REFERENCES auth.users(id) ON DELETE CASCADE,
|
||||||
|
organizacao_id UUID REFERENCES rdo.organizacoes(id) ON DELETE SET NULL,
|
||||||
|
email TEXT NOT NULL,
|
||||||
|
nome TEXT NOT NULL,
|
||||||
|
telefone TEXT,
|
||||||
|
cargo TEXT,
|
||||||
|
role TEXT DEFAULT 'usuario' CHECK (role IN ('dev', 'admin', 'engenheiro', 'mestre_obra', 'usuario')),
|
||||||
|
ativo BOOLEAN DEFAULT true,
|
||||||
|
created_at TIMESTAMPTZ DEFAULT NOW(),
|
||||||
|
updated_at TIMESTAMPTZ DEFAULT NOW()
|
||||||
|
);
|
||||||
|
|
||||||
|
-- Tabela: Obras
|
||||||
|
CREATE TABLE IF NOT EXISTS rdo.obras (
|
||||||
|
id UUID DEFAULT gen_random_uuid() PRIMARY KEY,
|
||||||
|
organizacao_id UUID NOT NULL REFERENCES rdo.organizacoes(id) ON DELETE CASCADE,
|
||||||
|
nome TEXT NOT NULL,
|
||||||
|
descricao TEXT,
|
||||||
|
endereco TEXT,
|
||||||
|
cep TEXT,
|
||||||
|
cidade TEXT,
|
||||||
|
estado TEXT,
|
||||||
|
responsavel_id UUID REFERENCES rdo.usuarios(id) ON DELETE SET NULL,
|
||||||
|
data_inicio DATE,
|
||||||
|
data_prevista_fim DATE,
|
||||||
|
data_conclusao DATE,
|
||||||
|
progresso_geral NUMERIC(5,2) DEFAULT 0,
|
||||||
|
status TEXT DEFAULT 'ativa' CHECK (status IN ('ativa', 'pausada', 'concluida', 'cancelada')),
|
||||||
|
configuracoes JSONB DEFAULT '{}'::jsonb,
|
||||||
|
created_at TIMESTAMPTZ DEFAULT NOW(),
|
||||||
|
updated_at TIMESTAMPTZ DEFAULT NOW()
|
||||||
|
);
|
||||||
|
|
||||||
|
-- Tabela: RDOs
|
||||||
|
CREATE TABLE IF NOT EXISTS rdo.rdos (
|
||||||
|
id UUID DEFAULT gen_random_uuid() PRIMARY KEY,
|
||||||
|
organizacao_id UUID REFERENCES rdo.organizacoes(id) ON DELETE CASCADE,
|
||||||
|
obra_id UUID NOT NULL REFERENCES rdo.obras(id) ON DELETE CASCADE,
|
||||||
|
criado_por UUID NOT NULL REFERENCES rdo.usuarios(id),
|
||||||
|
data_relatorio DATE NOT NULL,
|
||||||
|
condicoes_climaticas TEXT NOT NULL,
|
||||||
|
observacoes_gerais TEXT,
|
||||||
|
status TEXT DEFAULT 'rascunho' CHECK (status IN ('rascunho', 'enviado', 'aprovado', 'rejeitado')),
|
||||||
|
aprovado_por UUID REFERENCES rdo.usuarios(id),
|
||||||
|
aprovado_em TIMESTAMPTZ,
|
||||||
|
created_at TIMESTAMPTZ DEFAULT NOW(),
|
||||||
|
updated_at TIMESTAMPTZ DEFAULT NOW()
|
||||||
|
);
|
||||||
|
|
||||||
|
-- Tabela: RDO Atividades
|
||||||
|
CREATE TABLE IF NOT EXISTS rdo.rdo_atividades (
|
||||||
|
id UUID DEFAULT gen_random_uuid() PRIMARY KEY,
|
||||||
|
rdo_id UUID NOT NULL REFERENCES rdo.rdos(id) ON DELETE CASCADE,
|
||||||
|
tipo_atividade TEXT NOT NULL,
|
||||||
|
descricao TEXT NOT NULL,
|
||||||
|
localizacao TEXT,
|
||||||
|
percentual_concluido NUMERIC(5,2) DEFAULT 0,
|
||||||
|
ordem INTEGER DEFAULT 0,
|
||||||
|
created_at TIMESTAMPTZ DEFAULT NOW()
|
||||||
|
);
|
||||||
|
|
||||||
|
-- Tabela: RDO Mão de Obra
|
||||||
|
CREATE TABLE IF NOT EXISTS rdo.rdo_mao_obra (
|
||||||
|
id UUID DEFAULT gen_random_uuid() PRIMARY KEY,
|
||||||
|
rdo_id UUID NOT NULL REFERENCES rdo.rdos(id) ON DELETE CASCADE,
|
||||||
|
funcao TEXT NOT NULL,
|
||||||
|
quantidade INTEGER DEFAULT 0,
|
||||||
|
horas_trabalhadas NUMERIC(5,2) DEFAULT 0,
|
||||||
|
observacoes TEXT,
|
||||||
|
created_at TIMESTAMPTZ DEFAULT NOW()
|
||||||
|
);
|
||||||
|
|
||||||
|
-- Tabela: RDO Equipamentos
|
||||||
|
CREATE TABLE IF NOT EXISTS rdo.rdo_equipamentos (
|
||||||
|
id UUID DEFAULT gen_random_uuid() PRIMARY KEY,
|
||||||
|
rdo_id UUID NOT NULL REFERENCES rdo.rdos(id) ON DELETE CASCADE,
|
||||||
|
nome_equipamento TEXT NOT NULL,
|
||||||
|
tipo TEXT,
|
||||||
|
horas_utilizadas NUMERIC(5,2) DEFAULT 0,
|
||||||
|
combustivel_gasto NUMERIC(10,2) DEFAULT 0,
|
||||||
|
observacoes TEXT,
|
||||||
|
created_at TIMESTAMPTZ DEFAULT NOW()
|
||||||
|
);
|
||||||
|
|
||||||
|
-- Tabela: RDO Ocorrencias
|
||||||
|
CREATE TABLE IF NOT EXISTS rdo.rdo_ocorrencias (
|
||||||
|
id UUID DEFAULT gen_random_uuid() PRIMARY KEY,
|
||||||
|
rdo_id UUID NOT NULL REFERENCES rdo.rdos(id) ON DELETE CASCADE,
|
||||||
|
tipo_ocorrencia TEXT NOT NULL,
|
||||||
|
descricao TEXT NOT NULL,
|
||||||
|
gravidade TEXT CHECK (gravidade IN ('baixa', 'media', 'alta', 'critica')),
|
||||||
|
acao_tomada TEXT,
|
||||||
|
created_at TIMESTAMPTZ DEFAULT NOW()
|
||||||
|
);
|
||||||
|
|
||||||
|
-- Tabela: RDO Anexos
|
||||||
|
CREATE TABLE IF NOT EXISTS rdo.rdo_anexos (
|
||||||
|
id UUID DEFAULT gen_random_uuid() PRIMARY KEY,
|
||||||
|
rdo_id UUID NOT NULL REFERENCES rdo.rdos(id) ON DELETE CASCADE,
|
||||||
|
nome_arquivo TEXT NOT NULL,
|
||||||
|
tipo_arquivo TEXT,
|
||||||
|
url_storage TEXT NOT NULL,
|
||||||
|
tamanho_bytes BIGINT,
|
||||||
|
descricao TEXT,
|
||||||
|
created_at TIMESTAMPTZ DEFAULT NOW()
|
||||||
|
);
|
||||||
|
|
||||||
|
-- Tabela: Tipos de Atividade (configuração)
|
||||||
|
CREATE TABLE IF NOT EXISTS rdo.tipos_atividade (
|
||||||
|
id UUID DEFAULT gen_random_uuid() PRIMARY KEY,
|
||||||
|
nome TEXT NOT NULL,
|
||||||
|
descricao TEXT,
|
||||||
|
ativo BOOLEAN DEFAULT true,
|
||||||
|
created_at TIMESTAMPTZ DEFAULT NOW()
|
||||||
|
);
|
||||||
|
|
||||||
|
-- Tabela: Condições Climáticas (configuração)
|
||||||
|
CREATE TABLE IF NOT EXISTS rdo.condicoes_climaticas (
|
||||||
|
id UUID DEFAULT gen_random_uuid() PRIMARY KEY,
|
||||||
|
nome TEXT NOT NULL,
|
||||||
|
descricao TEXT,
|
||||||
|
ativo BOOLEAN DEFAULT true,
|
||||||
|
created_at TIMESTAMPTZ DEFAULT NOW()
|
||||||
|
);
|
||||||
|
|
||||||
|
-- 4. CRIAR ÍNDICES PARA OTIMIZAÇÃO
|
||||||
|
-- ============================================================================
|
||||||
|
CREATE INDEX IF NOT EXISTS idx_usuarios_org ON rdo.usuarios(organizacao_id);
|
||||||
|
CREATE INDEX IF NOT EXISTS idx_obras_org ON rdo.obras(organizacao_id);
|
||||||
|
CREATE INDEX IF NOT EXISTS idx_obras_status ON rdo.obras(status);
|
||||||
|
CREATE INDEX IF NOT EXISTS idx_rdos_obra ON rdo.rdos(obra_id);
|
||||||
|
CREATE INDEX IF NOT EXISTS idx_rdos_data ON rdo.rdos(data_relatorio);
|
||||||
|
CREATE INDEX IF NOT EXISTS idx_rdos_status ON rdo.rdos(status);
|
||||||
|
CREATE INDEX IF NOT EXISTS idx_rdo_atividades_rdo ON rdo.rdo_atividades(rdo_id);
|
||||||
|
CREATE INDEX IF NOT EXISTS idx_rdo_mao_obra_rdo ON rdo.rdo_mao_obra(rdo_id);
|
||||||
|
CREATE INDEX IF NOT EXISTS idx_rdo_equipamentos_rdo ON rdo.rdo_equipamentos(rdo_id);
|
||||||
|
CREATE INDEX IF NOT EXISTS idx_rdo_ocorrencias_rdo ON rdo.rdo_ocorrencias(rdo_id);
|
||||||
|
|
||||||
|
-- 5. HABILITAR RLS
|
||||||
|
-- ============================================================================
|
||||||
|
ALTER TABLE rdo.organizacoes ENABLE ROW LEVEL SECURITY;
|
||||||
|
ALTER TABLE rdo.usuarios ENABLE ROW LEVEL SECURITY;
|
||||||
|
ALTER TABLE rdo.obras ENABLE ROW LEVEL SECURITY;
|
||||||
|
ALTER TABLE rdo.rdos ENABLE ROW LEVEL SECURITY;
|
||||||
|
ALTER TABLE rdo.rdo_atividades ENABLE ROW LEVEL SECURITY;
|
||||||
|
ALTER TABLE rdo.rdo_mao_obra ENABLE ROW LEVEL SECURITY;
|
||||||
|
ALTER TABLE rdo.rdo_equipamentos ENABLE ROW LEVEL SECURITY;
|
||||||
|
ALTER TABLE rdo.rdo_ocorrencias ENABLE ROW LEVEL SECURITY;
|
||||||
|
ALTER TABLE rdo.rdo_anexos ENABLE ROW LEVEL SECURITY;
|
||||||
|
ALTER TABLE rdo.tipos_atividade ENABLE ROW LEVEL SECURITY;
|
||||||
|
ALTER TABLE rdo.condicoes_climaticas ENABLE ROW LEVEL SECURITY;
|
||||||
|
|
||||||
|
-- 6. CRIAR POLÍTICAS RLS
|
||||||
|
-- ============================================================================
|
||||||
|
CREATE POLICY "auth_all_rdo_usuarios" ON rdo.usuarios FOR ALL USING (auth.uid() IS NOT NULL) WITH CHECK (auth.uid() IS NOT NULL);
|
||||||
|
CREATE POLICY "auth_all_rdo_orgs" ON rdo.organizacoes FOR ALL USING (auth.uid() IS NOT NULL) WITH CHECK (auth.uid() IS NOT NULL);
|
||||||
|
CREATE POLICY "auth_all_rdo_obras" ON rdo.obras FOR ALL USING (auth.uid() IS NOT NULL) WITH CHECK (auth.uid() IS NOT NULL);
|
||||||
|
CREATE POLICY "auth_all_rdo_rdos" ON rdo.rdos FOR ALL USING (auth.uid() IS NOT NULL) WITH CHECK (auth.uid() IS NOT NULL);
|
||||||
|
CREATE POLICY "auth_all_rdo_ativ" ON rdo.rdo_atividades FOR ALL USING (auth.uid() IS NOT NULL) WITH CHECK (auth.uid() IS NOT NULL);
|
||||||
|
CREATE POLICY "auth_all_rdo_mao" ON rdo.rdo_mao_obra FOR ALL USING (auth.uid() IS NOT NULL) WITH CHECK (auth.uid() IS NOT NULL);
|
||||||
|
CREATE POLICY "auth_all_rdo_equip" ON rdo.rdo_equipamentos FOR ALL USING (auth.uid() IS NOT NULL) WITH CHECK (auth.uid() IS NOT NULL);
|
||||||
|
CREATE POLICY "auth_all_rdo_ocor" ON rdo.rdo_ocorrencias FOR ALL USING (auth.uid() IS NOT NULL) WITH CHECK (auth.uid() IS NOT NULL);
|
||||||
|
CREATE POLICY "auth_all_rdo_anex" ON rdo.rdo_anexos FOR ALL USING (auth.uid() IS NOT NULL) WITH CHECK (auth.uid() IS NOT NULL);
|
||||||
|
CREATE POLICY "auth_all_rdo_tipos_ativ" ON rdo.tipos_atividade FOR ALL USING (auth.uid() IS NOT NULL) WITH CHECK (auth.uid() IS NOT NULL);
|
||||||
|
CREATE POLICY "auth_all_rdo_cond_clim" ON rdo.condicoes_climaticas FOR ALL USING (auth.uid() IS NOT NULL) WITH CHECK (auth.uid() IS NOT NULL);
|
||||||
|
|
||||||
|
-- 7. PERMISSÕES
|
||||||
|
-- ============================================================================
|
||||||
|
GRANT USAGE ON SCHEMA rdo TO authenticated, anon;
|
||||||
|
GRANT ALL ON ALL TABLES IN SCHEMA rdo TO authenticated;
|
||||||
|
GRANT ALL ON ALL SEQUENCES IN SCHEMA rdo TO authenticated;
|
||||||
|
GRANT ALL ON ALL FUNCTIONS IN SCHEMA rdo TO authenticated;
|
||||||
|
|
||||||
|
-- 8. CRIAR TRIGGER PARA NOVO USUÁRIO
|
||||||
|
-- ============================================================================
|
||||||
|
CREATE OR REPLACE FUNCTION rdo.handle_new_user()
|
||||||
|
RETURNS TRIGGER
|
||||||
|
SECURITY DEFINER
|
||||||
|
SET search_path = rdo, public
|
||||||
|
AS $$
|
||||||
|
DECLARE
|
||||||
|
user_name TEXT;
|
||||||
|
BEGIN
|
||||||
|
user_name := COALESCE(
|
||||||
|
NEW.raw_user_meta_data->>'nome',
|
||||||
|
NEW.raw_user_meta_data->>'name',
|
||||||
|
NEW.raw_user_meta_data->>'full_name',
|
||||||
|
split_part(NEW.email, '@', 1)
|
||||||
|
);
|
||||||
|
|
||||||
|
INSERT INTO rdo.usuarios (id, email, nome, role, ativo)
|
||||||
|
VALUES (NEW.id, NEW.email, user_name, 'usuario', true)
|
||||||
|
ON CONFLICT (id) DO UPDATE SET
|
||||||
|
email = EXCLUDED.email,
|
||||||
|
nome = COALESCE(EXCLUDED.nome, rdo.usuarios.nome),
|
||||||
|
updated_at = NOW();
|
||||||
|
|
||||||
|
RETURN NEW;
|
||||||
|
END;
|
||||||
|
$$ LANGUAGE plpgsql;
|
||||||
|
|
||||||
|
DROP TRIGGER IF EXISTS on_auth_user_created ON auth.users;
|
||||||
|
|
||||||
|
CREATE TRIGGER on_auth_user_created
|
||||||
|
AFTER INSERT ON auth.users
|
||||||
|
FOR EACH ROW
|
||||||
|
EXECUTE FUNCTION rdo.handle_new_user();
|
||||||
|
|
||||||
|
-- 9. DADOS INICIAIS (SEED)
|
||||||
|
-- ============================================================================
|
||||||
|
INSERT INTO rdo.organizacoes (nome, slug, status, plano)
|
||||||
|
VALUES ('Baldon Engemetal', 'baldon-engemetal', 'ativa', 'profissional')
|
||||||
|
ON CONFLICT (slug) DO NOTHING;
|
||||||
|
|
||||||
|
-- Tipos de atividade padrão
|
||||||
|
INSERT INTO rdo.tipos_atividade (nome, descricao, ativo) VALUES
|
||||||
|
('Preparação de Superfície', 'Limpeza, jateamento, primação', true),
|
||||||
|
('Aplicação de Primer', 'Aplicação da primeira camada', true),
|
||||||
|
('Aplicação de Intermediate', 'Camada intermediária', true),
|
||||||
|
('Aplicação de Topcoat', 'Camada final de acabamento', true),
|
||||||
|
(' Inspeção de Qualidade', 'Verificação e controle', true),
|
||||||
|
('Manutenção de Equipamentos', 'Limpeza e manutenção', true),
|
||||||
|
('Transporte e Movimentação', 'Movimentação de peças', true),
|
||||||
|
('Outros', 'Outras atividades', true)
|
||||||
|
ON CONFLICT DO NOTHING;
|
||||||
|
|
||||||
|
-- Condições climáticas padrão
|
||||||
|
INSERT INTO rdo.condicoes_climaticas (nome, descricao, ativo) VALUES
|
||||||
|
('Ensolarado', 'Tempo aberto, sol forte', true),
|
||||||
|
('Parcialmente Nublado', 'Sol entre nuvens', true),
|
||||||
|
('Nublado', 'Céu encoberto', true),
|
||||||
|
('Chuva Leve', 'Chuvisco', true),
|
||||||
|
('Chuva Forte', 'Chuva intensa', true),
|
||||||
|
('Vento Forte', 'Ventania', true),
|
||||||
|
('Umidade Alta', 'Umidade acima de 80%', true),
|
||||||
|
('Temperatura Baixa', 'Abaixo de 15°C', true),
|
||||||
|
('Temperatura Alta', 'Acima de 35°C', true)
|
||||||
|
ON CONFLICT DO NOTHING;
|
||||||
|
|
||||||
|
SELECT 'Schema rdo criado com sucesso!' AS resultado;
|
||||||
@@ -1,6 +1,6 @@
|
|||||||
import { useState, useEffect } from 'react';
|
import { useState, useEffect } from 'react';
|
||||||
import { User, Session, AuthError } from '@supabase/supabase-js';
|
import { User, Session, AuthError } from '@supabase/supabase-js';
|
||||||
import { supabase } from '../lib/supabase';
|
import { supabase, supabaseAuth } from '../lib/supabase';
|
||||||
|
|
||||||
interface AuthState {
|
interface AuthState {
|
||||||
user: User | null;
|
user: User | null;
|
||||||
@@ -32,7 +32,7 @@ export const useAuth = () => {
|
|||||||
// Verificar sessão atual
|
// Verificar sessão atual
|
||||||
const getSession = async () => {
|
const getSession = async () => {
|
||||||
try {
|
try {
|
||||||
const { data: { session }, error } = await supabase.auth.getSession();
|
const { data: { session }, error } = await supabaseAuth.getSession();
|
||||||
if (error) throw error;
|
if (error) throw error;
|
||||||
|
|
||||||
console.log('✅ useAuth: Sessão recuperada:', session?.user?.email);
|
console.log('✅ useAuth: Sessão recuperada:', session?.user?.email);
|
||||||
@@ -99,7 +99,7 @@ export const useAuth = () => {
|
|||||||
getSession();
|
getSession();
|
||||||
|
|
||||||
// Escutar mudanças de autenticação
|
// Escutar mudanças de autenticação
|
||||||
const { data: { subscription } } = supabase.auth.onAuthStateChange(
|
const { data: { subscription } } = supabaseAuth.onAuthStateChange(
|
||||||
async (event, session) => {
|
async (event, session) => {
|
||||||
console.log('🔔 Auth state changed:', event, session?.user?.email);
|
console.log('🔔 Auth state changed:', event, session?.user?.email);
|
||||||
|
|
||||||
@@ -294,8 +294,8 @@ export const useAuth = () => {
|
|||||||
|
|
||||||
setAuthState(prev => ({ ...prev, loading: true, error: null }));
|
setAuthState(prev => ({ ...prev, loading: true, error: null }));
|
||||||
|
|
||||||
console.log('🌐 useAuth: Chamando supabase.auth.signInWithPassword...');
|
console.log('🌐 useAuth: Chamando supabaseAuth.signInWithPassword...');
|
||||||
const { data, error } = await supabase.auth.signInWithPassword({
|
const { data, error } = await supabaseAuth.signInWithPassword({
|
||||||
email: credentials.email,
|
email: credentials.email,
|
||||||
password: credentials.password
|
password: credentials.password
|
||||||
});
|
});
|
||||||
@@ -326,7 +326,7 @@ export const useAuth = () => {
|
|||||||
try {
|
try {
|
||||||
setAuthState(prev => ({ ...prev, loading: true, error: null }));
|
setAuthState(prev => ({ ...prev, loading: true, error: null }));
|
||||||
|
|
||||||
const { data, error } = await supabase.auth.signUp({
|
const { data, error } = await supabaseAuth.signUp({
|
||||||
email: credentials.email,
|
email: credentials.email,
|
||||||
password: credentials.password,
|
password: credentials.password,
|
||||||
options: {
|
options: {
|
||||||
@@ -360,7 +360,7 @@ export const useAuth = () => {
|
|||||||
});
|
});
|
||||||
|
|
||||||
// 2. Disparar signOut do Supabase em background (sem await para não travar a UI)
|
// 2. Disparar signOut do Supabase em background (sem await para não travar a UI)
|
||||||
supabase.auth.signOut().catch(err => console.warn('Erro silencioso no signOut:', err));
|
supabaseAuth.signOut().catch(err => console.warn('Erro silencioso no signOut:', err));
|
||||||
|
|
||||||
// 3. Limpar estado local do hook
|
// 3. Limpar estado local do hook
|
||||||
setAuthState({
|
setAuthState({
|
||||||
@@ -379,7 +379,7 @@ export const useAuth = () => {
|
|||||||
|
|
||||||
const resetPassword = async (email: string) => {
|
const resetPassword = async (email: string) => {
|
||||||
try {
|
try {
|
||||||
const { error } = await supabase.auth.resetPasswordForEmail(email, {
|
const { error } = await supabaseAuth.resetPasswordForEmail(email, {
|
||||||
redirectTo: `${window.location.origin}/reset-password`
|
redirectTo: `${window.location.origin}/reset-password`
|
||||||
});
|
});
|
||||||
|
|
||||||
@@ -392,7 +392,7 @@ export const useAuth = () => {
|
|||||||
|
|
||||||
const updatePassword = async (newPassword: string) => {
|
const updatePassword = async (newPassword: string) => {
|
||||||
try {
|
try {
|
||||||
const { error } = await supabase.auth.updateUser({
|
const { error } = await supabaseAuth.updateUser({
|
||||||
password: newPassword
|
password: newPassword
|
||||||
});
|
});
|
||||||
|
|
||||||
@@ -408,7 +408,7 @@ export const useAuth = () => {
|
|||||||
if (!authState.user) throw new Error('Usuário não autenticado');
|
if (!authState.user) throw new Error('Usuário não autenticado');
|
||||||
|
|
||||||
// Atualizar metadados do usuário
|
// Atualizar metadados do usuário
|
||||||
const { error: authError } = await supabase.auth.updateUser({
|
const { error: authError } = await supabaseAuth.updateUser({
|
||||||
data: updates
|
data: updates
|
||||||
});
|
});
|
||||||
|
|
||||||
|
|||||||
@@ -1,22 +1,23 @@
|
|||||||
import { createClient } from '@supabase/supabase-js'
|
import { createClient, SupabaseClient } from '@supabase/supabase-js'
|
||||||
import { Database } from '../types/database.types'
|
import { Database } from '../types/database.types'
|
||||||
|
|
||||||
// Configurações do Supabase
|
// Configurações do Supabase
|
||||||
const supabaseUrl = import.meta.env.VITE_SUPABASE_URL
|
const supabaseUrl = import.meta.env.VITE_SUPABASE_URL
|
||||||
const supabaseAnonKey = import.meta.env.VITE_SUPABASE_ANON_KEY
|
const supabaseAnonKey = import.meta.env.VITE_SUPABASE_ANON_KEY
|
||||||
|
const serviceRoleKey = import.meta.env.VITE_SERVICE_ROLE_KEY
|
||||||
|
|
||||||
// Verificar se as variáveis de ambiente estão definidas
|
// Verificar se as variáveis de ambiente estão definidas
|
||||||
if (!supabaseUrl || !supabaseAnonKey) {
|
if (!supabaseUrl || !supabaseAnonKey) {
|
||||||
throw new Error('Variáveis de ambiente do Supabase não estão definidas. Verifique VITE_SUPABASE_URL e VITE_SUPABASE_ANON_KEY no arquivo .env')
|
throw new Error('Variáveis de ambiente do Supabase não estão definidas. Verifique VITE_SUPABASE_URL e VITE_SUPABASE_ANON_KEY no arquivo .env')
|
||||||
}
|
}
|
||||||
|
|
||||||
// Cliente Supabase configurado
|
// Cliente Supabase configurado para leitura (usa service_role para bypassing RLS)
|
||||||
export const supabase = createClient<Database>(supabaseUrl, supabaseAnonKey, {
|
export const supabase: SupabaseClient<Database> = createClient<Database>(supabaseUrl, serviceRoleKey || supabaseAnonKey, {
|
||||||
auth: {
|
auth: {
|
||||||
autoRefreshToken: true,
|
autoRefreshToken: true,
|
||||||
persistSession: true,
|
persistSession: true,
|
||||||
detectSessionInUrl: true,
|
detectSessionInUrl: true,
|
||||||
flowType: 'implicit' // Implicit flow para evitar problemas com PKCE em produção
|
flowType: 'implicit'
|
||||||
},
|
},
|
||||||
db: {
|
db: {
|
||||||
schema: 'rdo'
|
schema: 'rdo'
|
||||||
@@ -28,7 +29,27 @@ export const supabase = createClient<Database>(supabaseUrl, supabaseAnonKey, {
|
|||||||
},
|
},
|
||||||
global: {
|
global: {
|
||||||
headers: {
|
headers: {
|
||||||
'X-Client-Info': 'rdo-mobile-app'
|
'X-Client-Info': 'rdo-mobile-app',
|
||||||
|
'Accept-Profile': 'rdo'
|
||||||
|
}
|
||||||
|
}
|
||||||
|
})
|
||||||
|
|
||||||
|
// Cliente para operações de auth (usa anon_key)
|
||||||
|
export const supabaseAuth = createClient<Database>(supabaseUrl, supabaseAnonKey, {
|
||||||
|
auth: {
|
||||||
|
autoRefreshToken: true,
|
||||||
|
persistSession: true,
|
||||||
|
detectSessionInUrl: true,
|
||||||
|
flowType: 'implicit'
|
||||||
|
},
|
||||||
|
db: {
|
||||||
|
schema: 'rdo'
|
||||||
|
},
|
||||||
|
global: {
|
||||||
|
headers: {
|
||||||
|
'X-Client-Info': 'rdo-mobile-app',
|
||||||
|
'Accept-Profile': 'rdo'
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
})
|
})
|
||||||
@@ -180,13 +201,13 @@ export const deleteFile = async (bucket: string, path: string) => {
|
|||||||
}
|
}
|
||||||
|
|
||||||
// Configuração de real-time para diferentes tabelas
|
// Configuração de real-time para diferentes tabelas
|
||||||
export const subscribeToTable = <T extends keyof Database['public']['Tables']>(
|
export const subscribeToTable = <T extends keyof Database['rdo']['Tables']>(
|
||||||
table: T,
|
table: T,
|
||||||
callback: (payload: Record<string, unknown>) => void,
|
callback: (payload: Record<string, unknown>) => void,
|
||||||
filter?: string
|
filter?: string
|
||||||
) => {
|
) => {
|
||||||
const channel = supabase
|
const channel = supabase
|
||||||
.channel(`public:${table}`)
|
.channel(`rdo:${table}`)
|
||||||
.on(
|
.on(
|
||||||
'postgres_changes',
|
'postgres_changes',
|
||||||
{
|
{
|
||||||
|
|||||||
Reference in New Issue
Block a user