---
title: Queries y datos en multitienda
section: multistore
slug: queries
description: "Queries SQL en contexto multitienda: filtrar por tienda, Configuration::get con id_shop, ObjectModel y datos compartidos."
keywords: prestashop multitienda queries SQL id_shop configuration objectmodel datos compartidos
last_updated: 2024-12-01
source_url: "https://ayudaprestashop.es/multistore/queries"
---

# Queries y datos en multitienda

> Queries SQL en contexto multitienda: filtrar por tienda, Configuration::get con id_shop, ObjectModel y datos compartidos.

En multitienda, cada query debe considerar el contexto de tienda. Un modulo que funciona en tienda unica puede fallar en multitienda si no filtra correctamente por id_shop.

## Configuration en multitienda

*Leer y escribir configuracion por tienda*

```php
<?php

// ── Configuration::get() respeta el contexto de tienda automaticamente ──
$valor = Configuration::get('MI_MODULO_OPCION');
// Busca en: tienda actual → grupo de tiendas → global

// ── Leer valor de una tienda especifica ──
$valorTienda2 = Configuration::get('MI_MODULO_OPCION', null, null, 2);
// Firma: get($key, $id_lang = null, $id_shop_group = null, $id_shop = null)

// ── Escribir valor para la tienda actual ──
Configuration::updateValue('MI_MODULO_OPCION', 'valor');
// Guarda en ps_configuration con id_shop = tienda actual

// ── Escribir valor global (todas las tiendas) ──
Configuration::updateGlobalValue('MI_MODULO_OPCION', 'valor_global');
// id_shop = 0, id_shop_group = 0

// ── Escribir valor para tienda especifica ──
$oldShop = Shop::getContext();
Shop::setContext(Shop::CONTEXT_SHOP, 2);
Configuration::updateValue('MI_MODULO_OPCION', 'valor_tienda_2');
Shop::setContext($oldShop);

// ── Eliminar configuracion por tienda ──
Configuration::deleteByName('MI_MODULO_OPCION');
// Elimina de TODAS las tiendas
```

## ObjectModel y id_shop

*ObjectModel en contexto multitienda*

```php
<?php

// ── ObjectModel con multishop ──
// En la definicion de la clase:
class MyEntity extends ObjectModel
{
    public static $definition = [
        'table'     => 'mymodule_entity',
        'primary'   => 'id_mymodule_entity',
        'multilang' => true,
        'multishop' => true,  // ← Habilitar multitienda
        'fields'    => [
            'active' => ['type' => self::TYPE_BOOL, 'shop' => true],
            // 'shop' => true → este campo se guarda POR tienda
            // 'shop' => false o ausente → campo global
            'name'   => ['type' => self::TYPE_STRING, 'lang' => true, 'shop' => true],
            'config' => ['type' => self::TYPE_STRING, 'shop' => false], // Global
        ],
    ];
}

// Cuando multishop = true, PS crea automaticamente:
// ps_mymodule_entity          (datos globales)
// ps_mymodule_entity_shop     (datos por tienda)
// ps_mymodule_entity_lang     (si multilang)

// ── Guardar asociacion con tienda ──
$entity = new MyEntity();
$entity->active = true;
$entity->name   = 'Mi entidad';
$entity->id_shop_list = [1, 2]; // Asociar a tiendas 1 y 2
$entity->add();

// ── Leer filtrando por tienda ──
$entity = new MyEntity($id); // Usa la tienda actual del contexto
```

## Queries con filtro de tienda

*Filtrar queries por id_shop*

```php
<?php

// ── Obtener id_shop actual ──
$idShop = (int) Context::getContext()->shop->id;

// ── Query filtrada por tienda ──
$results = Db::getInstance()->executeS(
    (new DbQuery())
        ->select('e.*, es.active')
        ->from('mymodule_entity', 'e')
        ->innerJoin('mymodule_entity_shop', 'es',
            'e.id_mymodule_entity = es.id_mymodule_entity AND es.id_shop = ' . $idShop)
        ->where('es.active = 1')
        ->orderBy('e.position ASC')
);

// ── Con Shop::addSqlRestriction (metodo recomendado) ──
$sql = 'SELECT p.*, ps.active, ps.price
        FROM `' . _DB_PREFIX_ . 'product` p
        ' . Shop::addSqlAssociation('product', 'p') . '
        WHERE ps.active = 1';
// addSqlAssociation genera:
// INNER JOIN ps_product_shop ps ON p.id_product = ps.id_product
//   AND ps.id_shop IN (tiendas del contexto actual)

// ── Para tablas custom, usar Shop::addSqlRestriction ──
$sql = 'SELECT * FROM `' . _DB_PREFIX_ . 'mymodule_data` md
        WHERE 1 ' . Shop::addSqlRestriction(false, 'md');
// Añade: AND md.id_shop = X (o IN (X, Y) segun contexto)
```

## Datos compartidos vs por tienda

| Dato | Compartido | Por tienda | Recomendacion |
| --- | --- | --- | --- |
| Producto (base) | Si | Precio, stock, activo | Crear producto una vez, personalizar por tienda |
| Categoria | Si (estructura) | Nombre, desc, activo | Misma estructura, contenido diferente |
| Cliente | Configurable | Configurable | Compartir clientes entre tiendas es lo habitual |
| Pedido | No | Si (pertenece a una tienda) | Cada pedido es de una tienda especifica |
| Transportista | No | Si | Diferentes transportistas por tienda |
| CMS Page | Si (ID) | Contenido por tienda | Misma pagina, diferente contenido |
| Modulo config | Depende | Depende | Usar Configuration con id_shop |


---

*Fuente: [https://ayudaprestashop.es/multistore/queries](https://ayudaprestashop.es/multistore/queries). Version Markdown generada automaticamente para consumo por LLMs.*
