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.mddocs/tenants/alpuntodeventa/business-observer/BUSINESS-OBSERVER-DATA-CONTRACT-001.mddocs/tenants/alpuntodeventa/business-observer/mappings/SOURCE-001-CLIENTES-MAPPING.mddocs/tenants/alpuntodeventa/business-observer/sources/SOURCE-002-SGC-PRODUCTOS.mddocs/tenants/alpuntodeventa/business-observer/sources/SOURCE-003-SGC-VENTAS-COMPROBANTES.mddocs/tenants/alpuntodeventa/business-observer/SOURCE-INVENTORY-RESULTS-003.mddocs/tenants/alpuntodeventa/business-observer/SOURCE-003-DRIFT-ANALYSIS-001.mddocs/tenants/alpuntodeventa/business-observer/design/SOURCE-003-SALES-ITEMS-DDL-DESIGN.mddocs/tenants/alpuntodeventa/business-observer/design/SOURCE-003-SALES-ITEMS-PILOT-MIGRATION.mddocs/tenants/alpuntodeventa/business-observer/design/SOURCE-003-SALES-ITEMS-PILOT-LOAD-001.mddocs/tenants/alpuntodeventa/business-observer/design/SOURCE-003-SALES-ITEMS-WINDOW-PILOT-001.mddocs/tenants/alpuntodeventa/business-observer/design/SOURCE-003-CREDENTIALS-PREFLIGHT.mddocs/tenants/alpuntodeventa/business-observer/design/POSTGRES-LOCAL-DEV-ENVIRONMENT.mddocs/tenants/alpuntodeventa/business-observer/design/SOURCE-003-DEDICATED-DB-DDL-PILOT-EXECUTION-001.mddocs/tenants/alpuntodeventa/business-observer/design/SOURCE-003-DEDICATED-DB-PILOT-LOAD-GATE.mddocs/tenants/alpuntodeventa/business-observer/analytics/CUSTOMER-OWNERSHIP-ANALYTICS.mddocs/tenants/alpuntodeventa/business-observer/analytics/SELLER-RECONCILIATION-RULES.mddocs/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,auditoanalytics - politica conceptual de borrado
- sensibilidad de datos
- estrategia incremental y performance
No incluye:
SQLejecutableDDLfinal- migraciones
- ejecucion de queries
- creacion de tablas
- vistas fisicas
materialized views- runtime,
VPS,Dockero servicios
Cierre de etapa local PostgreSQL¶
Decision documentada al 2026-06-11:
gestion_de_negocios_corefue usado como entorno local piloto valido paraBusiness Observer APV.- El aislamiento del piloto fue por schema
business_observer; no fue por base fisica separada. - El estado final del piloto local conserva
1886filas reales de2026-06-09enbusiness_observer.source_003_sales_items. - El backup logico acotado a
business_observerquedoVERDEconpg_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_devo en un sandboxVPSevaluado 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_devcon schemabusiness_observery rolesopenclaw_bo_admin,openclaw_bo_writeryopenclaw_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
DDLpiloto debusiness_observer.source_003_sales_itemsfue ejecutado y validado. gestion_de_negocios_coreno 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 EJECUTARhasta 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.mdydocs/tenants/alpuntodeventa/business-observer/design/SOURCE-003-DEDICATED-DB-PILOT-LOAD-GATE.md
3. Reglas rectoras obligatorias¶
SOURCE-001usatenant_id + codigo_clientecomo clave logica fuerte.SOURCE-002usatenant_id + skucomo clave canonica del dominio producto.SOURCE-003 / Tabla 2 vNextes candidata canonica parasource_003_sales_items.SOURCE-003 / SGC Ventases fuente viva: una fecha ya cargada puede cambiar por entregas, rechazos, cobros, descuentos, notas de credito, anulaciones, refacturacion o ajustes de cuenta corriente.SOURCE-003no debe sincronizarse con incremental simple basado solo enultima fecha cargada.- Las ventas se atribuyen al vendedor transaccional real.
seller_assignedno sobrescribeseller_transactional.seller_transactionalno borra la cartera asignada del cliente.- La diferencia entre vendedor asignado y transaccional se preserva como senal analitica.
Zonade clientes es logistica, no territorio comercial de vendedor.- Clientes suspendidos o de baja se preservan para historico.
WhatsAppno es identificador unico.- Fechas del
SGC, comofecha_alta_sgc, no reemplazancreated_atniupdated_at. extracted_atylast_seen_atcontrolan sync y reconciliacion.source_row_hashcontrola deteccion de cambios.sync_batch_idpermite auditoria por corrida.- No hay
hard deletepor 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:
activeinactivesuspendedmissing_from_sourcesupersededinvalidmanual_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.mdvalidoTabla 2 vNexten solo lectura.line_key_v1fallo unicidad en ventana mayor.line_key_v3fallo porqueHorano resolvio los duplicados restantes.- No se observo un
line_idestable en metadata deecommerce.dbo.V_VENTAS; elIdFilaactual es tecnico de sesion y no debe persistirse como clave. - La identidad vigente para piloto es
line_key_v4, en estadoAMARILLO 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_v1resuelve unicidad agregada como tecnica de pipeline, pero no demuestra identidad fisica de lineaERP.- La migracion piloto fue ejecutada y validada en
business_observer.source_003_sales_itemsdentro de la base localgestion_de_negocios_core. - La carga piloto
001desdeSOURCE-003-SNAPSHOT-001dejo1886filas persistidas,68/68columnas de negocio contempladas,0duplicados deline_key, conciliacion de importe total yCMVen verde, y rollback no ejecutado por validacion exitosa. - El aislamiento fisico real del piloto local fue el schema
business_observerdentro degestion_de_negocios_core. - El backup acotado a
business_observerquedo verificado enVERDE; 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_coreno 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_keypuede representarsync_batch_id. - En
source_sync_runs,source_keypuede representarsync_batch_id + source_object + source_query_version. - En
source_row_audit,source_keyrepresenta 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.VCLIENTESo 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 + skues 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-002CySOURCE-002Dno reemplazan aSOURCE-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_keysolo 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_catalogylogistic_zonessostienen 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 extracto ventana completa controlada - calcular
source_row_hashpor fila canonicalizada - insertar nuevas filas cuando no exista
source_key - actualizar solo cuando cambia
source_row_hash - refrescar
last_seen_atcuando la fila aparece sin cambios - marcar
missing_from_sourceorecord_status = missing_from_sourcecuando la fila desaparece de una extraccion valida - no ejecutar
hard delete - auditar cada cambio en
source_row_audito 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 de10dias para cubrir una semana operativa mas margen - comparar por
tenant_id + line_keyysource_row_hash - refrescar
last_seen_atsi la fila aparece sin cambios - actualizar valores si cambia
source_row_hash - marcar
missing_from_sourcesi una linea deja de aparecer dentro de una extraccionfullo 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
SGCvivo - no depender de campos crudos del
ERPsi 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_atylast_seen_at
8. Estrategia de performance¶
Indices base:
tenant_id + clave_logicaen todas las tablas coretenant_id + codigo_clienteen clientes y ventas por clientetenant_id + skuen productos y ventas por productotenant_id + sale_dateen ventas y analyticstenant_id + seller_transactional_code + sale_datepara atribucion real de ventastenant_id + seller_assigned_codepara cartera formaltenant_id + sync_batch_iden tablas sincronizadas y auditablessource_row_hashdonde se use deteccion de cambioslast_seen_atdonde 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_dateensource_003_sales_itemssi el volumen crece mucho o si las ventanas historicas vuelven costosas las consultas y mantenimiento
Analytics:
- considerar
materialized viewsfuturas para agregados pesados - no crear
materialized viewshasta 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_keypara evitar multiplicar clientes. - Se preserva
raw + normalizeden contacto, territorio y campos con calidad heterogenea. - Se modela
Zonacomo dimension logistica, no como territorio comercial. - Se separa
seller_assigned_keydeseller_transactional_key. - La facturacion real se atribuye siempre a
seller_transactional_key. source_003_sales_documentsqueda 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 deletepara 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 vNextpara ventana movil o backfill antes de ejecutar cargas futuras - conciliacion
Tabla 2vsTabla 3/4/5/6 - mantener el siguiente piloto en el entorno aislado ya preparado:
openclaw_business_observer_dev; cualquier alternativaVPSrequiere 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 + VALIDATEaplicado para esta actualizacion - runtime de aplicacion no tocado
- sin queries de carga real en la DB dedicada
- tabla piloto historica
source_003_sales_itemscreada, ajustada y cargada engestion_de_negocios_corecon1886filas desdeSOURCE-003-SNAPSHOT-001 DDLpiloto dedicado ejecutado enopenclaw_business_observer_dev; carga piloto dedicada sigue en estadoNO EJECUTAR- migracion piloto historica ejecutada en
PostgreSQLlocal - sin vistas fisicas
- sin
VPS - sin
Docker - arquitectura
PostgreSQLdocumentada conceptualmente - etapa local en
gestion_de_negocios_coredocumentada y cerrada como piloto acotado - aislamiento por schema
business_observerdocumentado - backup acotado a
business_observerdocumentado comoVERDE - no se recomienda escalar pilotos largos futuros en
gestion_de_negocios_core DDLdocumental desource_003_sales_itemsreferenciado- migracion piloto/documental de
source_003_sales_itemsejecutada y validada SOURCE-001,SOURCE-002ySOURCE-003contemplados- analytics futuras contempladas