Saltar al contenido principal

Guía de Desarrollo

Guía completa para desarrollar en Floutic, incluyendo configuración, flujo de trabajo, ejemplos y mejores prácticas.

Inicio Rápido

Requisitos Previos

  • Docker Desktop (incluye Docker y Docker Compose)
  • Git para clonar el repositorio
  • Editor de código (VS Code recomendado)
  • Node.js 20.19.5+ (solo si ejecutas tests del frontend fuera de Docker)
  • Python 3.11+ (solo si ejecutas backend fuera de Docker)

Configuración Inicial

  1. Clonar el repositorio:

    git clone <repository-url>
    cd floutic
  2. Configurar variables de entorno:

    # Copiar archivos de ejemplo
    cp backend/.env.example backend/.env
    cp frontend/.env.example frontend/.env

    # Editar con tus valores
    nano backend/.env
    nano frontend/.env
  3. Iniciar el entorno:

    ./start-dev.sh

Flujo de Trabajo Recomendado

1. Iniciar el Entorno

# Iniciar todos los servicios
./start-dev.sh

# O con rebuild
./start-dev.sh --rebuild

Servicios iniciados:

  • Backend (FastAPI) en http://localhost:18080 (expuesto desde Docker)
  • Frontend (Astro) en http://localhost:3000
  • PostgreSQL en puerto 5432
  • Redis en puerto 6379
  • OpenObserve en http://localhost:5080
  • Docusaurus en http://localhost:3001

2. Verificar que Todo Funciona

# Ver estado de servicios
./status-dev.sh

# O manualmente
docker compose ps

# Verificar salud del backend
curl http://localhost:18080/health

# Verificar frontend
curl http://localhost:3000

3. Desarrollar

Backend:

  • Edita archivos en backend/
  • Los cambios se reflejan automáticamente (hot reload)
  • Ver logs: docker compose logs -f backend

Frontend:

  • Edita archivos en frontend/
  • Los cambios se reflejan automáticamente (HMR)
  • Ver logs: docker compose logs -f frontend

Documentación:

  • Edita archivos en docs-site/docs/
  • Reconstruye: docker compose exec docs npm run build

4. Ejecutar Tests

# Tests del backend
./scripts/test_backend.sh

# Tests unitarios del frontend
./scripts/test_frontend_unit.sh

# Tests E2E del frontend
./scripts/test_e2e.sh

# Tests de seguridad
./scripts/test_frontend_security.sh

Notas:

  • Cobertura E2E y auditoría: frontend/tests/e2e/E2E_COVERAGE.md, AUDIT.md, SCENARIOS.md
  • Si necesitas ejecutar Playwright directo: ./scripts/test_e2e.sh
  • Variables E2E: .env.e2e es plantilla; el script ./scripts/test_e2e.sh aplica overrides sobre .env

5. Detener el Entorno

./stop-dev.sh

# O manualmente
docker compose down

Estructura del Proyecto

floutic/
├── backend/ # API FastAPI
│ ├── app/
│ │ ├── api/v1/endpoints/ # Endpoints de la API
│ │ ├── models/ # Modelos de base de datos
│ │ ├── schemas/ # Esquemas Pydantic
│ │ ├── services/ # Servicios de negocio
│ │ └── core/ # Configuración
│ ├── alembic/ # Migraciones
│ ├── tests/ # Tests
│ └── scripts/ # Scripts de utilidades
├── frontend/ # Frontend Astro + React
│ ├── src/
│ │ ├── components/ # Componentes React
│ │ ├── pages/ # Páginas Astro
│ │ ├── layouts/ # Layouts
│ │ ├── stores/ # Stores Zustand
│ │ └── lib/ # Utilidades
│ └── tests/ # Tests
├── docs-site/ # Documentación Docusaurus
│ ├── docs/ # Archivos Markdown/MDX
│ └── src/ # Componentes React personalizados
├── docs/ # Documentación en Markdown
├── scripts/ # Scripts de utilidades
└── docker-compose.yml # Configuración Docker Compose

Desarrollo del Backend

Estructura Detallada

backend/
├── app/
│ ├── api/
│ │ └── v1/
│ │ ├── endpoints/ # Módulos de endpoints
│ │ │ ├── auth/ # Autenticación (modular)
│ │ │ │ ├── __init__.py
│ │ │ │ ├── registration.py
│ │ │ │ ├── login.py
│ │ │ │ ├── session.py
│ │ │ │ ├── email_verification.py
│ │ │ │ ├── password.py
│ │ │ │ └── roles.py
│ │ │ ├── projects/ # Proyectos (modular)
│ │ │ │ ├── __init__.py
│ │ │ │ ├── listing.py
│ │ │ │ ├── crud.py
│ │ │ │ ├── applications.py
│ │ │ │ ├── selection.py
│ │ │ │ ├── workflow.py
│ │ │ │ └── disputes.py
│ │ │ ├── payments.py
│ │ │ └── ...
│ │ └── api.py # Router principal
│ ├── models/ # Modelos SQLAlchemy
│ │ ├── user.py
│ │ ├── project.py
│ │ └── ...
│ ├── schemas/ # Esquemas Pydantic
│ │ ├── user.py
│ │ ├── project.py
│ │ └── ...
│ ├── services/ # Servicios de negocio
│ │ ├── stripe_service.py
│ │ ├── email_service.py
│ │ └── ...
│ ├── core/ # Configuración
│ │ ├── security.py
│ │ ├── config.py
│ │ └── ...
│ └── database.py # Configuración BD
├── alembic/ # Migraciones
│ ├── versions/ # Versiones de migración
│ └── env.py # Configuración Alembic
└── tests/ # Tests
├── endpoints/ # Tests de endpoints
├── unit/ # Tests unitarios
└── conftest.py # Fixtures compartidas

Crear un Nuevo Endpoint

  1. Crear el endpoint en app/api/v1/endpoints/:

    from fastapi import APIRouter, Depends
    from app.database import get_db
    from app.api.deps import get_current_active_user

    router = APIRouter()

    @router.get("/example")
    async def get_example(
    current_user: User = Depends(get_current_active_user),
    db: AsyncSession = Depends(get_db)
    ):
    return {"message": "Example"}
  2. Añadir el router en app/api/v1/api.py:

    from app.api.v1.endpoints import example

    api_router.include_router(
    example.router,
    prefix="/example",
    tags=["example"]
    )
  3. Crear schemas en app/schemas/:

    from pydantic import BaseModel

    class ExampleResponse(BaseModel):
    message: str
  4. Escribir tests en tests/endpoints/test_example.py:

    async def test_get_example(client, auth_headers):
    response = await client.get(
    "/api/example",
    headers=auth_headers
    )
    assert response.status_code == 200

Comandos Útiles

# Ejecutar migraciones
docker compose exec backend alembic upgrade head

# Crear nueva migración
docker compose exec backend alembic revision --autogenerate -m "descripción"

# Ver estado de migraciones
docker compose exec backend alembic current

# Ver historial de migraciones
docker compose exec backend alembic history

# Ver logs en tiempo real
docker compose logs -f backend

# Acceder al shell del backend
docker compose exec backend bash

# Ejecutar Python interactivo
docker compose exec backend python

# Ejecutar tests específicos
./scripts/test_backend.sh tests/endpoints/projects/ -v

# Ejecutar tests con cobertura
./scripts/test_backend.sh --cov=app --cov-report=html

Ejemplo: Añadir un Nuevo Modelo

  1. Crear el modelo en app/models/example.py:

    from sqlalchemy import Column, Integer, String
    from app.database import Base

    class Example(Base):
    __tablename__ = "examples"

    id = Column(Integer, primary_key=True)
    name = Column(String, nullable=False)
  2. Crear la migración:

    docker compose exec backend alembic revision --autogenerate -m "add example table"
  3. Aplicar la migración:

    docker compose exec backend alembic upgrade head

Desarrollo del Frontend

Estructura Detallada

frontend/
├── src/
│ ├── components/
│ │ ├── ui/ # Componentes shadcn/ui
│ │ ├── shared/ # Componentes compartidos
│ │ └── features/ # Componentes por funcionalidad
│ ├── pages/ # Rutas Astro (file-based routing)
│ │ ├── index.astro # Landing page
│ │ ├── login.astro # Login
│ │ └── dashboard/ # Dashboards
│ ├── layouts/ # Layouts de páginas
│ │ └── Layout.astro # Layout principal
│ ├── lib/
│ │ ├── api/ # Cliente API y endpoints
│ │ ├── stores/ # Zustand stores
│ │ ├── utils/ # Utilidades
│ │ ├── types/ # TypeScript types
│ │ └── hooks/ # Hooks personalizados
│ └── styles/
│ └── global.css # Estilos globales
└── tests/ # Tests E2E con Playwright

Crear un Nuevo Componente

  1. Crear el componente en src/components/features/:

    import React from 'react';
    import { Card, CardContent, CardHeader, CardTitle } from '../ui/card';

    interface ExampleComponentProps {
    title: string;
    }

    export default function ExampleComponent({ title }: ExampleComponentProps) {
    return (
    <Card>
    <CardHeader>
    <CardTitle>{title}</CardTitle>
    </CardHeader>
    <CardContent>
    Contenido del componente
    </CardContent>
    </Card>
    );
    }
  2. Usar el componente:

    import ExampleComponent from '@/components/features/ExampleComponent';

    <ExampleComponent title="Ejemplo" />

Crear una Nueva Página

  1. Crear el archivo en src/pages/:

    ---
    import Layout from '../layouts/Layout.astro';
    ---

    <Layout title="Nueva Página">
    <h1>Nueva Página</h1>
    </Layout>
  2. La ruta se genera automáticamente:

    • src/pages/example.astro/example
    • src/pages/example/[id].astro/example/:id

Comandos Útiles

# Ver logs en tiempo real
docker compose logs -f frontend

# Acceder al shell del frontend
docker compose exec frontend sh

# Ejecutar tests unitarios
./scripts/test_frontend_unit.sh

# Ejecutar tests E2E
./scripts/test_e2e.sh

# Ejecutar tests con cobertura
docker compose exec frontend npm run test:coverage

# Build de producción
docker compose exec frontend npm run build

# Preview del build
docker compose exec frontend npm run preview

Desarrollo de Documentación

Estructura

docs-site/
├── docs/ # Archivos Markdown/MDX
│ ├── intro.md
│ ├── backend/
│ ├── frontend/
│ └── ...
├── src/ # Componentes React personalizados
│ └── components/
└── static/ # Archivos estáticos

Añadir Nueva Documentación

  1. Crear archivo en docs-site/docs/:

    ---
    sidebar_position: 1
    ---

    # Título de la Documentación

    Contenido de la documentación...
  2. Añadir al sidebar en sidebars.ts:

    {
    type: 'category',
    label: 'Categoría',
    items: ['ruta/al/archivo'],
    }
  3. Reconstruir:

    docker compose exec docs npm run build

Comandos Útiles

# Reconstruir documentación
docker compose exec docs npm run build

# Ver documentación localmente
docker compose exec docs npm run start

# Limpiar build
docker compose exec docs npm run clear

Debugging

Backend

Ver logs en tiempo real:

docker compose logs -f backend

Acceder a la base de datos:

docker compose exec postgres psql -U ${POSTGRES_USER} -d ${POSTGRES_DB}

Verificar Redis:

docker compose exec redis redis-cli
docker compose exec redis redis-cli keys "*"

Debug con Python:

# Acceder al shell
docker compose exec backend bash

# Ejecutar Python interactivo
python

# Importar modelos y servicios
from app.models.user import User
from app.database import SessionLocal

Frontend

Ver logs en tiempo real:

docker compose logs -f frontend

Inspeccionar en el navegador:

  • Abre DevTools en http://localhost:3000
  • Network tab para ver requests
  • Console para ver logs
  • React DevTools para inspeccionar componentes

Debug con React DevTools:

  • Instalar extensión del navegador
  • Inspeccionar estado de componentes
  • Ver props y hooks

Ejemplos de Desarrollo

Ejemplo 1: Añadir Nuevo Endpoint de API

Backend (backend/app/api/v1/endpoints/example.py):

from fastapi import APIRouter, Depends, HTTPException
from sqlalchemy.ext.asyncio import AsyncSession
from app.database import get_db
from app.api.deps import get_current_active_user
from app.models.user import User
from pydantic import BaseModel

router = APIRouter()

class ExampleResponse(BaseModel):
message: str
user_id: int

@router.get("/example", response_model=ExampleResponse)
async def get_example(
current_user: User = Depends(get_current_active_user),
db: AsyncSession = Depends(get_db)
):
return ExampleResponse(
message="Hello from example endpoint",
user_id=current_user.id
)

Frontend (frontend/src/lib/api/example.ts):

import { apiClient } from './client';

export interface ExampleResponse {
message: string;
user_id: number;
}

export const ExampleService = {
async getExample(): Promise<ExampleResponse> {
const response = await apiClient.get<ExampleResponse>('/example');
return response.data;
}
};

Uso en componente:

import { ExampleService } from '@/lib/api/example';
import { useEffect, useState } from 'react';

export default function ExampleComponent() {
const [data, setData] = useState(null);

useEffect(() => {
ExampleService.getExample().then(setData);
}, []);

return <div>{data?.message}</div>;
}

Ejemplo 2: Crear Nuevo Componente con Estado

import React, { useState } from 'react';
import { Button } from '@/components/ui/button';
import { Input } from '@/components/ui/input';

export default function Counter() {
const [count, setCount] = useState(0);

return (
<div>
<p>Count: {count}</p>
<Button onClick={() => setCount(count + 1)}>Increment</Button>
<Button onClick={() => setCount(count - 1)}>Decrement</Button>
</div>
);
}

Ejemplo 3: Usar Hook Personalizado

import { useSecureAuth } from '@/lib/hooks/useSecureAuth';

export default function UserProfile() {
const { user, isAuthenticated, isLoading } = useSecureAuth();

if (isLoading) return <div>Loading...</div>;
if (!isAuthenticated) return <div>Please login</div>;

return <div>Welcome, {user?.username}!</div>;
}

Mejores Prácticas

Backend

  1. Siempre usar async/await para operaciones I/O
  2. Validar datos con Pydantic antes de procesar
  3. Usar dependencias de FastAPI para autenticación y BD
  4. Escribir tests para cada nuevo endpoint
  5. Documentar endpoints con docstrings
  6. Manejar errores con HTTPException apropiados
  7. Usar transacciones para operaciones críticas

Frontend

  1. Usar TypeScript para tipado estático
  2. Validar formularios con Zod
  3. Sanitizar inputs con DOMPurify
  4. Manejar estados de carga y errores
  5. Usar hooks personalizados para lógica reutilizable
  6. Optimizar renders con useMemo y useCallback
  7. Escribir tests para componentes críticos

Git

  1. Crear ramas descriptivas: feature/nueva-funcionalidad
  2. Commits atómicos: Un commit por cambio lógico
  3. Mensajes descriptivos: "Add user profile endpoint"
  4. Revisar antes de commit: git diff
  5. Ejecutar tests antes de push

Troubleshooting

Problemas Comunes

Backend no inicia:

  • Verificar variables de entorno
  • Verificar que PostgreSQL esté corriendo
  • Revisar logs: docker compose logs backend

Frontend no carga:

  • Verificar que el backend esté saludable
  • Verificar variables de entorno
  • Limpiar caché: docker compose exec frontend npm run clear

Tests fallan:

  • Verificar que Redis esté corriendo
  • Desactivar rate limiting en tests
  • Verificar fixtures y mocks

Migraciones fallan:

  • Verificar estado actual: alembic current
  • Revisar conflictos: alembic history
  • Aplicar migraciones: docker compose exec backend alembic upgrade head

Próximos Pasos