Commit Graph

254 Commits

Author SHA1 Message Date
be4bb8d9ad feat(manager): add Nexus Instance Manager for demo orchestration
- Complete Flask-based control panel for multi-tenant POS instances
- Dashboard with global stats, system health, and recent demos
- Demo provisioning in 1 click with auto-expiration tracking
- Tenant management: activate/deactivate, reset data, delete
- Health monitoring: PostgreSQL, Redis, disk, memory, systemd services
- Migration orchestration UI for running schema updates across all tenants
- JWT authentication with manager_users table
- Dark theme SPA frontend with real-time search and actions
- systemd service file included
2026-05-17 21:01:01 +00:00
da362e32a6 feat(catalog): full vehicle selector flow in brand catalog
Brand catalog now follows the same navigation as the regular catalog:
1. Brands -> 2. Models -> 3. Years -> 4. Engines -> 5. Categories -> 6. Parts

Backend:
- Add /mye-parts endpoint for MYE-specific parts with category filter
- Uses existing /models, /years, /engines, /categories endpoints

Frontend:
- Complete rewrite of brand-catalog.js with breadcrumb navigation
- State machine: brands -> models -> years -> engines -> categories -> parts
- Search and pagination preserved at parts level
- Breadcrumb allows jumping back to any previous step
2026-05-14 22:35:01 +00:00
79fa7984a1 feat(sw): auto-reload page when service worker updates
Add updatefound listener in catalog.html that reloads the page
automatically when a new service worker is activated. This ensures
users get the latest HTML and JS without manual hard refresh.
2026-05-14 22:26:42 +00:00
30abecc07d fix(sw): v6 with network-first HTML strategy
- Bump cache to nexus-pos-v6 to force invalidation
- HTML pages now use network-first instead of cache-first
  This ensures users always get the latest HTML with correct
  JS/CSS references (?v=3) instead of stale cached HTML
- Remove HTML pages from APP_SHELL precache (only static assets)
- Keep cache-first for JS/CSS/images
2026-05-14 22:26:27 +00:00
521455f156 fix(brand-catalog): separate search input from content grid
- Add #brandCatalogSearch container in HTML for search inputs
- Move brand search input out of renderBrandList so it persists while typing
- Move parts search input out of renderPartsList so it persists while typing
- Reset now clears search container
- Bump JS cache bust to v=3
2026-05-14 22:24:09 +00:00
24db5eff43 fix(sw): bump cache to v5, add brand-catalog.js to precache
Update service worker cache name to nexus-pos-v5 to force cache
invalidation. Add brand-catalog.js to APP_SHELL precache list.
This should resolve stale cached JS causing parse errors.
2026-05-14 22:11:13 +00:00
4d6a7d9f32 fix(catalog): filter vehicle-brands to North America OEM brands only
/vehicle-brands now uses get_brands_for_mode('oem') to return the same
36 North American brands (Mexico/USA/Canada) as the regular catalog flow,
instead of all 619 brands in the database.
2026-05-14 21:38:36 +00:00
c6b3ca9bdf fix(brand-catalog): add JWT auth token to all API requests
brand-catalog.js was missing Authorization header on fetch calls,
causing 401 Unauthorized errors. Now reads pos_token from localStorage
and includes Bearer token in every request. Also handles 401 responses
by redirecting to /pos/login. Bump JS cache bust to v=2.
2026-05-14 21:26:10 +00:00
9da14e40da feat(catalog): brand search, parts pagination, and parts search
Backend:
- Add 'search' param to /brand-parts endpoint (filters oem_part_number and name via ILIKE)
- Keep count query accurate with search filter

Frontend (brand-catalog.js):
- Brand search input: filters 619 brands locally while typing
- Parts pagination: Previous/Next buttons with page counter (50 per page)
- Parts search within category: search input + Enter key triggers backend search
- Visual polish: stock badges, empty-state messages, responsive layout
- Loading states and breadcrumbs improved
2026-05-14 21:23:02 +00:00
e61063bdd7 feat(domain): separate POS to pos.nexusautoparts.com.mx subdomain
- nexusautoparts.com.mx -> Dashboard/Landing (port 5000)
- pos.nexusautoparts.com.mx -> POS (port 5001) with static assets proxy
- admin.nexusautoparts.com.mx -> Dashboard (port 5000)
- Update mobile app configs to point to pos.nexusautoparts.com.mx
- Update Caddy docs with new subdomain layout
2026-05-14 09:30:43 +00:00
6734993508 fix(nginx): fix static assets 404 on new domain
Remove broken location blocks for static files that had no proxy_pass,
which caused all .js/.css files to return 404 or HTML.
Add explicit /pos/static/ location with proxy_pass + cache headers.
Update nexus-pos.conf in repo to match live config.
2026-05-14 09:19:00 +00:00
2b0215d6b8 chore(domain): migrate to nexusautoparts.com.mx
- Update Nginx config:
  - nexusautoparts.com.mx -> POS (port 5001)
  - admin.nexusautoparts.com.mx -> Dashboard (port 5000)
  - nexus.consultoria-as.com -> legacy redirect (dashboard)
  - Add redirect / -> /pos/login for main domain
- Update domain references in code:
  - capacitor.config.json (mobile apps)
  - pos/mobile/README.md
  - pos/config.py SMTP_FROM
- Add Caddy config docs for reverse proxy VM (192.168.10.74)
2026-05-14 08:59:29 +00:00
ee9eea58c1 feat(catalog): wire up brand-first OEM catalog UI
- Add brand-catalog.js overlay: Brands -> Categories -> Parts flow
- Update catalog.html: 'Por Marca' button opens BrandCatalog overlay
- Optimize /vehicle-brands to query brands table (fast) instead of 256M part_vehicle_preview
- Keep /brand-categories and /brand-parts using exact match on part_vehicle_preview
- Integrate addToCart with existing CatalogApp cart
2026-05-14 08:37:37 +00:00
ff45905b49 feat(whatsapp): QWEN primary AI backend, Hermes fallback, conversation history, vehicle persistence, demo prompts
- Add QWEN (qwen3.6) as primary AI backend with short system prompt
- Hermes remains as fallback with 45s timeout
- Increase QWEN timeout to 35s, max_tokens to 4000
- Add conversation history loading from whatsapp_messages (last 4 msgs)
- Persist detected vehicle in whatsapp_sessions table
- Add 'limpiar chat' / 'nuevo chat' / 'reset' commands to clear history
- Fix CSS conflict: rename whatsapp chat-panel classes to wa-chat-panel
- Fix JS ID conflicts with chat.js widget (waChatPanel, waChatMessages, etc.)
- Improve no-stock response: conversational with alternatives
- Split search_query by | for multi-part lookups
- Add DEMO_PROMPTS.md and DEMO_PROMPTS_V2.md
2026-05-06 20:27:14 +00:00
371d72887e refactor: centralize QWEN fitment saving via save_qwen_fitment()
- Added save_qwen_fitment() in inventory_vehicle_compat.py to centralize
  inserting QWEN results into inventory_vehicle_compat
- Simplified inventory_bp.py create_item() and auto_match_item_vehicles()
  to use the centralized function, removing duplicated INSERT logic
2026-05-01 07:03:04 +00:00
af7b010e55 feat: configurable vehicle compatibility source (TecDoc / QWEN / Both)
Backend:
- Added GET/PUT /pos/api/config/vehicle-compat-source endpoints
- Added get_compat_source() helper reading from tenant_config
- create_item() now respects config: runs TecDoc and/or QWEN accordingly
- auto_match_item_vehicles() respects config: runs only configured source

Frontend:
- Added 'Compatibilidad de Vehiculos' section in config.html
- Added loadVehicleCompatSource() / saveVehicleCompatSource() in config.js
- Regenerated config.min.js
2026-05-01 06:52:06 +00:00
5421c47ffc fix(compat): get_compatibility used wrong connection for master tables
inventory_vehicle_compat.get_compatibility was trying to JOIN tenant
inventory_vehicle_compat with master tables (model_year_engine, brands,
models, years, engines) on a single tenant connection. Those tables only
exist in the master DB, causing the query to fail silently.

Fix: split into two queries:
  1. Fetch MYE IDs from tenant's inventory_vehicle_compat
  2. Resolve vehicle details from master DB via ANY(%s)
  3. Merge results

Also fixes the argument mismatch: inventory_bp passed (tenant, master,
item_id) but the function only accepted 2 args.
2026-05-01 06:41:22 +00:00
2e80ba7400 feat(auto_match): exhaustive multi-strategy vehicle compatibility search
Replaced simple exact-match with 8-layer fallback strategy:

1. Exact normalized part number (parts.oem_part_number)
2. Exact normalized aftermarket part number
3. Exact normalized cross-reference number
4. Partial ILIKE match on OEM numbers
5. Partial ILIKE match on aftermarket numbers
6. Partial ILIKE match on cross-reference numbers
7. Separator-stripped fallback (KYB-343412 → KYB343412)
8. Name-based search on parts.name_part / parts.name_es
   and aftermarket_parts.name_aftermarket_parts when no part_number hit

Brand-aware filtering: when brand hint is provided and not 'GENERAL',
only returns MYEs for vehicles of that brand.

Limits: max 20 part IDs per layer, max 200 MYEs total.

Test: BPR5ES + TOYOTA → matched True, 2 parts, 200 MYEs inserted.
2026-05-01 06:22:17 +00:00
0e549e7746 fix: connection pool exhaustion + cross_ref column name
- tenant_db.py: add rollback() before returning conn to pool to prevent
  'idle in transaction (aborted)' state that exhausts the pool
- tenant_db.py: increase pool maxconn from 10 to 20 for better concurrency
- inventory_vehicle_compat.py: fix column name cross_ref_number ->
  cross_reference_number to match actual schema
2026-05-01 02:25:58 +00:00
2b418701b6 fix(inventory): add cache-buster v=2 to inventory.js to force reload
Nginx auto-serves .min.js when .js is requested with try_files.
The browser had the old file cached with 6M expiry. Adding ?v=2
forces clients to fetch the new version with autoMatchCompat exposed.
2026-05-01 01:11:09 +00:00
91826487f9 fix: remove _oem_blocked() from catalog search/part + expose autoMatchCompat
- catalog_bp.py: /search and /part/<id> no longer blocked by CATALOG_OEM_ENABLED
  These endpoints query the master parts DB and enrich with local stock;
  they should work in both local and OEM modes.
- inventory.js: expose autoMatchCompat and removeCompat to window for
  onclick handlers in dynamically generated HTML.
- Regenerated inventory.min.js
2026-05-01 00:30:10 +00:00
b27dd720aa feat(catalog): expand LOCAL_BODEGA_BRANDS to 96 Nort America brands
- Added all brands with vehicles >= 1980 relevant to Mexico-USA-Canada
- Covers: American, Japanese, Korean, German, UK, Italian, French,
  Swedish, Spanish, Chinese (with MX presence), Indian, and commercial
- All 96 brands verified against master DB with year >= 1980
2026-04-30 07:43:39 +00:00
b94b194217 docs: update FASES_IMPLEMENTADAS.md with QWEN 3.6 AI Vehicle Fitment
- Added QWEN env vars section
- Added completed QWEN fitment feature with architecture details
- Documented retry logic, fuzzy matching, and fail-safe behavior
2026-04-29 08:44:26 +00:00
623c57bb08 fix(qwen_fitment): resolve DB schema mismatch and double-fetchone bug
- Fixed column names: brands.name_brand, models.name_model, engines.name_engine
- Added fuzzy model matching with ILIKE %%pattern%% for TecDoc-style names
- Removed erroneous double cur.fetchone() that always returned None
- Added retry logic (3 attempts) for QWEN API empty responses
- Added fallback engine-less query when engine description doesn't match DB
- Protected _extract_json against None input
2026-04-29 08:38:17 +00:00
3cd2874ed7 test(e2e): improve catalog test with mocked APIs and auth
- catalog.spec.js: added fake JWT auth setup, mocked brand/search APIs
  with Playwright route.fulfill, asserts actual rendered cards and
  search dropdown visibility
2026-04-29 07:11:40 +00:00
cf46790ed8 feat(pwa): improve service worker with background sync, push, IndexedDB
- Bumped cache version to nexus-pos-v3
- Background sync for cart (nexus-cart-sync): replays pending
  requests from IndexedDB, clears queue on success
- Push notifications: parse payload, show notification, focus/open
  /pos/sale on click
- Offline cart strategy: queue failed POST /pos/api/cart/* in
  IndexedDB, return queued JSON response
- Message handlers: SKIP_WAITING (preserved) + CLEAR_CACHES
- Periodic background sync stub commented for future cache warming
2026-04-29 07:10:47 +00:00
45b69bcae8 test(e2e): add Playwright smoke tests for catalog, inventory, checkout, auth
- catalog.spec.js: brand grid loads, search interaction
- inventory.spec.js: table loads, detail modal opens
- pos-checkout.spec.js: cart visible, catalog search from POS
- auth-guard.spec.js: unauthenticated redirect to login
2026-04-29 07:10:34 +00:00
3792e4053c feat(monitoring): add Alertmanager with alert rules
- docker-compose.monitoring.yml: added alertmanager service (port 9093)
- prometheus.yml: alerting config + rule_files entry
- alerts.yml: 5 alert rules (PostgreSQLDown, RedisDown, HighDiskUsage,
  HighMemoryUsage, NodeDown)
- alertmanager.yml: SMTP + webhook receiver, inhibit rules
2026-04-29 07:10:22 +00:00
5a913dcac1 feat(monitoring): add Grafana dashboards for PostgreSQL, Redis, System, App
- nexus-postgresql.json: connections, transactions, cache hit, WAL,
  slow queries, table bloat
- nexus-redis.json: memory, commands/sec, clients, cache hit,
  keyspace hits/misses, evicted keys
- nexus-system.json: CPU, memory, disk, network, load average
- nexus-gunicorn.json: request rate, response time, workers,
  5xx errors, memory per worker
- dashboards.yml: auto-provisioning config
2026-04-29 07:10:01 +00:00
cc9a0cf57c feat(backup): automated daily backup script + systemd timer
- scripts/backup.sh: pg_dump + project tar, S3 upload (optional),
  local retention (7 days), dry-run support
- systemd/nexus-backup.service + nexus-backup.timer: daily at 02:00 UTC
- AWS CLI v2 installed locally in tools/ for S3 uploads
2026-04-29 07:09:43 +00:00
f78d4c9b44 docs: sync FASES_IMPLEMENTADAS.md with actual project status
- Moved completed items from this session to 'Completados recientemente'
- Cleared critical debt section (PostgreSQL restart done)
- Marked stubs as 'creado' with file references
- Added new polish items: Grafana dashboards, Alertmanager, SW improvements
- Updated infrastructure table with Prometheus/Grafana
2026-04-29 06:44:27 +00:00
ca239a458b docs: update API, architecture, installation guides and README
- API-POS.md: added sections 11-15 (BNPL, ERP, WhatsApp Cloud,
  Supplier Portal, Dashboard Stats)
- ARCHITECTURE.md: added infra/monitoring section with systemd,
  Prometheus/Grafana, PWA, and integration stubs
- INSTALACION.md: added systemd setup, monitoring docker compose,
  PWA install notes, and Playwright test commands
- README.md: updated endpoint count, tech stack, infrastructure table
2026-04-29 06:34:40 +00:00
fb591c7de6 chore(config): add .env.example and initial catalog seed SQL
- .env.example: complete environment variable template for new installs
- pos/seed/initial_catalog.sql: seed data for catalog setup
2026-04-29 06:31:46 +00:00
b803950fae chore(assets): regenerate minified JS bundles
- customers.min.js, fleet.min.js, inventory.min.js, pos-utils.min.js,
  sidebar.min.js, virtual-scroll.min.js
2026-04-29 06:31:25 +00:00
bd2cf307f7 docs: update FASES_IMPLEMENTADAS.md with completed items and current roadmap
- Added 'Completados recientemente' section (partitioning, Quart,
  minify fix, voice AI, chat.js fix, PostgreSQL tuning)
- Reordered and renumbered remaining roadmap items
- Updated infrastructure table: Quart now shows production status
2026-04-29 06:31:18 +00:00
9b02005116 fix(blueprints): correct auth import and decorator call in tasks_bp
- Changed 'from auth import require_auth' → 'from middleware import require_auth'
- Added missing parentheses: @require_auth → @require_auth()
- Prevents 'No module named auth' and endpoint name collision errors
2026-04-29 06:31:11 +00:00
2cfe4b3913 feat(api): add BNPL, ERP, WhatsApp Cloud, Supplier Portal stubs
- bnpl_bp.py: APLAZO/Kueski/Clip application workflow (mock)
- erp_bp.py: Aspel/CONTPAQi/SAP/Odoo sync jobs (mock)
- whatsapp_cloud_bp.py: Meta Cloud API webhook, messages, templates
- supplier_portal_bp.py: demand by zone/branch and top-parts analytics
- app.py: register all new blueprints
2026-04-29 06:31:03 +00:00
12989e30be feat(dashboard): add real-time in-app stats with Chart.js
- dashboard_stats_bp.py: endpoints /pos/api/dashboard/stats and
  /pos/api/dashboard/stats/employees (sales today/month, hourly,
  top products, employee productivity)
- dashboard-stats.js: renders hourly sales bar chart and top products
  doughnut chart using Chart.js
- chart.umd.min.js: vendored Chart.js v4.4.2
2026-04-29 06:30:54 +00:00
c4db5e7550 test(e2e): setup Playwright with login smoke test
- Installed @playwright/test + Chromium
- playwright.config.js: baseURL localhost:5001, Desktop Chrome
- tests/e2e/login.spec.js: validates login form loads and invalid
  credentials show error
2026-04-29 06:30:46 +00:00
3b8224d15e feat(pwa): add install prompt banner and register in all POS templates
- pwa-install.js: captures beforeinstallprompt, shows dismissible
  banner with 7-day localStorage cooldown, handles appinstalled
- Registered in 12 POS templates alongside existing service worker
2026-04-29 06:30:38 +00:00
4b3b0f8313 feat(monitoring): deploy Prometheus + Grafana stack via Docker
- prometheus.yml: scrapes node, postgres, redis, nexus-pos, nexus-quart
- docker-compose.monitoring.yml: Prometheus, Grafana, node-exporter,
  postgres-exporter, redis-exporter
- Grafana auto-provisions Prometheus datasource
- Access: Grafana :3001 (admin/nexus2026), Prometheus :9090
2026-04-29 06:30:30 +00:00
c766571b7d docs(infra): add PostgreSQL tuning and systemd service documentation
- POSTGRESQL_TUNING.md: documents applied config (8GB shared_buffers,
  64MB work_mem, 8GB max_wal_size, SSD params)
- SYSTEMD_SERVICES.md: lists all production systemd services
- systemd/: versioned copies of all .service and .timer files
- .gitignore: ignore package-lock.json and backups/
2026-04-29 06:30:22 +00:00
44c3a6c910 fix(chat): add missing chatTtsToggle button to prevent null reference error
The chat.js init() template did not include #chatTtsToggle, causing
a runtime TypeError when hasTTS was true. Added the toggle button
inside .chat-header-actions, matching chat-public.js structure.
Regenerated chat.min.js.
2026-04-29 06:30:13 +00:00
f24f25e74e feat(infra): particiona vehicle_parts en 16 particiones HASH + fix script
- Corrige UNIQUE constraint que fallaba por duplicados → índice normal
- Aumenta BATCH_SIZE a 10M + synchronous_commit=off para velocidad
- Particionamiento completado: 2.16B filas en 16 particiones
- vehicle_parts_old conservada como rollback (254 GB)
- Minify script y Quart producción ya commiteados
2026-04-28 11:52:12 +00:00
b829e4f026 fix(infra): 3 mejoras críticas — minify script + Quart producción + particionamiento bloqueado
- scripts/minify-assets.sh: excluye archivos .min.* para evitar .min.min.*
- nginx/nexus-pos.conf: agrega upstream nexus_quart + location /pos/api/catalog/async-search
- nexus-quart.service: servicio systemd para hypercorn en puerto 5002
- particionamiento vehicle_parts: BLOQUEADO — tabla 254 GB, disco solo 177 GB libres
2026-04-28 06:52:52 +00:00
c75e2a75c9 docs: actualiza FASES_IMPLEMENTADAS.md con estado post-voz y roadmap pendiente 2026-04-28 05:17:31 +00:00
27cb4ee683 fix(dashboard): arregla landing.css 404 y APIs 500
- Agrega ruta genérica en server.py para servir CSS/JS/HTML desde root
- Configura DATABASE_URL y JWT_SECRET en nexus.service systemd
- Agrega trust en pg_hba.conf para postgres@localhost en nexus_autoparts
2026-04-28 04:53:34 +00:00
afb3b2405c feat(voice): implementa voz y TTS en chats POS y dashboard
- Agrega TTS (speechSynthesis) a chat.js del POS para leer respuestas IA
- Copia lógica de voz completa (STT + TTS) a dashboard/chat-public.js
- Extiende estilos TTS en chat.css y chat-public.css
- Agrega chat widget a 13 templates POS que no lo tenían
- Corrige duplicado de chat.css en diagrams.html
- Minifica assets actualizados
- 73/73 tests pasan
2026-04-28 00:53:57 +00:00
1f909f4c42 C1: Register tasks_bp in app.py
- Blueprint tasks_bp registrado para endpoints /pos/api/tasks/*
- Tests: 73/73 pasando
2026-04-27 21:02:23 +00:00
a1be8dd0ea OPCIÓN A: A2 Virtual Scroll + A3 Celery + A4 asyncpg PoC + A5 particionamiento
A2 — Virtual scroll en tablas grandes:
- Nuevo helper VirtualScroll en pos/static/js/virtual-scroll.js
- inventory.js: tabla de productos con virtual scroll
- customers.js: tabla de clientes con virtual scroll
- fleet.js: renderMaintenance() y renderHistory() con virtual scroll
- Templates envueltos en .vs-container para scroll

A3 — Celery worker queue:
- pos/celery_app.py + pos/tasks.py (warm cache, bulk import, reports)
- Blueprint tasks_bp.py con endpoints /pos/api/tasks/*
- Script scripts/start_celery.sh

A4 — asyncpg + Quart PoC:
- pos/async_catalog.py: endpoint /pos/api/catalog/async-search
- scripts/benchmark_async_catalog.py: benchmark Flask vs Quart

A5 — Particionar vehicle_parts:
- scripts/partition_vehicle_parts.py: migración segura por hash (16 particiones)
- Soporta --dry-run, --skip-swap, --skip-drop

Tests: 36/36 pasando
2026-04-27 09:53:36 +00:00