Vendaweb-portal/App.tsx

215 lines
7.4 KiB
TypeScript
Raw Permalink Normal View History

2026-01-08 12:09:16 +00:00
import React, { useState, useEffect } from 'react';
import { View, Product, OrderItem } from './types';
import LoginView from './views/LoginView';
import HomeMenuView from './views/HomeMenuView';
import SalesDashboardView from './views/SalesDashboardView';
import ProductSearchView from './views/ProductSearchView';
import CheckoutView from './views/CheckoutView';
import Header from './components/Header';
import CartDrawer from './components/CartDrawer';
import ConfirmDialog from './components/ConfirmDialog';
import { useAuth } from './src/contexts/AuthContext';
import { useCart } from './src/hooks/useCart';
import { shoppingService } from './src/services/shopping.service';
const App: React.FC = () => {
const { isAuthenticated, isLoading, logout: authLogout, user } = useAuth();
const {
cart,
isLoading: isCartLoading,
addToCart,
updateQuantity,
removeFromCart,
refreshCart,
clearCart,
} = useCart();
const [currentView, setCurrentView] = useState<View>(View.LOGIN);
const [isCartOpen, setIsCartOpen] = useState(false);
const [showLogoutConfirm, setShowLogoutConfirm] = useState(false);
// Redirecionar baseado no estado de autenticação
useEffect(() => {
console.log('Auth state changed:', { isAuthenticated, isLoading, user: !!user });
if (!isLoading) {
if (isAuthenticated && user) {
console.log('Redirecionando para HOME_MENU');
setCurrentView(View.HOME_MENU);
} else if (!isAuthenticated) {
console.log('Redirecionando para LOGIN');
setCurrentView(View.LOGIN);
}
}
}, [isAuthenticated, isLoading, user]);
// Recarregar carrinho quando navegar para a página de produtos (como no Angular)
useEffect(() => {
if (currentView === View.PRODUCT_SEARCH && isAuthenticated && user) {
console.log('🛒 [APP] Navegando para ProductSearchView, recarregando carrinho...');
const cartId = shoppingService.getCart();
if (cartId) {
console.log('🛒 [APP] CartId encontrado, chamando refreshCart:', cartId);
refreshCart();
} else {
console.log('🛒 [APP] Nenhum cartId encontrado no localStorage');
}
}
}, [currentView, isAuthenticated, user, refreshCart]);
const handleLogin = () => {
// Login é gerenciado pelo LoginView através do contexto
if (isAuthenticated) {
setCurrentView(View.HOME_MENU);
}
};
const handleLogout = () => {
// Mostrar confirmação antes de fazer logout
setShowLogoutConfirm(true);
};
const executeLogout = () => {
console.log("🚪 [APP] Iniciando processo de logout...");
// 1. Limpar carrinho usando o hook
clearCart();
console.log("🚪 [APP] Estado do carrinho limpo");
// 2. Limpar dados de autenticação (token, user) do localStorage e contexto
authLogout();
console.log("🚪 [APP] Dados de autenticação removidos");
// 3. Redirecionar para login
setCurrentView(View.LOGIN);
console.log("🚪 [APP] Redirecionado para tela de login");
setShowLogoutConfirm(false);
};
// Handler para novo pedido - limpa todos os dados do pedido atual
const handleNewOrder = () => {
console.log("🆕 [APP] Iniciando novo pedido...");
// 1. Limpar carrinho usando o hook
clearCart();
console.log("🆕 [APP] Estado do carrinho limpo");
// 2. Limpar todos os dados do localStorage relacionados ao pedido
shoppingService.clearShoppingData();
console.log("🆕 [APP] Dados do pedido limpos do localStorage");
// 3. Fechar o carrinho se estiver aberto
setIsCartOpen(false);
// 4. Redirecionar para a página de produtos se não estiver lá
if (currentView !== View.PRODUCT_SEARCH) {
setCurrentView(View.PRODUCT_SEARCH);
}
console.log("🆕 [APP] Novo pedido iniciado com sucesso");
};
// Handler para adicionar item ao carrinho
const handleAddToCart = async (product: Product | OrderItem) => {
try {
await addToCart(product);
// Abrir o carrinho automaticamente ao adicionar
setIsCartOpen(true);
} catch (error: any) {
console.error('🛒 [APP] Erro ao adicionar item ao carrinho:', error);
// O hook já trata o erro, apenas logamos aqui
}
};
const renderView = () => {
const isDashboardOrSearch = currentView === View.SALES_DASHBOARD || currentView === View.PRODUCT_SEARCH || currentView === View.CHECKOUT;
return (
<div className="flex flex-col h-screen lg:h-screen overflow-hidden fixed inset-0 lg:relative lg:inset-auto">
{isDashboardOrSearch && user && (
<Header
user={{
name: user.username || user.name || 'Usuário',
store: user.store || 'Loja'
}}
currentView={currentView}
onNavigate={setCurrentView}
cartCount={cart.reduce((acc, i) => acc + i.quantity, 0)}
onCartClick={() => setIsCartOpen(true)}
onLogout={handleLogout}
/>
)}
<div className="flex-1 overflow-auto bg-slate-50 lg:overflow-auto">
{(() => {
switch (currentView) {
case View.LOGIN:
return <LoginView onLogin={handleLogin} />;
case View.HOME_MENU:
return user ? (
<HomeMenuView
onNavigate={setCurrentView}
user={{
name: user.username || user.name || 'Usuário',
store: user.store || 'Loja'
}}
onLogout={handleLogout}
/>
) : null;
case View.SALES_DASHBOARD:
return <SalesDashboardView onNavigate={setCurrentView} onNewOrder={handleNewOrder} />;
case View.PRODUCT_SEARCH:
return <ProductSearchView onAddToCart={handleAddToCart} />;
case View.CHECKOUT:
return (
<CheckoutView
cart={cart}
onBack={() => setCurrentView(View.PRODUCT_SEARCH)}
onCartUpdate={refreshCart}
onClearCart={clearCart}
/>
);
default:
return <LoginView onLogin={handleLogin} />;
}
})()}
</div>
{/* Carrinho Global */}
<CartDrawer
isOpen={isCartOpen}
onClose={() => setIsCartOpen(false)}
items={cart}
onUpdateQuantity={updateQuantity}
onRemove={removeFromCart}
onCheckout={() => {
setIsCartOpen(false);
setCurrentView(View.CHECKOUT);
}}
onNewOrder={handleNewOrder}
/>
</div>
);
};
return (
<div className="min-h-screen lg:min-h-screen">
{/* Meta tag para mobile app-like experience */}
<meta name="viewport" content="width=device-width, initial-scale=1.0, maximum-scale=1.0, user-scalable=no, viewport-fit=cover" />
{renderView()}
{/* Confirmação de Logout */}
<ConfirmDialog
isOpen={showLogoutConfirm}
type="warning"
title="Confirmar Saída"
message="Deseja realmente sair do sistema? Todos os dados não salvos serão perdidos."
onConfirm={executeLogout}
onClose={() => setShowLogoutConfirm(false)}
confirmText="Sair"
cancelText="Cancelar"
/>
</div>
);
};
export default App;