El comercio electrónico B2B actual plantea demandas técnicas de máxima exigencia para la ingeniería de software. Los clientes empresariales requieren tarifas contractuales acordadas, pedidos mínimos (MOQ) y escalas de descuento transparentes en función del volumen solicitado. Paralelamente, los motores de búsqueda y los asistentes de compra basados en inteligencia artificial reclaman datos estandarizados y procesables mecánicamente sobre costes unitarios y umbrales cuantitativos. Cualquier desajuste entre los importes declarados en los feeds de datos y los totales computados en el proceso de pago deriva en el rechazo de productos en Google Merchant Center.
Para desplegar un sistema de precios escalonados de alto rendimiento en WooCommerce es indispensable superar las viejas estructuras de metadatos genéricos. Resulta imperativo diseñar esquemas relacionales independientes, implementar mecanismos de generación de feeds mediante flujos continuos (streaming) y aplicar un etiquetado semántico riguroso bajo la norma Schema.org.
Especificaciones técnicas de Google Merchant Center para precios unitarios y tramos mayoristas
Google Merchant Center aplica criterios normativos estrictos a los artículos comercializados por peso, volumen, superficie o en embalajes industriales combinados. En la UE, los países de la AELC, el Reino Unido, Australia y Nueva Zelanda, Google exige el precio unitario en los productos que la normativa local obliga a mostrarlo, para que los compradores corporativos y particulares deben poder evaluar de inmediato la rentabilidad económica de un producto mediante un precio unitario de referencia estandarizado (por ejemplo, el coste por kilogramo, litro o metro cuadrado).
Los atributos troncales del catálogo de productos comprenden:
unit_pricing_measure: La cantidad física o dimensión neta contenida en la unidad comercializada (como25kg,500mlo100ct). Este valor indica al analizador sintáctico la magnitud real comercializada en cada unidad física.unit_pricing_base_measure: El denominador métrico de comparación común (como1kg,100mlo1ct). Google divide el importe íntegro entre este factor para elaborar de forma automática el distintivo de precio unitario.auto_pricing_min_price: El precio más bajo al que Google puede reducir un producto en los descuentos automáticos y las promociones dinámicas.loyalty_program: Atributo de grupo para precios de socio, envíos para miembros y puntos de fidelidad. Es el único lugar para los precios que dependen de unirse a un programa; no existe un atributo separado para tramos mayoristas.
El empleo erróneo de las unidades de medición o incongruencias en las monedas fijadas desencadenan fallos críticos de validación. En el supuesto de comercializar un disolvente industrial en un bidón de 20 litros a un importe de 220 EUR, el parámetro unit_pricing_measure debe reflejar con exactitud 20l y unit_pricing_base_measure debe señalar 1l, permitiendo al buscador proyectar la indicación complementaria de 11 EUR por litro.
Cómo enviar precios escalonados B2B en un feed de Google Merchant Center
La especificación de datos de producto de Google no tiene ningún atributo para tramos por cantidad. Cada artículo del feed lleva un único price, y las reglas del atributo price determinan qué cifra debe ser. Si existe una cantidad mínima de pedido, el precio del feed es el precio de esa cantidad mínima: Google indica que no se envíe el precio de una sola unidad cuando el cliente no puede comprar solo una. En un multipack o lote creado por el comerciante, el precio es el total del paquete completo.
Quedan tres formas viables de mostrar una escala por volumen:
- Productos separados por formato. Cada tamaño de envase (cubo, caja, palé) se convierte en un artículo propio con su
id, supricey suunit_pricing_measure, y todos comparten un mismoitem_group_id. La documentación de unit_pricing_measure muestra este patrón con arroz en bolsas de 5, 10 y 12 libras, cada una con una medida base de 1 libra, de modo que el precio unitario indica al comprador qué formato sale más barato por unidad de peso. - El atributo
multipack. Según la página de multipack, sirve para paquetes que el comerciante ha formado con productos idénticos, y es obligatorio en las fichas gratuitas cuando se crea un paquete así. En un paquete definido por el fabricante no se envíamultipacky la cantidad se expresa conunit_pricing_measure. - La tabla de tramos se queda en la web. Los descuentos por encima del mínimo viven en WooCommerce y en la ficha de producto, mientras el feed transmite el precio de entrada. Esta opción no multiplica las referencias y se mantiene coherente siempre que la página de destino muestre ese mismo precio de entrada.
Para el precio unitario, ambos atributos deben usar el mismo tipo de unidad, y unit_pricing_base_measure solo admite valores concretos: 1, 2, 4, 8, 10 o 100 de una unidad, además de 75cl, 750ml, 50kg y 1000kg (unit_pricing_base_measure). La medida admite como máximo dos decimales. Para el Reino Unido, Google interpreta las unidades imperiales como unidades imperiales estadounidenses, así que lo seguro son los valores métricos. Si un artículo lleva a la vez unit_pricing_measure y una clase de eficiencia energética, Google muestra solo la clase energética.
Qué reglas de página de destino y pago provocan rechazos de productos B2B en Merchant Center
La mayoría de los rechazos B2B nacen de la diferencia entre el feed y lo que ve el comprador. Las reglas del atributo price contienen las restricciones que chocan con las configuraciones mayoristas habituales:
- El precio del feed debe coincidir con el de la página de destino y el del proceso de pago, en la moneda del país de destino, y no se permite “ver precio en el carrito”.
- Cualquier usuario del país de destino debe poder comprar al precio enviado. Se puede exigir una cuenta solo si el registro es gratuito y sencillo, lo que descarta feeds basados en precios que solo ven las cuentas profesionales aprobadas.
- En países como Alemania, Francia o el Reino Unido el precio incluye el IVA, y Google lo aplica también a las ofertas mayoristas. En Estados Unidos y Canadá los impuestos quedan fuera del precio.
- Un importe mínimo de pedido no forma parte del precio. Se configura en los ajustes de envío.
Los precios contractuales y de socio tienen su propio canal. Google establece que los precios para miembros no deben ir en price ni en sale_price; van en el atributo de grupo loyalty_program, con subatributos como program_label, tier_label, price, loyalty_points y member_price_effective_date. El programa debe configurarse antes en Merchant Center, los precios para miembros tienen que ser visibles para ellos en la web, y Google solo muestra precios de socio en los anuncios cuando el descuento alcanza al menos el 5 % o 5 unidades de la moneda. Los ejemplos de Google son niveles de cliente como plata y oro, no cuentas empresariales verificadas, así que una tienda B2B debe comprobar si su tarifa profesional encaja en ese modelo.
Una promoción temporal de un tramo corresponde a sale_price, que debe ser inferior a price. El precio completo sigue enviándose en price, la página de destino muestra ambos precios, el proceso de pago muestra solo el precio rebajado y sale_price_effective_date limita el periodo; sin ese atributo, el precio rebajado se aplica de inmediato. auto_pricing_min_price es otra herramienta: el atributo de precio mínimo es obligatorio para los descuentos automáticos y las promociones dinámicas, y debe situarse entre el coste de los bienes vendidos, si se envía, y el 95 % del precio habitual.
Cuellos de botella en wp_postmeta y una tabla propia de tramos de precio
El esquema de datos predeterminado en WordPress se apoya en el modelo Entity-Attribute-Value (EAV), concentrando todos los metadatos de productos y variaciones en la tabla genérica wp_postmeta. En tiendas minoristas de catálogo moderado este planteamiento resulta funcional. No obstante, en un entorno B2B consolidado donde un producto presenta 5 tramos de volumen para 8 perfiles de cliente corporativo, el volumen de registros se multiplica exponencialmente.
Gestionar 40 condiciones de tarifa para una única referencia se traduce en 40 filas independientes dentro de wp_postmeta. En inventarios industriales con 30 000 productos y 100 000 variaciones, la tabla de metadatos rebasa holgadamente las decenas de millones de filas. Cualquier consulta en las páginas de catálogo provoca costosas operaciones LEFT JOIN, produciendo bloqueos en la base de datos MySQL y retardando las respuestas del servidor.
High-Performance Order Storage (HPOS) no resuelve esto por sí solo. Según la documentación de HPOS de WooCommerce, traslada los pedidos y sus direcciones a cuatro tablas propias (wc_orders, wc_order_addresses, wc_order_operational_data y wc_orders_meta), mientras los productos siguen en las tablas de entradas. Lo que aporta HPOS es el patrón: los datos con una forma conocida reciben su propia tabla con índices que encajan con las consultas. Para los tramos de precio, eso significa una tabla separada con índices compuestos:
-- Tabla relacional especifica para la gestion de precios escalonados b2b
CREATE TABLE IF NOT EXISTS wp_wc_b2b_price_tiers (
tier_id BIGINT UNSIGNED AUTO_INCREMENT PRIMARY KEY,
product_id BIGINT UNSIGNED NOT NULL,
customer_group VARCHAR(32) NOT NULL DEFAULT 'all',
min_quantity INT UNSIGNED NOT NULL DEFAULT 1,
max_quantity INT UNSIGNED DEFAULT NULL,
price_cents BIGINT NOT NULL,
currency CHAR(3) NOT NULL DEFAULT 'EUR',
created_at TIMESTAMP DEFAULT CURRENT_TIMESTAMP,
INDEX idx_product_lookup (product_id, customer_group, min_quantity),
INDEX idx_pricing_search (min_quantity, max_quantity)
) ENGINE=InnoDB DEFAULT CHARSET=utf8mb4 COLLATE=utf8mb4_unicode_ci;Gracias al índice compuesto (product_id, customer_group, min_quantity), la búsqueda de un producto, un grupo de clientes y una cantidad se convierte en una única lectura de rango sobre el índice en lugar de una cadena de uniones sobre wp_postmeta. Prescindir de las consultas contra wp_postmeta reduce la saturación de memoria del InnoDB Buffer Pool y aporta máxima estabilidad a las sesiones concurrentes de compra.
Para explorar estrategias integrales de enlace entre catálogos de comercio y entornos de gestión empresarial, examine nuestro contenido relativo a integración woocommerce erp.
Generación de feeds XML y NDJSON mediante flujos continuos de memoria reducida
La remisión sistemática de decenas de miles de productos B2B con sus escalas de precios a Google Merchant Center exige canales de exportación diseñados con criterios de alta eficiencia. Intentar cargar el catálogo completo en una estructura de memoria en PHP mediante utilidades convencionales como wc_get_products() sobrepasa inexorablemente el límite operativo de memoria (memory_limit).
Una infraestructura moderna de exportación recurre a cursores de base de datos vinculados con generadores de flujo en PHP (yield). Este sistema vuelca los datos en bloques discretos directamente sobre el soporte de almacenamiento o envía flujos NDJSON hacia repositorios en la nube:
<?php
/**
* Generador de feed de productos en flujo continuo para Google Merchant Center
*/
declare(strict_types=1);
namespace WPPoland\B2BFeedsES;
use Generator;
use wpdb;
class StreamedProductFeedGenerator
{
private wpdb $db;
public function __construct(wpdb $db)
{
$this->db = $db;
}
public function streamCatalogBatch(int $batchSize = 500): Generator
{
$offset = 0;
while (true) {
$query = $this->db->prepare(
"SELECT p.ID, p.post_title, t.min_quantity, t.price_cents, t.currency
FROM {$this->db->posts} p
INNER JOIN wp_wc_b2b_price_tiers t ON p.ID = t.product_id
WHERE p.post_type IN ('product', 'product_variation')
AND p.post_status = 'publish'
AND t.customer_group = 'wholesale_tier_1'
ORDER BY p.ID ASC
LIMIT %d OFFSET %d",
$batchSize,
$offset
);
$rows = $this->db->get_results($query, ARRAY_A);
if (empty($rows)) {
break;
}
foreach ($rows as $row) {
yield $this->formatGoogleXmlNode($row);
}
$offset += $batchSize;
}
}
private function formatGoogleXmlNode(array $product): string
{
$price = number_format($product['price_cents'] / 100, 2, '.', '');
return sprintf(
"<item>\n <g:id>%d</g:id>\n <g:title><![CDATA[%s]]></g:title>\n <g:price>%s %s</g:price>\n <g:min_handling_time>1</g:min_handling_time>\n</item>\n",
$product['ID'],
htmlspecialchars($product['post_title'], ENT_QUOTES, 'UTF-8'),
$price,
$product['currency']
);
}
}Como solo hay en memoria un lote de 500 filas cada vez, el consumo depende del tamaño del lote y no del tamaño del catálogo. Programar la ejecución de los feeds mediante tareas en segundo plano en WP-CLI garantiza que el proceso de volcado no penalice la navegación de los clientes en tiempo real.
Para garantizar que los puntos de acceso de exportación y las APIs internas no presenten fisuras de seguridad, le recomendamos coordinar una sistemática auditoría de seguridad wordpress.
Modelado de datos semánticos con PriceSpecification y unitCode en schema.org
Reflejar con absoluta precisión los precios unitarios y los descuentos cuantitativos en el código de las fichas de producto resulta fundamental para el posicionamiento orgánico y la comprensión de los algoritmos de IA. Schema.org describe los precios unitarios mediante UnitPriceSpecification anidado en una oferta.
Conviene definir con nitidez las unidades métricas empleando la codificación internacional UN/CEFACT (como KGM para kilogramos, LTR para litros, MTK para metros cuadrados y C62 para unidades sueltas):
{
"@context": "https://schema.org",
"@type": "Product",
"name": "Adhesivo estructural de poliuretano, cubo de 5 kg",
"sku": "ADH-IND-500",
"offers": {
"@type": "Offer",
"price": "230.00",
"priceCurrency": "EUR",
"availability": "https://schema.org/InStock",
"priceSpecification": {
"@type": "UnitPriceSpecification",
"price": "230.00",
"priceCurrency": "EUR",
"referenceQuantity": {
"@type": "QuantitativeValue",
"value": 5,
"unitCode": "KGM",
"valueReference": {
"@type": "QuantitativeValue",
"value": 1,
"unitCode": "KGM"
}
}
}
}
}La documentación de fichas de comerciante de Google acota lo que permite Schema.org. Las fichas de comerciante necesitan un Offer, porque el comerciante tiene que ser el vendedor; AggregateOffer solo se acepta en fragmentos de producto. El precio unitario va en priceSpecification como UnitPriceSpecification, donde referenceQuantity es la cantidad vendida por ese precio y valueReference la cantidad base, los equivalentes en datos estructurados de unit_pricing_measure y unit_pricing_base_measure. En el ejemplo el cubo contiene 5 kg, así que el precio de 230 EUR equivale a 46 EUR por kilogramo. El único priceType que admite Google es StrikethroughPrice, los precios de socio usan validForMemberTier junto con un precio habitual, y una especificación que combine ambos se ignora. La página no menciona eligibleQuantity, de modo que no cabe esperar que los tramos por encima del precio de entrada aparezcan en los resultados de Google; el marcado transmite el precio de entrada, el mismo que el feed.
Estrategias de almacenamiento en caché periférica para tarifas mayoristas
Los sistemas convencionales de almacenamiento en caché de página completa (como Nginx FastCGI o Redis Page Cache) quedan invalidados en tiendas B2B cuando cada cuenta empresarial dispone de acuerdos de precio personalizados. Anular la caché para todos los visitantes autenticados colapsa los procesos del servidor y degrada el Time to First Byte (TTFB).
La solución técnica más ventajosa adopta un modelo híbrido en el borde de la red:
- Almacenamiento en caché del armazón estático: Las descripciones de catálogo, fotografías de alta definición y fichas técnicas se conservan cacheadas en los puntos de presencia de la CDN.
- Inyección asíncrona de tarifas: Al acceder a la página, el navegador del cliente corporativo ejecuta una consulta REST ligera para solicitar la matriz de precios correspondiente a su contrato.
- Actualización dinámica del DOM: Un componente en JavaScript reemplaza en el cliente los valores numéricos y recalcula los totales sin necesidad de invalidar la caché global.
En infraestructuras de envergadura comercial, la segregación de capas mediante arquitecturas avanzadas garantiza una solidez inigualable. Conozca nuestra propuesta especializada en el ámbito de headless wordpress.
Sincronización en tiempo real con ERP y consistencia transaccional
La correlación exacta de tarifas entre la tienda digital y Google Merchant Center depende de la agilidad en la sincronización con el sistema ERP central (como SAP, Microsoft Dynamics 365 o SAGE). Cuando se modifican los costes de materias primas o las tarifas generales en el ERP, estos valores deben volcarse de inmediato tanto en el portal web como en los canales publicitarios.
La arquitectura de enlace debe apoyarse en colas asíncronas de Action Scheduler y webhooks basados en eventos. Cualquier alteración de precio actualiza la tabla wp_wc_b2b_price_tiers y emite una actualización directa a través de la Merchant API de Google, sin aguardar a la compilación periódica del archivo XML completo.
La integración de procesos bidireccionales con registros en búfer previene bloqueos de concurrencia en la base de datos durante las fases punta de pedidos al por mayor, emitiendo avisos automáticos ante cualquier discordancia técnica.
Qué mapea Google for WooCommerce y qué exige un feed propio
La extensión oficial Google for WooCommerce cubre parte de esta configuración. Su mapeo de atributos admite 15 atributos de Google, entre ellos Multipack, Is Bundle, GTIN, MPN y Brand. Una regla puede aplicarse a todas las categorías, a todas salvo las seleccionadas o a una sola categoría. Las reglas solo rellenan atributos vacíos, y los valores definidos en la pestaña de Google de cada producto tienen prioridad. Las reglas leen únicamente atributos globales, de modo que los atributos creados en la ficha de un solo producto deben convertirse antes en globales.
La medida de precio unitario no figura en esa lista. Una tienda que vende por peso, volumen o superficie necesita valores por producto o una integración propia, por feed o por API, para unit_pricing_measure y unit_pricing_base_measure. Lo mismo ocurre con los productos por formato generados desde una tabla de tramos propia, que la extensión desconoce.
La capa de transporte cambió en 2026. Google indica que la Content API for Shopping se retiró el 18 de agosto de 2026, que las solicitudes empiezan a fallar de forma progresiva desde el 1 de septiembre de 2026 y remite a la Merchant API. Google for WooCommerce hizo el cambio en la versión 3.8.1. Una integración propia escribe productos mediante recursos ProductInput con insert, patch y delete, lee los recursos Product ya procesados y solo puede escribir en fuentes de datos de tipo API, como explica la guía de productos de la Merchant API.
Pruebas automatizadas y verificación continua de las reglas de cálculo
En el entorno B2B, los errores de cálculo en las tarifas escalonadas conllevan repercusiones económicas y normativas de gran gravedad. Publicar en Google Shopping precios divergentes de los aplicados finalmente en factura incumple las reglas de coincidencia de precios citadas arriba y puede acarrear rechazos de productos o la suspensión de la cuenta.
La verificación técnica exige la ejecución de pruebas automáticas en cada proceso de despliegue:
<?php
/**
* Pruebas de integracion para tarifas escalonadas y metrica unitaria b2b
*/
declare(strict_types=1);
namespace WPPoland\Tests\PricingES;
use PHPUnit\Framework\TestCase;
class TieredPricingCalculationTest extends TestCase
{
public function testEscaladoPorVolumenCorrecto(): void
{
$calculador = new \WPPoland\Pricing\TieredPriceCalculator();
// Producto con precio unitario base de 46 EUR y tramo de 33 EUR para 10 unidades
$tarifaIndividual = $calculador->resolveEffectivePrice(
productId: 5120,
quantity: 3,
customerGroup: 'wholesale_tier_1'
);
$this->assertEquals(4600, $tarifaIndividual, 'Cantidades por debajo del tramo deben liquidar el precio regular.');
$tarifaVolumen = $calculador->resolveEffectivePrice(
productId: 5120,
quantity: 14,
customerGroup: 'wholesale_tier_1'
);
$this->assertEquals(3300, $tarifaVolumen, 'Cantidades a partir de 10 unidades deben liquidar el precio bonificado.');
}
public function testValidacionParametrosMetricos(): void
{
$validador = new \WPPoland\B2BFeedsES\FeedAttributeValidator();
$medidaValida = $validador->validateUnitPricingAttributes(
measure: '25kg',
baseMeasure: '1kg'
);
$this->assertTrue($medidaValida, 'Las unidades de la lista admitida por Google deben aceptarse.');
$medidaInvalida = $validador->validateUnitPricingAttributes(
measure: '25bultos',
baseMeasure: 'contenedor'
);
$this->assertFalse($medidaInvalida, 'Las etiquetas genericas no normalizadas deben rechazarse.');
}
}Esta batería de comprobaciones elude imprecisiones en el redondeo de divisas y desfases fiscales antes de trasladar la información a las redes publicitarias.
Lista de comprobación técnica previa a la publicación en Google Shopping B2B
Lleve a cabo las siguientes comprobaciones antes de iniciar sus campañas B2B:
- Homologación de unidades de medida: Verifique que
unit_pricing_measureyunit_pricing_base_measureusan solo unidades de la lista admitida por Google y un valor base permitido. - Cálculo fiable en el carrito: Compruebe que la inclusión de volúmenes correspondientes a escalas superiores recalcula al instante el coste unitario del pedido.
- Precisión en códigos GTIN y MPN: Asegure que todos los lotes y presentaciones comerciales incorporan códigos de barras oficiales expedidos por GS1.
- Pruebas de estrés transaccional: Desarrolle pruebas de carga con miles de peticiones simultáneas sobre las tablas relacionales de tarifas.
- Validación estructural Schema.org: Compruebe las direcciones en la herramienta de prueba de resultados enriquecidos de Google para garantizar la corrección de
UnitPriceSpecification. - Consumo contenido de memoria en feeds: Corrobore que el pico de memoria PHP durante la exportación se mantiene plano aunque crezca el catálogo.
- Sistema de alertas de catálogo: Configure avisos sobre los rechazos que indiquen el diagnóstico de Merchant Center o la Merchant API.
- Protocolos de cifrado y seguridad: Exija TLS 1.3 y credenciales criptográficas seguras en todas las rutas de intercambio de tarifas.
- Reglas de distribución y transporte B2B: Configure en Merchant Center parámetros específicos para mercancías paletizadas y pedidos con importe mínimo.
- Interruptor de contingencia (Kill Switch): Implemente un mecanismo de respaldo que presente tarifas estáticas predeterminadas si fallan transitoriamente las conexiones con el ERP.
Una infraestructura de precios escalonados para el sector B2B requiere una adecuada correspondencia entre bases de datos transaccionales y las directrices de los motores de búsqueda. Si desea auditar o transformar sus sistemas de catálogo, póngase en contacto a través de nuestra página de contacto.







