Fase 3:
- Backend API: Autenticación y autorización básicas con JWT implementadas. Cambio de contraseña funcional. Módulo "Tipos de Pago" (CRUD completo) implementado en el backend (Controlador, Servicio, Repositorio) usando Dapper, transacciones y con lógica de historial. Se incluyen permisos en el token JWT. - Frontend React: Estructura base con Vite, TypeScript, MUI. Contexto de autenticación (AuthContext) que maneja el estado del usuario y el token. Página de Login. Modal de Cambio de Contraseña (forzado y opcional). Hook usePermissions para verificar permisos. Página GestionarTiposPagoPage con tabla, paginación, filtro, modal para crear/editar, y menú de acciones, respetando permisos. Layout principal (MainLayout) con navegación por Tabs (funcionalidad básica de navegación). Estructura de enrutamiento (AppRoutes) que maneja rutas públicas, protegidas y anidadas para módulos.
This commit is contained in:
21
Frontend/src/services/authService.ts
Normal file
21
Frontend/src/services/authService.ts
Normal file
@@ -0,0 +1,21 @@
|
||||
import apiClient from './apiClient';
|
||||
import type { LoginRequestDto } from '../models/dtos/LoginRequestDto';
|
||||
import type { LoginResponseDto } from '../models/dtos/LoginResponseDto';
|
||||
import type { ChangePasswordRequestDto } from '../models/dtos/ChangePasswordRequestDto'; // Importar DTO
|
||||
|
||||
const login = async (credentials: LoginRequestDto): Promise<LoginResponseDto> => {
|
||||
const response = await apiClient.post<LoginResponseDto>('/auth/login', credentials);
|
||||
return response.data;
|
||||
};
|
||||
|
||||
const changePassword = async (data: ChangePasswordRequestDto): Promise<void> => {
|
||||
// No esperamos datos de vuelta, solo éxito (204) o error
|
||||
await apiClient.post('/auth/change-password', data);
|
||||
};
|
||||
|
||||
const authService = {
|
||||
login,
|
||||
changePassword, // Exportar la nueva función
|
||||
};
|
||||
|
||||
export default authService;
|
||||
43
Frontend/src/services/tipoPagoService.ts
Normal file
43
Frontend/src/services/tipoPagoService.ts
Normal file
@@ -0,0 +1,43 @@
|
||||
import apiClient from './apiClient';
|
||||
import type { TipoPago } from '../models/Entities/TipoPago';
|
||||
import type { CreateTipoPagoDto } from '../models/dtos/tiposPago/CreateTipoPagoDto';
|
||||
import type { UpdateTipoPagoDto } from '../models/dtos/tiposPago/UpdateTipoPagoDto';
|
||||
|
||||
const getAllTiposPago = async (nombreFilter?: string): Promise<TipoPago[]> => {
|
||||
const params: Record<string, string> = {};
|
||||
if (nombreFilter) {
|
||||
params.nombre = nombreFilter;
|
||||
}
|
||||
const response = await apiClient.get<TipoPago[]>('/tipospago', { params });
|
||||
return response.data;
|
||||
};
|
||||
|
||||
const getTipoPagoById = async (id: number): Promise<TipoPago> => {
|
||||
const response = await apiClient.get<TipoPago>(`/tipospago/${id}`);
|
||||
return response.data;
|
||||
};
|
||||
|
||||
const createTipoPago = async (data: CreateTipoPagoDto): Promise<TipoPago> => {
|
||||
const response = await apiClient.post<TipoPago>('/tipospago', data);
|
||||
return response.data; // La API devuelve el objeto creado (201 Created)
|
||||
};
|
||||
|
||||
const updateTipoPago = async (id: number, data: UpdateTipoPagoDto): Promise<void> => {
|
||||
// PUT no suele devolver contenido en éxito (204 No Content)
|
||||
await apiClient.put(`/tipospago/${id}`, data);
|
||||
};
|
||||
|
||||
const deleteTipoPago = async (id: number): Promise<void> => {
|
||||
// DELETE no suele devolver contenido en éxito (204 No Content)
|
||||
await apiClient.delete(`/tipospago/${id}`);
|
||||
};
|
||||
|
||||
const tipoPagoService = {
|
||||
getAllTiposPago,
|
||||
getTipoPagoById,
|
||||
createTipoPago,
|
||||
updateTipoPago,
|
||||
deleteTipoPago,
|
||||
};
|
||||
|
||||
export default tipoPagoService;
|
||||
Reference in New Issue
Block a user