entityQuery con múltiples condiciones en términos de taxonomía no devuelve ningún resultado

13

En mi caso de uso, tengo una entidad que tiene dos campos que hacen referencia a vocabularios únicos.

Noticias: - etiqueta (referencia de entidad) - categoría (referencia de entidad)

Si consulto sobre una de esas referencias, obtengo resultados; sin embargo, cuando consulto ambos (un filtro AND) no obtengo resultados. Ya lo he verificado tres veces y hay entidades que contienen tanto la etiqueta como la categoría que estoy consultando.

¿Es esto un error del usuario o un error de Drupal?

$query = \Drupal::entityQuery('node')
    ->condition('status', 1)
    ->condition('type', 'news')
;
$group = $query->andConditionGroup()
    ->condition('field_tag.entity.name', ['cars'], 'IN')
    ->condition('field_category.entity.name', ['sport'], 'IN')
;
$query->condition($group);
$nids = $query->execute();

EDITAR: He encontrado una solución al consultar el valor bruto en lugar de entity.value. Sin embargo, esta es una situación no deseable

$query = \Drupal::entityQuery('node')
    ->condition('status', 1)
    ->condition('type', 'news')
;
$group = $query->andConditionGroup()
    ->condition('field_tag.entity.name', ['cars'], 'IN')
    ->condition('field_category', [1], 'IN')
;
$query->condition($group);
$nids = $query->execute();
Codificador incompleto
fuente
La conjunción predeterminada para EQ es AND (que puede cambiar), por lo que no hay nada de malo en agrupar las condiciones ... es por eso que está ahí. No entiendo lo que esperabas?

Respuestas:

8

La razón por la que no puede hacer eso es que ambos campos son referencias de entidad a la misma entidad. Eso significa que la tabla base es la misma tabla base.

Le está pidiendo a Drupal que una la tabla taxonomy_data a la tabla de nodos y luego haga una condición AND imposible en ella.

PD

Puedes usar en condition('field_tags', 1);lugar decondition('field_tags', [1], 'IN');

Y como se menciona en los comentarios, el grupo de condiciones AND es el predeterminado, por lo que no necesita especificarlo.

PPS

Debe hacer que ambas condiciones usen la identificación referenciada para ser coherente.

Eyal
fuente
1
Esta respuesta solo cubre una imaginación ingenua de cómo podría funcionar la consulta de entidad. Sin embargo, es mucho, mucho más capaz que esto. Mira mi respuesta.
3

Una suposición salvaje y no probada:

$query = \Drupal::entityQuery('node')
  ->condition('status', 1)
  ->condition('type', 'news');

$query = $query->condition($query->andConditionGroup()->condition('field_tag.entity.name', ['cars'], 'IN'))
  ->condition($query->andConditionGroup()->condition('field_category.entity.name', ['sport'], 'IN'));

Si esto no funciona, búscame en IRC # drupal-contrib la próxima semana y llegaremos al final.

Tim Yao
fuente
Esto debería solucionarse en Drupal Core pero la solución anterior funciona.
Mr.B
1

En realidad encontré un truco para esto. Aquí está mi explicación de lo que he encontrado:

Tenía 3 campos en mi tipo de contenido, cada uno con una referencia a un término de taxonomía de diferentes vocabularios. Y quería consultar a las entidades para aquellas que tienen un término de taxonomía específico en cada uno de esos 3 campos (una y condición).

comprobando la consulta SQL interna que se produce después de varios intentos con diferentes combinaciones de condiciones, encontré que

[Previous conditions] AND (taxonomy_term__[taxonomy_term_field_name] IN  (:db_condition_placeholder_2)) AND (taxonomy_term__[taxonomy_term_field_name] IN  (:db_condition_placeholder_3)) AND (taxonomy_term__[taxonomy_term_field_name] IN  (:db_condition_placeholder_4))

básicamente, como puede ver, no tiene referencia a los campos individuales reales que usan ese vocabulario específico, por lo que mi truco es hacer algo como esto:

 $query = \Drupal::entityQuery('node')
            ->condition('status', '1')
            ->condition('type', $content_type_machine_name)
            ->condition('field_holding_term_ref.entity.name', array($label_of_term_in_field1, $label_of_term_in_field2, $label_of_term_in_field3), 'IN');

De nuevo, esto funciona, lo he probado y funciona como una condición AND que devuelve solo el tipo de contenido con esos 3 términos de taxonomía, incluso si las referencias a esos términos de taxonomía se almacenan en diferentes campos en el tipo de contenido.

No estoy orgulloso del truco, pero funciona, así que si esto puede ayudar a alguien a ahorrar en algún momento, adelante.

Elias
fuente