Почему я должен использовать EntityFieldQuery, когда я могу сделать ту же работу с Db_select (), чтобы получить значение.
Было бы лучше, если бы кто-то мог привести пример, а не только ссылку.
Почему я должен использовать EntityFieldQuery, когда я могу сделать ту же работу с Db_select (), чтобы получить значение.
Было бы лучше, если бы кто-то мог привести пример, а не только ссылку.
Ответы:
Я думаю, что дело в том, что синтаксис намного проще, и код будет более понятным.
Например, если вы хотите, чтобы узлы с типом , чье my_type
поле имело значение field_foo
со значением $val
, с помощью Db_Select, yuoll делают что-то вроде:
$nids = db_select('node', 'n')
->fields('n', array('nid'))
->join('field_data_field_foo', 'foo', 'foo.entity_id = n.nid')
->condition('n.type', 'my_type')
->condition('foo.field_foo_value', $val)
->execute()->fetchCol();
Что намного проще с EntityFieldQuery:
$query = new EntityFieldQuery;
$entities = $query->entityCondition('entity_type', 'node')
->entityCondition('bundle', 'my_type')
->fieldCondition('field_foo', 'value', $val)
->execute();
Я думаю , что главная причина желаемая EntityFieldQuery
над db_select
том , что вы не должны знать о структуре нижнего уровня, другими словами: как материал хранится в базе данных. Это улучшает слабую связь .
EntityFieldQuery (EFQ) будет возвращать только идентификаторы сущностей. Если вы хотите получить доступ к данным сущностей, вам придется вызывать их entity_load()
, что, помимо загрузки данных, позволит убедиться, что все базовые вещи, которые вам обычно не нужны (такие как загрузка полей, вызов других модулей и т. Д.), Выполнены , Конечно, это приводит к двум запросам SQL и большим накладным расходам, но это цена, которую нужно заплатить за абстракцию.
Что касается синтаксиса EFQ, более понятного, я думаю, что это гораздо больше вопрос личных предпочтений. Я, например, не думаю, что EFQ понятнее. Обратите внимание, что рабочая db_select()
замена с EFQ должна включать проверку возвращаемого значения и последующий entity_load()
вызов, и это добавляет много шума в код, IMHO:
$query = new EntityFieldQuery();
$entities = $query->entityCondition('entity_type', 'node')
->entityCondition('bundle', 'my_type')
->fieldCondition('field_foo', 'value', $val)
->execute();
if (!empty($entities['node'])) {
$nodes = entity_load('node', array_keys($entities['node']));
} else {
$nodes = array();
}
Итак, отвечая на ваш вопрос: используйте EFQ, если ваши сущности являются полнофункциональными (например, могут использоваться в полевых условиях, могут использоваться другими модулями и т. Д.) И / или вы считаете, что его синтаксис более понятен. Если другие случаи, использование может использовать db_select()
.
entity_metadata_wrapper()
помогает здесь. Вам все еще нужно загрузить объект.
EntityFieldQuery гораздо более ограничен db_select()
, поэтому у вас должна быть действительно веская причина не использовать db_select()
(см. Ответ Барта), которая достаточно читабельна и гораздо более гибкая.
Например, entityFieldQuery
используйте innerJoin для извлечения полей. Если вам нужен левый джойн по какой-либо причине, вы попали в ловушку ...
http://drupal.org/node/1226622