एक EntityFieldQuery बनाएँ जो संदर्भित संस्थाओं का चयन करता है


10

मैं टाइप ए की इकाई की आईडी की तलाश कर रहा हूं और मुझे कंपनी बी की आईडी पता है कि संदर्भ ए।

मुझे EntityFieldQuery के बारे में कुछ अच्छे स्रोत मिले। मैं चकित था कि मुझे google में .NET से परिणाम मिल रहे थे :) (क्या यह द्रुपाल की परिपक्वता का संकेत है? :)। लेकिन यह पता लगाने के लिए प्रबंधन नहीं किया। कृपया सहायता कीजिए ...

कुछ स्रोत:

यह इकाई भार के साथ जैसा दिखता है - आप समझेंगे कि मुझे उस क्वेरी की आवश्यकता है :) मुख्य रूप से अभ्यास के लिए रैपर है। ध्यान दें कि यह लक्ष्य इकाई को लोड करता है - काफी क्वेरीज़।

  $b = entity_load('B', array($id));
  $bm = entity_metadata_wrapper('B', $sl[$id]);

  $tsl = $slm->field_sl_tpref->value();
  echo $tsl->id;

1
एक EntityFieldQueryसंस्था के केवल एक सेट को संदर्भित कर सकता है, यह दुर्भाग्य से अन्य संस्थाओं के लिए संबंध नहीं बना सकता है। यह एक समय में केवल एक प्रकार की इकाई को वापस कर सकता है, भले ही आप इन रिश्तों को बना सकें लेकिन परिणाम अविश्वसनीय होंगे।
क्लाइव

@ क्या आप इसे एक उत्तर के रूप में जोड़ना चाहेंगे, इसलिए मैं इसकी पुष्टि कर सकता हूं? धन्यवाद :)
mojzis

जवाबों:


15

आप संदर्भित संस्थाओं की आईडी के आधार पर संस्थाओं को पुनः प्राप्त करने के target_idबजाय उपयोग कर सकते हैं value:

$query = new EntityFieldQuery();
$query->entityCondition('entity_type', <type-of-the-entity>);
$query->fieldCondition('<name-of-the-field-referring-the-other-entity>', 'target_id', <id-of-the-referenced-entity>, '=');
$results = $query->execute();

धन्यवाद, लेकिन मुझे नहीं लगता है कि मैं क्या देख रहा था ... मैं दूसरी दिशा प्राप्त करने की कोशिश कर रहा था, इस तरह से आप A को जानेंगे और B की तलाश करेंगे :)
mojzis

2

गलत है, क्या संबंध मॉड्यूल है जिसे आप खोज रहे हैं? ऐसा लगता है कि एक्स और वाई संस्थाओं के बीच संबंधों को परिभाषित करना है जिसे आप टूडू चाहते हैं। इस तरह की जानकारी आसानी से प्राप्त करने के लिए इसका अपना RelationQuery (EFQ के आसपास एक आवरण) और RelationQueryEndpoint है।


धन्यवाद। दुर्भाग्य से मैं पहले से ही उद्यमशीलता के साथ कुछ संबंधों को परिभाषित कर चुका हूं, इसलिए संबंध पर स्विच करना समस्याग्रस्त होगा ... अगली बार कोशिश करेंगे :)।
मोजजिस

2

मुझे पता है कि यह एक पुराना सवाल है, लेकिन लोगों से यह जानने के लिए कि मुझे लगता है कि मैं यहां एक और दृष्टिकोण फेंक दूंगा।

सेटअप के ऊपर के विवरण में 2 इकाई प्रकार हैं, ए और बी। इसलिए यदि आपके पास B की आईडी है तो आपके पास डेटाबेस में संग्रहीत A की ID के साथ एक फ़ील्ड होना चाहिए।

कोड नोट्स:

  • मूल एनआईडी - $original_node->nidयह बी की आईडी होगी
  • बंडल प्रकार - $typeयह ए का प्रकार होना चाहिए
  • क्षेत्र की स्थिति सिर्फ उस क्षेत्र की तलाश करती है जो संदर्भ रखता है
  • EFQ का उपयोग कैसे करें के बारे में अधिक जानकारी के लिए इसे देखें

कोड

// Start a new EFQ
$query = new EntityFieldQuery();

// Define query, the user load is probably not needed but sometimes is.
$query->entityCondition('entity_type', 'node')
      ->entityCondition('bundle', $type)
      ->fieldCondition('field_NAME_OF_FIELD', 'target_id', $original_node->nid, '=')
      ->addMetaData('account', user_load(1));

// Execute query, result with have node key
$result = $query->execute();

// If results it will be in node key
if (isset($result['node'])) {
  $nids = array_keys($result['node']);
  // This example has multiple nodes being referenced by one node
  $nodes = node_load_multiple($nids, array('type' => $type));
  // Devel module needed
  dpm($nodes);
}

आप दो तरह के इकाई संदर्भ भी सेट कर सकते हैं और पीछे की तरफ एक ही क्वेरी कर सकते हैं। आप CER जैसे मॉड्यूल का उपयोग यह सुनिश्चित करने के लिए कर सकते हैं कि उन संदर्भों को अद्यतित रखा गया है। या संदर्भ को अद्यतन रखने के लिए एक नियम सेट करें, मैंने दोनों का उपयोग किया है।


यदि field_NAME_OF_FIELD बहु fieldCondition('field_NAME_OF_FIELD', 'target_id', $original_node->nid, '=')कार्य है तो क्या होगा ? इसे बदल दिया जाना चाहिए fieldCondition('field_NAME_OF_FIELD', 'target_id', array($original_node->nid), 'IN')। बहुसंख्‍यक प्रतिश्रेणी क्षेत्र पर स्थिति कैसे लागू की जाए, इसके बारे में कुछ भी पता नहीं लगा सका। कोई उपाय?
किरकिंग

1
मैं यह एक पुरानी टिप्पणी जानता हूं, लेकिन यदि आप EntityFieldQuery चूक को IN में ऐसे फील्डकंडिशन ('field_NAME_OF_FIELD', 'target_id', $ original_node-> nid से छोड़ते हैं) तो वास्तव में उस स्थिति में काम नहीं करेगा। आप शायद पहले से ही जानते हैं कि अभी तक लेकिन बाद में किसी और को ठोकर
मारते हैं

1

एक काफी गतिशील समाधान (थोड़ा गंदा भी है लेकिन मुझे इसकी जल्दी जरूरत है) इसलिए आपको संदर्भ क्षेत्र के लिए हार्ड कोड नाम की आवश्यकता नहीं है और इसे भविष्य में आपके द्वारा जोड़े जाने वाले नए संदर्भ क्षेत्र के साथ स्वचालित रूप से नियंत्रित किया जाएगा:

अपने कस्टम मॉड्यूल में:

/**
 * Implement hook_field_create_instance().
 */
function MY_CUSTOM_MODULE_field_create_instance() {
  _MY_CUSTOM_MODULE_set_variable_node_back_references();
}

/**
 * Implement hook_field_delete_field().
 */
function MY_CUSTOM_MODULE_field_delete_field() {
  _MY_CUSTOM_MODULE_set_variable_node_back_references();
}

/**
 * Set Variable node_back_references.
 */
function _MY_CUSTOM_MODULE_set_variable_node_back_references() {
  $field_list = db_select('field_config', 'fc')
    ->fields('fc', array('field_name', 'data'))
    ->condition('fc.data', '%"foreign keys";a:1:{s:4:"node"%', 'like')
    ->condition('fc.deleted', 0);
  $field_list->innerJoin('field_config_instance', 'fci', 'fci.field_name = fc.field_name');
  $field_list->rightJoin('node_type', 'n', 'n.type = fci.bundle');
  $fields = $field_list->execute()->fetchAll();

  $fields_array = array();
  foreach ($fields as $field) {
    $unserialized = unserialize($field->data);
    if (isset($unserialized['settings']['handler_settings']['target_bundles'])) {
      foreach ($unserialized['settings']['handler_settings']['target_bundles'] as $bundle) {
        $fields_array[$bundle][] = $field->field_name;
      }
    }
  }

  variable_set('node_back_references', $fields_array);
}

function _MY_CUSTOM_MODULE_get_referencing_nodes($node) {
  $nids = array();
  $fields = variable_get('node_back_references', array());
  if (isset($fields[$node->type])) {
    foreach ($fields[$node->type] as $field) {
      $query = new \EntityFieldQuery();
      $query->entityCondition('entity_type', 'node');
      $query->propertyCondition('status', 1);
      $query->fieldCondition($field, 'target_id', $node->nid);
      $result = $query->execute();
      $nids = isset($result['node']) ? array_merge(array_keys($result['node']), $nids) : $nids;
    }
    $nodes = (!empty($nids)) ? node_load_multiple($nids) : array();

    return $nodes;
  }

  return $nids;
}

जहां आपको बच्चे को दिए गए माता-पिता के नोड्स प्राप्त करने की आवश्यकता है:

$nodes = _MY_CUSTOM_MODULE_get_referencing_nodes($node);
हमारी साइट का प्रयोग करके, आप स्वीकार करते हैं कि आपने हमारी Cookie Policy और निजता नीति को पढ़ और समझा लिया है।
Licensed under cc by-sa 3.0 with attribution required.