Saltar al contenido
SaaSEn producción2025

Petzara

SaaS full-stack de gestión para petshops — citas, finanzas, equipo y suscripción con Stripe

React 19Vite 6Tailwind CSS v4Node.js 22Express 5
Funciona enWebPWA (celular y computadora)Desktop (Electron)
petzara.app
pasos para reservar: mascota, servicio y fecha
3
paletas de color cambiadas en vivo
4
roles — administrador y colaborador — en el mismo petshop
2
instalable en el celular y en la computadora
PWA

01

Visión General

Petzara es un SaaS construido desde cero con dos repositorios separados: un front-end en React 19/Vite y un back-end en Node.js/Express/MongoDB. El sistema es multi-tenant: cada petshop tiene sus datos aislados y puede agregar colaboradores que comparten el contexto en tiempo real mediante Socket.io. Cuenta con autenticación JWT con renovación automática a través de una cookie httpOnly, un sistema de suscripción completo con Stripe (planes mensual y anual, período de prueba, webhooks y bloqueo de acceso al vencer), cron jobs para actualizar automáticamente el estado de las citas y envío de correos transaccionales con Resend.

Mi rol

Desarrollador full-stack en solitario — arquitectura, back-end Node.js/Express/MongoDB, front-end React 19/Vite, Socket.io, integración completa con Stripe, despliegue en Railway y mantenimiento en producción.


Categoría

SaaS

Año

2025

Estado

En producción

Plataformas

WebPWA (celular y computadora)Desktop (Electron)

Dos repositorios, un producto: el front-end React habla solo con la API, y la API es quien conoce el tenant, la suscripción y el estado. Stripe, Resend y Socket.io giran en torno al servidor: el navegador nunca ve un secreto.

App React 19

Vite · PWA · Railway

Tailwind v4React Router 7Socket.io clientRecharts

API Express 5

Node 22 · Railway

JWT + refresh httpOnlySocket.ionode-cronStripe webhook

Datos y servicios

MongoDB + integraciones

MongooseStripeResendSentry

Sincronización: Cada recurso lleva el ObjectId del dueño; los colaboradores heredan el owner y entran a la misma sala de Socket.io: la misma agenda cambia para todos al mismo tiempo.


02

El Problema

Los petshops crecen por el boca a boca, pero se traban en la operación: la agenda en un cuaderno, el historial de clientes perdido en WhatsApp, el equipo sin visibilidad del día y las finanzas en hojas de cálculo. Con el crecimiento, este proceso manual se convierte en un cuello de botella que limita la capacidad operativa.

03 — La Solución

SaaS multi-tenant con front-end React PWA y back-end Node.js/MongoDB: agenda de citas con actualización automática de estado, registro de clientes, mascotas y servicios, finanzas integradas, gestión de colaboradores con permisos y suscripción con Stripe con período de prueba — accesible como app instalable en el celular.


04

Por dentro del producto

El sistema en funcionamiento, grabado de la aplicación real con una tienda de demostración — ninguna pantalla es un mockup.

01

Agenda

Una cita en tres pasos — y el equipo la ve al instante

El cliente y la mascota vienen del registro, el servicio base suma los extras al precio, la fecha sale de un calendario y la hora de un reloj. Al guardar, la fila entra resaltada en la lista, el estado cambia desde el menú de la propia tabla y un cron pasa la atención a “En curso” cuando llega la hora.

  • Precio calculado al instante: servicio base + extras seleccionados
  • Estado Pendiente → En curso → Finalizado con transición automática por cron
  • Lista, mes, semana y día sobre los mismos datos, con filtros y búsqueda
Agenda
02

Enlace público

El cliente elige el horario y confirma por WhatsApp

Cada petshop obtiene su propia URL (petzara.app/agendar/nombre). La página pública lee la grilla de horarios, los descansos y la cantidad de atenciones simultáneas configuradas en el panel, muestra solo los cupos libres de la mañana y de la tarde y abre el WhatsApp de la tienda con el mensaje listo — sin registro, sin contraseña.

  • La grilla, los descansos y la capacidad vienen de la Configuración del petshop
  • Los cupos ocupados desaparecen solos a medida que se llena la agenda
  • El enlace se puede desactivar con un interruptor, sin borrar nada
Enlace público
03

Personalización

Cuatro paletas, un cambio en vivo

Terracotta & Sage, Deep Forest, Muted Ocean y Earthy Ochre. La elección queda en el usuario y se convierte en dos CSS custom properties en la raíz: la barra lateral, los botones, los gráficos y hasta el logo cambian sin recargar la página.

  • Tokens de Tailwind v4 apuntando a --brand-primary y --brand-secondary
  • Logo en SVG con una versión por paleta
  • Preferencia guardada en la cuenta: vale en cualquier dispositivo
Personalización
04

Finanzas

De la atención finalizada a la cuenta por cobrar

Cada cita finalizada genera un ingreso; la pestaña Cuentas por Cobrar lista lo que sigue pendiente y confirma el pago con el método elegido. Los gastos se registran por categoría, el flujo de caja y el gráfico circular de gastos se calculan en el servidor, y la base de citas se exporta a CSV o Excel por período.

  • Saldo, ingresos y gastos del período con gráficos de Recharts
  • Confirmación de pago con Pix, tarjeta o efectivo
  • Exportación XLSX/CSV generada en el navegador a partir de la API
Finanzas
05

Equipo

Invitación por correo y permisos por área

El administrador invita por correo, define el departamento y marca lo que el colaborador puede ver. La invitación sale por Resend con un enlace de aceptación; quien entra recibe el mismo owner, cae en la misma sala de Socket.io y ve la agenda del día — sin ver las finanzas si no se le da acceso.

  • Invitación con vencimiento y aceptación con contraseña propia
  • Permisos por módulo, modificables después
  • Notificaciones internas por categoría: agenda, cobros y equipo
Equipo
06

Primer acceso

Asistente, tour guiado y checklist hasta la primera cita

Quien acaba de crear la cuenta configura el nombre, los días y horarios de atención y el enlace público en tres pantallas. Después, un tour resalta, elemento por elemento, el camino hasta la primera cita — y un checklist en el inicio muestra el progreso mientras corre el período de prueba.

  • Período de prueba con aviso por correo antes de vencer y bloqueo suave al terminar
  • Tour basado en data-tour: abre y cierra la barra lateral solo en el celular
  • Checklist de cuatro pasos con progreso en el inicio
Primer acceso
07

Celular

Hecho para el mostrador: menú de cajón y formularios en hoja

En el celular, la barra lateral se convierte en un cajón, las tarjetas de la agenda reemplazan la tabla y la nueva cita sube como una hoja. La PWA se instala en la pantalla de inicio y el enlace público fue diseñado primero para el teléfono del cliente.

  • Un solo layout, dos contextos: administrador completo y colaborador enfocado en el día
  • El chunk error boundary recarga solo después de un despliegue
  • Instalable como app, con actualización automática
Celular

05

8 flujos en video

Cada video muestra una tarea completa, de principio a fin. Haz clic para verlo con controles.


06

Funcionalidades Principales

01

Agenda en tiempo real

Citas con transición automática de estado (confirmada → en curso → completada) mediante cron job, con actualizaciones instantáneas para todo el equipo a través de Socket.io.

02

Gestión de clientes y mascotas

Registro completo de tutores y mascotas con historial de servicios, observaciones y preferencias de atención.

03

Control financiero

Panel de ingresos, transacciones y métricas del negocio, con exportación de datos por período.

04

Gestión de colaboradores

Registro del equipo con permisos escalonados: los colaboradores acceden solo a lo necesario para la atención diaria.

05

Suscripción con Stripe

Planes mensual y anual con checkout de Stripe, período de prueba gratuito, webhook de pago y bloqueo automático de acceso al vencer la suscripción.

06

PWA + enlace público de reservas

Instalable como app en el celular mediante PWA. Un enlace público permite que los clientes reserven un horario sin crear una cuenta en el sistema.


07

Pantallas del sistema

Capturas reales del producto, organizadas por módulo. Haz clic en cualquier pantalla para ampliarla.

Visión general: citas del mes, ingresos por servicio y la agenda del día
Estados de las citas y minicalendario del mes
Centro de notificaciones por categoría
Lista con mascota, tutor, servicios, precio y acciones por fila
Vista del mes
Semana con atenciones por hora
Día a día, hora a hora
Paso 1: cliente y mascota
Paso 2: servicio base y extras
Paso 3: calendario y reloj
Detalle con tutor, responsable, observaciones y finalizar
Filtros de orden, período y estado

08

En el celular

El dueño del petshop revisa la agenda del mostrador y el tutor reserva por teléfono: las dos pantallas fueron diseñadas primero para el celular e instaladas como PWA.

Inicio
Menú
Agenda
Calendario
Nueva cita
Finanzas
Clientes
Notificaciones
Enlace público
Confirmar
Inicio de sesión

09

Tecnologías

Front-end

React 19Vite 6Tailwind CSS v4

Back-end

Node.js 22Express 5

Base de datos

MongoDBMongoose

Despliegue

Railway

Integraciones

StripeSocket.ioResendGoogle OAuthSentry

Bibliotecas

React Hook FormRechartsReact Router 7node-cronvite-plugin-pwa

10

Decisiones de Diseño

Cuatro temas de color intercambiables en tiempo de ejecución mediante CSS custom properties (terracotta, forest, ocean, ochre). La interfaz se divide en dos contextos: administrador con gestión completa y colaborador con una vista enfocada en la atención del día. Un tour guiado integrado mediante GuidedTourContext hace el onboarding de los usuarios nuevos.

11

Desafíos Técnicos

El webhook de Stripe exige el body crudo (Buffer) para validar la firma con el secret, pero express.json() consume el body antes. Solución: montar la ruta del webhook antes de cualquier middleware de body parsing. El segundo desafío: el refresh token inline en authMiddleware, que regenera el access token sin rechazar la solicitud — el nuevo token se devuelve en el header X-Access-Token y el interceptor de axios del front-end lo captura de forma transparente.


12

Resultados

  • SaaS en producción con citas y suscripciones de Stripe activas
  • Multi-tenancy funcionando: el administrador y los colaboradores comparten datos en tiempo real mediante Socket.io
  • PWA instalable en el celular con enlace público de reservas para clientes sin cuenta

13

Aprendizajes

  • JWT de doble capa: access token de 15 min + refresh token de 30 días en una cookie httpOnly, renovado automáticamente mediante un interceptor de axios sin redirigir al usuario
  • Multi-tenancy en MongoDB: aislar los recursos por ObjectId del owner, con colaboradores que heredan el contexto del administrador mediante el campo owner
  • Integración completa con Stripe: la ruta del webhook debe montarse antes de express.json() para recibir el body crudo y validar la firma — un detalle que rompe la integración si se ignora
  • Socket.io con salas por owner: todos los eventos (citas, clientes, mascotas, finanzas) disparan actualizaciones en tiempo real para el administrador y los colaboradores al mismo tiempo
  • Cron jobs en producción: actualización automática del estado de las citas, alertas de períodos de prueba que vencen en 3 días y expiración automática de pruebas vencidas