Saltar a contenido

PostgreSQL Physical Architecture - Business Observer APV

Fecha: 2026-06-11

Estado: DISENO FISICO CONCEPTUAL / ETAPA LOCAL PILOTO CERRADA / DB DEDICADA LOCAL PREPARADA / LOAD GATE NO EJECUTAR

Scope: tenant

tenant_id: alpuntodeventa

Owner: Gabi / Carlos Canu

Fuente de verdad: docs/tenants/alpuntodeventa/business-observer/design/POSTGRES-PHYSICAL-ARCHITECTURE.md

Documentos relacionados:

  • docs/governance/standards/DATA-DESIGN-STANDARD.md
  • docs/tenants/alpuntodeventa/business-observer/BUSINESS-OBSERVER-DATA-CONTRACT-001.md
  • docs/tenants/alpuntodeventa/business-observer/mappings/SOURCE-001-CLIENTES-MAPPING.md
  • docs/tenants/alpuntodeventa/business-observer/sources/SOURCE-002-SGC-PRODUCTOS.md
  • docs/tenants/alpuntodeventa/business-observer/sources/SOURCE-003-SGC-VENTAS-COMPROBANTES.md
  • docs/tenants/alpuntodeventa/business-observer/SOURCE-INVENTORY-RESULTS-003.md
  • docs/tenants/alpuntodeventa/business-observer/SOURCE-003-DRIFT-ANALYSIS-001.md
  • docs/tenants/alpuntodeventa/business-observer/design/SOURCE-003-SALES-ITEMS-DDL-DESIGN.md
  • docs/tenants/alpuntodeventa/business-observer/design/SOURCE-003-SALES-ITEMS-PILOT-MIGRATION.md
  • docs/tenants/alpuntodeventa/business-observer/design/SOURCE-003-SALES-ITEMS-PILOT-LOAD-001.md
  • docs/tenants/alpuntodeventa/business-observer/design/SOURCE-003-SALES-ITEMS-WINDOW-PILOT-001.md
  • docs/tenants/alpuntodeventa/business-observer/design/SOURCE-003-CREDENTIALS-PREFLIGHT.md
  • docs/tenants/alpuntodeventa/business-observer/design/POSTGRES-LOCAL-DEV-ENVIRONMENT.md
  • docs/tenants/alpuntodeventa/business-observer/design/SOURCE-003-DEDICATED-DB-DDL-PILOT-EXECUTION-001.md
  • docs/tenants/alpuntodeventa/business-observer/design/SOURCE-003-DEDICATED-DB-PILOT-LOAD-GATE.md
  • docs/tenants/alpuntodeventa/business-observer/analytics/CUSTOMER-OWNERSHIP-ANALYTICS.md
  • docs/tenants/alpuntodeventa/business-observer/analytics/SELLER-RECONCILIATION-RULES.md
  • docs/tenants/alpuntodeventa/business-observer/territory/TERRITORY-NORMALIZATION-STRATEGY.md

1. Proposito

Definir conceptualmente la arquitectura fisica futura en PostgreSQL para el Business Observer de APV, cubriendo clientes, productos, ventas, sync, auditoria, territorio y analytics futuras.

Este documento no crea por si mismo tablas, migraciones, queries ni DDL final, y no toca runtime. Como hecho historico al 2026-06-11, la etapa local en gestion_de_negocios_core quedo cerrada: la tabla business_observer.source_003_sales_items fue creada, ajustada a las 68 columnas reales aprobadas y cargada desde SOURCE-003-SNAPSHOT-001, sin produccion final. La DB dedicada local openclaw_business_observer_dev fue preparada posteriormente para aislar futuros pilotos; la carga piloto dedicada SOURCE-003 sigue bloqueada y requiere autorizacion explicita separada.

Su funcion es dejar una guia fisica suficiente para que una implementacion posterior pueda escribir DDL, migraciones, cargas iniciales y validaciones sin volver a discutir las fronteras principales del modelo.

2. Alcance y limites

Incluye:

  • grupos de tablas futuros para sync, auditoria, clientes, productos, ventas, territorio y analytics
  • claves logicas recomendadas
  • columnas principales por tabla
  • campos obligatorios del DATA-DESIGN-STANDARD
  • indices sugeridos
  • clasificacion raw, core, audit o analytics
  • politica conceptual de borrado
  • sensibilidad de datos
  • estrategia incremental y performance

No incluye:

  • SQL ejecutable
  • DDL final
  • migraciones
  • ejecucion de queries
  • creacion de tablas
  • vistas fisicas
  • materialized views
  • runtime, VPS, Docker o servicios

Cierre de etapa local PostgreSQL

Decision documentada al 2026-06-11:

  • gestion_de_negocios_core fue usado como entorno local piloto valido para Business Observer APV.
  • El aislamiento del piloto fue por schema business_observer; no fue por base fisica separada.
  • El estado final del piloto local conserva 1886 filas reales de 2026-06-09 en business_observer.source_003_sales_items.
  • El backup logico acotado a business_observer quedo VERDE con pg_restore --list PASS.
  • La etapa fue suficiente para piloto acotado y evidencia inicial, pero no se recomienda escalar pilotos largos en esa misma DB.
  • Futuros pilotos deberian ejecutarse en una base separada openclaw_business_observer_dev o en un sandbox VPS evaluado formalmente.
  • Esta decision no crea bases nuevas, no mueve datos y no habilita sync, produccion final ni runtime.

Preparacion de DB local dedicada

Evolucion documentada al 2026-06-11:

  • objetivo vigente: usar la base local dedicada openclaw_business_observer_dev con schema business_observer y roles openclaw_bo_admin, openclaw_bo_writer y openclaw_bo_reader.
  • primer intento seguro: el gate admin fallo por autenticacion y se detuvo sin crear base, schema, roles, grants, default privileges ni passwords nuevos.
  • estado posterior documentado: la DB dedicada fue creada y el DDL piloto de business_observer.source_003_sales_items fue ejecutado y validado.
  • gestion_de_negocios_core no fue modificada por la preparacion dedicada y las filas del piloto historico no fueron migradas a la DB dedicada.
  • la carga piloto dedicada SOURCE-003 sigue en estado NO EJECUTAR hasta autorizacion explicita separada.
  • evidencia: docs/tenants/alpuntodeventa/business-observer/design/POSTGRES-LOCAL-DEV-ENVIRONMENT.md, docs/tenants/alpuntodeventa/business-observer/design/SOURCE-003-DEDICATED-DB-DDL-PILOT-EXECUTION-001.md y docs/tenants/alpuntodeventa/business-observer/design/SOURCE-003-DEDICATED-DB-PILOT-LOAD-GATE.md

3. Reglas rectoras obligatorias

  • SOURCE-001 usa tenant_id + codigo_cliente como clave logica fuerte.
  • SOURCE-002 usa tenant_id + sku como clave canonica del dominio producto.
  • SOURCE-003 / Tabla 2 vNext es candidata canonica para source_003_sales_items.
  • SOURCE-003 / SGC Ventas es fuente viva: una fecha ya cargada puede cambiar por entregas, rechazos, cobros, descuentos, notas de credito, anulaciones, refacturacion o ajustes de cuenta corriente.
  • SOURCE-003 no debe sincronizarse con incremental simple basado solo en ultima fecha cargada.
  • Las ventas se atribuyen al vendedor transaccional real.
  • seller_assigned no sobrescribe seller_transactional.
  • seller_transactional no borra la cartera asignada del cliente.
  • La diferencia entre vendedor asignado y transaccional se preserva como senal analitica.
  • Zona de clientes es logistica, no territorio comercial de vendedor.
  • Clientes suspendidos o de baja se preservan para historico.
  • WhatsApp no es identificador unico.
  • Fechas del SGC, como fecha_alta_sgc, no reemplazan created_at ni updated_at.
  • extracted_at y last_seen_at controlan sync y reconciliacion.
  • source_row_hash controla deteccion de cambios.
  • sync_batch_id permite auditoria por corrida.
  • No hay hard delete por baja comercial, ausencia temporal o cambio de estado funcional.

4. Campos estandar obligatorios

Toda tabla propuesta debe contemplar estos campos, salvo excepcion futura documentada en el DDL:

Campo Uso
id identificador tecnico interno
tenant_id aislamiento tenant
source_system sistema origen, por ejemplo mssql:mssql-sgc-ecommerce
source_object tabla, vista, query o salida origen
source_query_version version de autoridad o logica de extraccion
source_key clave funcional serializada o canonica
source_row_hash hash de valores relevantes para detectar cambios
sync_batch_id corrida que inserto o actualizo la fila
extracted_at momento en que la fila fue leida del origen
last_seen_at ultima extraccion valida en la que la fila fue observada
created_at alta tecnica interna en OpenClaw
updated_at actualizacion tecnica interna en OpenClaw
record_status estado tecnico/funcional de persistencia

Valores conceptuales sugeridos para record_status:

  • active
  • inactive
  • suspended
  • missing_from_source
  • superseded
  • invalid
  • manual_review

5. Diseno de claves

Clave Composicion conceptual Uso
customer_key tenant_id + codigo_cliente ancla comun de todos los bloques de cliente
product_key tenant_id + sku ancla comun de productos, ventas y analytics por item
sales_item_key tenant_id + fecha + tipo_comp + nro_comp + tipo_doc_int + nro_int_doc + documento + codigo_cliente + sku + seller_transactional_key + line_key identidad futura de linea de venta calculada
document_key tenant_id + tipo_comp + nro_comp + tipo_doc_int + nro_int_doc + documento identidad documental de comprobante
seller_assigned_key tenant_id + seller_code_raw desde SOURCE-001 vendedor responsable de cartera formal
seller_transactional_key tenant_id + seller_transactional_code_raw desde SOURCE-003 vendedor que hizo la venta real
logistic_zone_key tenant_id + logistic_zone_normalized agrupacion logistica canonica

Regla vigente por inventario controlado y decision humana:

  • SOURCE-INVENTORY-RESULTS-003.md valido Tabla 2 vNext en solo lectura.
  • line_key_v1 fallo unicidad en ventana mayor.
  • line_key_v3 fallo porque Hora no resolvio los duplicados restantes.
  • No se observo un line_id estable en metadata de ecommerce.dbo.V_VENTAS; el IdFila actual es tecnico de sesion y no debe persistirse como clave.
  • La identidad vigente para piloto es line_key_v4, en estado AMARILLO ACEPTADO:

text line_key_v4 = sha256(canonical( fecha, hora_origen_sgc, tipo_comp, nro_comp, tipo_doc_int, nro_int_doc, documento, codigo_cliente, sku, vendedor_codigo, line_sequence_v1 ))

  • line_sequence_v1 resuelve unicidad agregada como tecnica de pipeline, pero no demuestra identidad fisica de linea ERP.
  • La migracion piloto fue ejecutada y validada en business_observer.source_003_sales_items dentro de la base local gestion_de_negocios_core.
  • La carga piloto 001 desde SOURCE-003-SNAPSHOT-001 dejo 1886 filas persistidas, 68/68 columnas de negocio contempladas, 0 duplicados de line_key, conciliacion de importe total y CMV en verde, y rollback no ejecutado por validacion exitosa.
  • El aislamiento fisico real del piloto local fue el schema business_observer dentro de gestion_de_negocios_core.
  • El backup acotado a business_observer quedo verificado en VERDE; el backup completo de la base no fue requisito de cierre de la etapa local porque involucraba schemas no tocados por el piloto.
  • La base gestion_de_negocios_core no debe usarse como destino de pilotos largos futuros sin una decision explicita de gobierno.
  • Produccion final sigue pendiente de validacion adicional y aprobacion explicita.

6. Grupos de tablas

6.1 Sync y auditoria

Tabla Capa Proposito Grano Claves Columnas principales adicionales Indices sugeridos Hard delete Sensibilidad
sync_batches audit Registrar cada lote de sincronizacion futura. una corrida o batch por fuente/ventana id, tenant_id, sync_batch_id unico batch_started_at, batch_finished_at, batch_status, source_window_from, source_window_to, row_count_read, row_count_inserted, row_count_updated, row_count_missing, error_summary, metadata_json tenant_id + sync_batch_id, tenant_id + source_system + source_object + batch_started_at, batch_status No, salvo purga gobernada de logs viejos no requeridos por auditoria baja/media por metadata operativa
source_sync_runs audit Detallar ejecuciones por fuente dentro de un batch. una ejecucion por fuente, query y ventana id, tenant_id, sync_batch_id, source_system, source_object, source_query_version run_started_at, run_finished_at, run_status, extract_mode, window_from, window_to, checksum_summary, validation_status, validation_notes tenant_id + source_object + run_started_at, tenant_id + sync_batch_id, run_status No baja/media
source_row_audit audit Auditar cambios por fila y fuente sin depender solo de la tabla core. un evento observado por fila y batch id, tenant_id, source_key, sync_batch_id target_table, operation_type, previous_source_row_hash, new_source_row_hash, change_detected, missing_from_source, payload_before_json, payload_after_json, audit_reason tenant_id + source_key, tenant_id + sync_batch_id, tenant_id + target_table + source_key, source_row_hash No media/alta si incluye payloads con datos personales o fiscales

Campos estandar:

  • Las tres tablas incluyen todos los campos obligatorios.
  • En sync_batches, source_key puede representar sync_batch_id.
  • En source_sync_runs, source_key puede representar sync_batch_id + source_object + source_query_version.
  • En source_row_audit, source_key representa la clave funcional de la fila auditada.

6.2 Clientes SOURCE-001

Regla comun:

  • Todos los bloques de cliente cuelgan de tenant_id + codigo_cliente.
  • La separacion fisica no multiplica clientes: separa dominios de atributos del mismo cliente SGC.
  • Cada tabla debe incluir los campos estandar obligatorios y usar source_object = ecommerce.dbo.VCLIENTES o alias oficial vigente.
Tabla Capa Proposito Grano Claves Columnas principales adicionales Indices sugeridos Hard delete Sensibilidad
source_001_customers_core core Identidad, nombre, estado y fechas comerciales del cliente. un cliente SGC vigente o historico por codigo_cliente customer_key, tenant_id + codigo_cliente, source_key = codigo_cliente codigo_cliente, customer_name, legal_name, estado_raw, customer_status, can_sell, fecha_alta_sgc, fecha_baja_sgc, data_quality_status unico tenant_id + codigo_cliente; tenant_id + customer_status; tenant_id + fecha_baja_sgc; source_row_hash; sync_batch_id; last_seen_at No media, por razon social y estado
source_001_customers_contact core Datos de contacto preservando raw y normalizados. un set de contacto por cliente customer_key, tenant_id + codigo_cliente whatsapp_raw, whatsapp_normalized, whatsapp_quality_status, email_raw, email_normalized, admin_contact_raw, contact_quality_status tenant_id + codigo_cliente; tenant_id + email_normalized; tenant_id + whatsapp_normalized no unico; sync_batch_id No alta, datos personales/contacto
source_001_customers_address core Direccion operativa y territorio logistico del cliente. una direccion/logistica principal por cliente customer_key, tenant_id + codigo_cliente, logistic_zone_key opcional delivery_address_raw, cross_streets_raw, delivery_notes_raw, city_raw, city_normalized, state_province_raw, state_province_normalized, logistic_zone_raw, logistic_zone_type, logistic_zone_normalized, microzona_normalized tenant_id + codigo_cliente; tenant_id + state_province_normalized + city_normalized; tenant_id + logistic_zone_normalized; sync_batch_id No alta, direccion y ubicacion
source_001_customers_tax core Datos fiscales del cliente. un perfil fiscal por cliente customer_key, tenant_id + codigo_cliente vat_condition_raw, tax_id_raw, tax_id_normalized, gross_income_tax_id_raw, collect_pib_raw, pib_percentage_raw, tax_quality_status tenant_id + codigo_cliente; tenant_id + tax_id_normalized no necesariamente unico hasta validar; sync_batch_id No alta, datos fiscales
source_001_customers_commercial core Atributos comerciales no transaccionales del cliente. un perfil comercial por cliente customer_key, tenant_id + codigo_cliente price_list_code_raw, channel_raw, customer_category_raw, last_purchase_date, payment_terms_raw, discount_rule_raw, credit_limit_raw, allowed_arrears_raw tenant_id + codigo_cliente; tenant_id + last_purchase_date; tenant_id + price_list_code_raw; tenant_id + channel_raw; sync_batch_id No media/alta por credito y condiciones
source_001_customers_sales_owner core Vendedor asignado y ownership formal del cliente. un owner asignado por cliente y observacion vigente customer_key, seller_assigned_key, tenant_id + codigo_cliente seller_code_raw, seller_name_raw, seller_first_name, seller_last_name, ownership_assigned_status, assignment_valid_from, assignment_valid_to tenant_id + codigo_cliente; tenant_id + seller_code_raw; tenant_id + seller_code_raw + codigo_cliente; sync_batch_id No baja/media
source_001_customers_visit_schedule core Frecuencia y dias de visita asignados. un calendario de visita por cliente customer_key, tenant_id + codigo_cliente visit_frequency_code_raw, visit_frequency_label_raw, visit_monday_raw, visit_tuesday_raw, visit_wednesday_raw, visit_thursday_raw, visit_friday_raw, visit_saturday_raw, visit_days_mask, schedule_quality_status tenant_id + codigo_cliente; tenant_id + visit_frequency_code_raw; tenant_id + seller_assigned_key si se materializa; sync_batch_id No baja/media

6.3 Productos SOURCE-002

Regla comun:

  • tenant_id + sku es la clave canonica.
  • Los valores economicos vigentes pueden vivir en tablas core de producto, pero la historizacion fina de precios, costos, impuestos y margenes queda pendiente para diseno posterior.
  • SOURCE-002C y SOURCE-002D no reemplazan a SOURCE-002.
Tabla Capa Proposito Grano Claves Columnas principales adicionales Indices sugeridos Hard delete Sensibilidad
source_002_products_core core Identidad maestra, descripcion, estado y clasificacion del SKU. un SKU comercial por tenant product_key, tenant_id + sku, source_key = sku sku, article_name, brand_raw, product_status_raw, category_raw, subcategory_raw, plu_article, plu_pack, unit_of_measure, strategic_raw, last_purchase_date_sgc, last_sale_date_sgc, last_cost_change_date_sgc unico tenant_id + sku; tenant_id + brand_raw; tenant_id + category_raw; tenant_id + product_status_raw; source_row_hash; sync_batch_id No, salvo exclusion operativa gobernada y auditada baja/media
source_002_products_commercial core Politica comercial vigente, precios visibles y reglas de venta del SKU. una politica vigente por SKU product_key, tenant_id + sku price_list_net, price_list_final, allowed_discount, price_with_allowed_discount_final, offer_price_final, accepts_return_raw, minimum_sale_quantity, grouped_sale_quantity, markup, price_policy_quality_status tenant_id + sku; tenant_id + offer_price_final; tenant_id + allowed_discount; sync_batch_id No media por politica/precio
source_002_products_supplier core Relacion vigente del SKU con proveedor y marca/proveedor legible. un proveedor vigente por SKU product_key, tenant_id + sku, tenant_id + supplier_code_raw supplier_code_raw, supplier_name_raw, brand_raw, supplier_relation_status, supplier_quality_status tenant_id + sku; tenant_id + supplier_code_raw; tenant_id + supplier_name_raw; sync_batch_id No baja/media
source_002_products_costing core Costos, descuentos de compra, impuestos y senales economicas vigentes. una observacion economica vigente por SKU product_key, tenant_id + sku supplier_list_cost, purchase_discount_1, purchase_discount_2, purchase_discount_3, net_cost, vat_rate, vat_amount_list_final, margin_l1 a margin_l9, price_l1 a price_l9, vat_price_l1 a vat_price_l9, net_price_l1 a net_price_l9, cost_quality_status tenant_id + sku; tenant_id + net_cost; tenant_id + vat_rate; sync_batch_id; source_row_hash No alta comercial/economica

6.4 Ventas SOURCE-003

Regla comun:

  • La fuente candidata de sync es SOURCE-003 / Tabla 2 vNext.
  • La fuente debe tratarse como viva, con drift retroactivo aproximado de una semana operativa.
  • El hecho base recomendado es source_003_sales_items.
  • La venta se atribuye por seller_transactional_key.
  • seller_assigned_key solo se agrega como referencia analitica cuando se cruce contra clientes, nunca para reemplazar al vendedor real.
  • El estado raw del comprobante debe preservarse si la salida o una extension futura de autoridad lo expone.
Tabla Capa Proposito Grano Claves Columnas principales adicionales Indices sugeridos Hard delete Sensibilidad
source_003_sales_items raw/core Persistir la salida itemizada calculada de Tabla 2; el DDL documental queda en design/SOURCE-003-SALES-ITEMS-DDL-DESIGN.md, el mapping completo queda en design/SOURCE-003-SALES-ITEMS-COLUMN-MAPPING.md y la carga piloto 001 queda evidenciada en design/SOURCE-003-SALES-ITEMS-PILOT-LOAD-001.md. una linea calculada de comprobante por cliente, documento, SKU, vendedor transaccional, hora_origen_sgc, line_sequence_v1 y line_key_v4 tenant_id + line_key, document_key, customer_key, product_key, seller_transactional_key las 68 columnas reales de Tabla 2 V2, mas columnas tecnicas de tenant, batch, line_key_v4, line_sequence_v1, source_row_hash_v1, auditoria y estado; incluye entrega/repartidor, descuentos separados, impuestos, costos, CMV, contribucion, peso, volumen y bultos unico tenant_id + line_key; tenant_id + fecha; tenant_id + vendedor_codigo + fecha; tenant_id + codigo_cliente; tenant_id + sku + fecha; tenant_id + tipo_comp + nro_comp; tenant_id + sync_batch_id; tenant_id + record_status; tenant_id + source_row_hash No, recalculo por ventana y estados trazables alta comercial y transaccional
source_003_sales_documents core opcional Cabecera documental derivada cuando haga falta acelerar consultas por comprobante. un documento/comprobante document_key, tenant_id + document_key sale_date, tipo_comp, nro_comp, tipo_doc_int, nro_int_doc, documento, codigo_cliente, seller_transactional_code_raw, document_status_raw, document_total_net, document_total_gross, document_total_vat, document_total_iibb, items_count, document_quality_status unico tenant_id + document_key; tenant_id + sale_date; tenant_id + codigo_cliente + sale_date; tenant_id + seller_transactional_code_raw + sale_date; sync_batch_id No alta comercial/transaccional
source_003_sales_item_audit audit Preservar cambios por linea ante recalculo de ventanas moviles. un evento de cambio por sales item y batch id, tenant_id + sales_item_key + sync_batch_id sales_item_key, change_type, previous_source_row_hash, new_source_row_hash, previous_amounts_json, new_amounts_json, window_from, window_to, recalculation_reason, validation_status tenant_id + sales_item_key; tenant_id + sync_batch_id; tenant_id + sale_date; change_type No alta si preserva importes y contexto cliente

6.5 Territorio

Regla comun:

  • Territorio fisico/logistico y territorio comercial no son equivalentes.
  • territory_alias_catalog y logistic_zones sostienen normalizacion y consumo analitico, pero no definen vendedor.
Tabla Capa Proposito Grano Claves Columnas principales adicionales Indices sugeridos Hard delete Sensibilidad
territory_alias_catalog core Catalogar aliases territoriales y su valor canonico aprobado o pendiente. un alias por nivel territorial y fuente id, tenant_id + source_field + alias_raw source_field, territory_level, territory_type, alias_raw, canonical_value, confidence_status, approved_by, approved_at, source_evidence, active, notes tenant_id + source_field + alias_raw; tenant_id + canonical_value; tenant_id + confidence_status; sync_batch_id No; desactivar con active=false media si incluye evidencia de origen
logistic_zones core Catalogo canonico de zonas logisticas. una zona logistica canonica logistic_zone_key, tenant_id + logistic_zone_normalized logistic_zone_raw_representative, logistic_zone_normalized, logistic_zone_type, zone_status, description, source_evidence, approved_by, approved_at unico tenant_id + logistic_zone_normalized; tenant_id + logistic_zone_type; tenant_id + zone_status No baja
logistic_zone_localities core Relacion entre zona logistica canonica, provincia y localidad. una relacion zona-localidad-provincia id, logistic_zone_key, tenant_id + logistic_zone_normalized + state_province_normalized + city_normalized state_province_raw, state_province_normalized, city_raw, city_normalized, relationship_status, confidence_status, approved_by, approved_at, source_evidence tenant_id + logistic_zone_normalized; tenant_id + state_province_normalized + city_normalized; tenant_id + confidence_status No media por ubicacion

6.6 Analytics futuras

Regla comun:

  • Estas tablas no reemplazan fuentes core.
  • Deben derivarse desde source_003_sales_items, clientes, productos y catalogos territoriales.
  • Pueden implementarse luego como tablas agregadas o materialized views, segun performance real.
Tabla Capa Proposito Grano Claves Columnas principales adicionales Indices sugeridos Hard delete Sensibilidad
analytics_sales_daily analytics Agregado diario general de ventas calculadas. un dia por tenant tenant_id + sale_date sale_date, net_sales_amount, gross_sales_amount, vat_amount, iibb_amount, cmv_amount, contribution_amount, units_sold, sold_packs, documents_count, customers_count, items_count unico tenant_id + sale_date; sync_batch_id Regenerable, pero no borrar sin auditoria media comercial
analytics_sales_by_seller_daily analytics Ventas diarias por vendedor transaccional. un dia por vendedor transaccional tenant_id + sale_date + seller_transactional_key sale_date, seller_transactional_code, seller_transactional_name, net_sales_amount, gross_sales_amount, cmv_amount, contribution_amount, customers_count, items_count, documents_count unico tenant_id + sale_date + seller_transactional_code; tenant_id + seller_transactional_code + sale_date; sync_batch_id Regenerable media/alta por desempeno comercial
analytics_sales_by_customer_daily analytics Ventas diarias por cliente. un dia por cliente tenant_id + sale_date + customer_key sale_date, codigo_cliente, customer_name, seller_assigned_code, net_sales_amount, gross_sales_amount, sku_count, documents_count, last_transactional_seller_code unico tenant_id + sale_date + codigo_cliente; tenant_id + codigo_cliente + sale_date; sync_batch_id Regenerable alta por cliente
analytics_sales_by_product_daily analytics Ventas diarias por SKU. un dia por producto tenant_id + sale_date + product_key sale_date, sku, article_name, brand, supplier_code, supplier_name, net_sales_amount, gross_sales_amount, units_sold, sold_packs, cmv_amount, contribution_amount, customers_count unico tenant_id + sale_date + sku; tenant_id + sku + sale_date; tenant_id + brand + sale_date; tenant_id + supplier_code + sale_date; sync_batch_id Regenerable media/alta comercial
analytics_customer_ownership analytics Lectura derivada de ownership formal, ultima venta y actividad real. un cliente por corte analitico tenant_id + as_of_date + customer_key as_of_date, codigo_cliente, seller_assigned_code, seller_last_sale_code, seller_effective_code, last_sale_at, assigned_seller_last_sale_at, days_without_sale, days_without_assigned_seller_sale, seller_mismatch_status, ownership_status, recent_sellers_count, assigned_seller_sales_share unico tenant_id + as_of_date + codigo_cliente; tenant_id + seller_assigned_code + as_of_date; tenant_id + seller_last_sale_code + as_of_date; tenant_id + ownership_status Regenerable con snapshot auditado alta por cliente/vendedor
analytics_seller_reconciliation analytics Medir diferencia entre cartera asignada y ventas reales. un vendedor o par vendedor/periodo segun corte tenant_id + period_start + period_end + seller_key period_start, period_end, seller_code, assigned_customers_count, worked_assigned_customers_count, customers_worked_by_others_count, sales_in_own_portfolio, sales_outside_portfolio, mismatch_sales_count, mismatch_customers_count, manual_review_count tenant_id + seller_code + period_start; tenant_id + period_start + period_end; sync_batch_id Regenerable alta por performance
analytics_commercial_territory analytics Territorio comercial derivado de cartera, geografia, ventas y productos. vendedor, periodo y territorio normalizado tenant_id + period_start + period_end + seller_key + territory_key period_start, period_end, seller_code, state_province_normalized, city_normalized, logistic_zone_normalized, assigned_customers_count, active_customers_count, sold_customers_count, net_sales_amount, sku_count, brand_count, supplier_count, territory_status tenant_id + seller_code + period_start; tenant_id + logistic_zone_normalized + period_start; tenant_id + state_province_normalized + city_normalized; sync_batch_id Regenerable alta por territorio comercial

7. Estrategia incremental

Fuentes sin updated_at confiable:

  • usar full extract o ventana completa controlada
  • calcular source_row_hash por fila canonicalizada
  • insertar nuevas filas cuando no exista source_key
  • actualizar solo cuando cambia source_row_hash
  • refrescar last_seen_at cuando la fila aparece sin cambios
  • marcar missing_from_source o record_status = missing_from_source cuando la fila desaparece de una extraccion valida
  • no ejecutar hard delete
  • auditar cada cambio en source_row_audit o tabla audit especifica

Ventas:

  • ejecutar carga historica inicial antes de la sync diaria
  • tomar snapshot diario de SOURCE-003 / Tabla 2
  • recalcular ventana movil de SOURCE-003 / Tabla 2, sugerida inicialmente de 10 dias para cubrir una semana operativa mas margen
  • comparar por tenant_id + line_key y source_row_hash
  • refrescar last_seen_at si la fila aparece sin cambios
  • actualizar valores si cambia source_row_hash
  • marcar missing_from_source si una linea deja de aparecer dentro de una extraccion full o ventana controlada
  • preservar cambios de importes, signos, notas de credito, anulaciones y ajustes en source_003_sales_item_audit
  • congelar fechas piloto desde snapshot, no desde SGC vivo
  • no depender de campos crudos del ERP si difieren de la salida calculada

Batches:

  • todo proceso futuro debe crear sync_batches
  • toda fuente dentro del batch debe registrar source_sync_runs
  • toda tabla destino debe guardar sync_batch_id, extracted_at y last_seen_at

8. Estrategia de performance

Indices base:

  • tenant_id + clave_logica en todas las tablas core
  • tenant_id + codigo_cliente en clientes y ventas por cliente
  • tenant_id + sku en productos y ventas por producto
  • tenant_id + sale_date en ventas y analytics
  • tenant_id + seller_transactional_code + sale_date para atribucion real de ventas
  • tenant_id + seller_assigned_code para cartera formal
  • tenant_id + sync_batch_id en tablas sincronizadas y auditables
  • source_row_hash donde se use deteccion de cambios
  • last_seen_at donde se use reconciliacion de desapariciones

Ventas:

  • indexar por fecha de venta
  • indexar por vendedor transaccional
  • indexar por cliente
  • indexar por SKU
  • indexar por documento
  • evaluar particionado futuro por sale_date en source_003_sales_items si el volumen crece mucho o si las ventanas historicas vuelven costosas las consultas y mantenimiento

Analytics:

  • considerar materialized views futuras para agregados pesados
  • no crear materialized views hasta validar volumen, patrones de consulta y tiempos reales
  • separar agregados diarios de lecturas de ownership, reconciliacion y territorio comercial para evitar una unica tabla sobredimensionada

9. Decisiones de diseno

  • Se separan tablas de cliente por dominio para reducir mezcla de contacto, fiscal, direccion, comercial, ownership y calendario.
  • Se conserva una clave comun customer_key para evitar multiplicar clientes.
  • Se preserva raw + normalized en contacto, territorio y campos con calidad heterogenea.
  • Se modela Zona como dimension logistica, no como territorio comercial.
  • Se separa seller_assigned_key de seller_transactional_key.
  • La facturacion real se atribuye siempre a seller_transactional_key.
  • source_003_sales_documents queda opcional porque el itemizado es la fuente principal; se justifica solo por performance o consumo documental.
  • Los agregados analytics son regenerables, pero deben mantener trazabilidad de batch y fecha de corte.
  • No se habilita hard delete para core ni auditoria.
  • Los datos economicos de productos se preservan como vigentes en esta arquitectura, dejando historiales finos de precio/costo como diseno futuro.

10. Pendientes preservados

  • promocion productiva posterior a la migracion piloto validada
  • migracion productiva final
  • carga inicial
  • validacion ampliada de SOURCE-003 / Tabla 2 vNext para ventana movil o backfill antes de ejecutar cargas futuras
  • conciliacion Tabla 2 vs Tabla 3/4/5/6
  • mantener el siguiente piloto en el entorno aislado ya preparado: openclaw_business_observer_dev; cualquier alternativa VPS requiere evaluacion formal separada
  • definicion final de materialized views
  • permisos de consumo
  • performance real
  • historiales fisicos finos de precios, costos, impuestos, margenes y descuentos
  • externalizacion operativa de exclusiones SOURCE-002
  • normalizacion definitiva de WhatsApp
  • aprobacion humana final de aliases territoriales

11. Confirmaciones de alcance

  • modo DESIGN + BUILD + VALIDATE aplicado para esta actualizacion
  • runtime de aplicacion no tocado
  • sin queries de carga real en la DB dedicada
  • tabla piloto historica source_003_sales_items creada, ajustada y cargada en gestion_de_negocios_core con 1886 filas desde SOURCE-003-SNAPSHOT-001
  • DDL piloto dedicado ejecutado en openclaw_business_observer_dev; carga piloto dedicada sigue en estado NO EJECUTAR
  • migracion piloto historica ejecutada en PostgreSQL local
  • sin vistas fisicas
  • sin VPS
  • sin Docker
  • arquitectura PostgreSQL documentada conceptualmente
  • etapa local en gestion_de_negocios_core documentada y cerrada como piloto acotado
  • aislamiento por schema business_observer documentado
  • backup acotado a business_observer documentado como VERDE
  • no se recomienda escalar pilotos largos futuros en gestion_de_negocios_core
  • DDL documental de source_003_sales_items referenciado
  • migracion piloto/documental de source_003_sales_items ejecutada y validada
  • SOURCE-001, SOURCE-002 y SOURCE-003 contemplados
  • analytics futuras contempladas