From 51a8eaa36b73fe431f9f02543f3ada1860f60a00 Mon Sep 17 00:00:00 2001
From: bulat <bulat@1555416.no-reply.drupal.org>
Date: Mon, 17 Jun 2013 11:49:44 +0400
Subject: [PATCH] Issue #2021191 by bulat: Added support for LIKE and IN
 operators for flag name in EntityFieldQuery.

---
 flag.module     | 34 +++++++++++-----------
 tests/flag.test | 88 +++++++++++++++++++++++++++++++++++++++++++++++++++++++++
 2 files changed, 104 insertions(+), 18 deletions(-)

diff --git a/flag.module b/flag.module
index 8ca179e..a2b4ff1 100644
--- a/flag.module
+++ b/flag.module
@@ -142,30 +142,28 @@ function flagging_save($flagging) {
  *
  * Converts EntityFieldQuery instances on flaggings that have an entity
  * condition on bundles (flag machine names).
- *
- * Based on taxonomy_entity_query_alter().
  */
-function flag_entity_query_alter($query) {
+function flag_entity_query_alter(EntityFieldQuery $query) {
   $conditions = &$query->entityConditions;
-
+  
   // Alter only flagging queries with bundle conditions.
   if (isset($conditions['entity_type']) && $conditions['entity_type']['value'] == 'flagging' && isset($conditions['bundle'])) {
-    // Convert flag machine names to flag IDs.
-    $flags = flag_get_flags();
-    $fids = array();
-    if (is_array($conditions['bundle']['value'])) {
-      foreach ($conditions['bundle']['value'] as $flag_name) {
-        $fids[] = $flags[$flag_name]->fid;
-      }
-    }
-    else {
-      $flag_name = $conditions['bundle']['value'];
-      $fids = $flags[$flag_name]->fid;
-    }
-
-    $query->propertyCondition('fid', $fids, $conditions['bundle']['operator']);
+    $query->addMetaData('flag_name_value', $conditions['bundle']['value']);
+    $query->addMetaData('flag_name_operator', $conditions['bundle']['operator']);
+    $query->addTag('flagging_flag_names');
     unset($conditions['bundle']);
   }
+  
+}
+
+/**
+ * Implements hook_query_TAG_alter() for flagging_flag_names tag.
+ */
+function flag_query_flagging_flag_names_alter (QueryAlterableInterface $query) {
+    $value = $query->getMetaData('flag_name_value');
+    $operator = $query->getMetaData('flag_name_operator');
+    $query->join('flag', 'f', 'flagging.fid = f.fid');
+    $query->condition('f.name', $value, $operator);  
 }
 
 /**
diff --git a/tests/flag.test b/tests/flag.test
index 760fd32..b961e65 100644
--- a/tests/flag.test
+++ b/tests/flag.test
@@ -860,3 +860,91 @@ class FlagHookFlagAccessTestCase extends FlagTestCaseBase {
   }
 
 }
+
+class FlagEntityFieldQueryTestCase extends FlagTestCaseBase {
+  private $flag1;
+  public static function getInfo() {
+     return array(
+      'name' => t('Flagging Entity Field Query Extention'),
+      'description' => t('Entity Field Query for flagging entities.'),
+      'group' => t('Flag'),
+    );
+  }
+  
+  function setUp() {
+    parent::setUp('flag');
+    
+    $flag_data = array(
+      'entity_type' => 'node',
+      'name' => 'test_flag_1',
+      'title' => 'Test Flag',
+      'global' => 0,
+      'types' => array(
+        0 => 'article',
+      ),
+      'flag_short' => 'Flag this item',
+      'flag_long' => '',
+      'flag_message' => '',
+      'unflag_short' => 'Unflag this item',
+      'unflag_long' => '',
+      'unflag_message' => '',
+      'unflag_denied_text' => 'You may not unflag this item',
+      // Use the normal link type as it involves no intermediary page loads.
+      'link_type' => 'normal',
+      'weight' => 0,
+      'show_on_form' => 0,
+      'access_author' => '',
+      'show_contextual_link' => 0,
+      'show_in_links' => array(
+        'full' => 1,
+        'teaser' => 1,
+      ),
+      'i18n' => 0,
+      'api_version' => 3,
+    );
+    
+    $this->flag1 = $this->createFlag($flag_data);
+    $flag_data['name'] = 'test_flag_2';
+    $this->flag2 = $this->createFlag($flag_data);
+    $flag_data['name'] = 'test_flag_3';
+    $this->flag3 = $this->createFlag($flag_data);
+  
+    // Create test user who can flag and unflag.
+    $this->flag_unflag_user = $this->drupalCreateUser(array('flag test_flag_1', 'unflag test_flag_1', 'flag test_flag_2', 'unflag test_flag_2'));
+    $this->drupalLogin($this->flag_unflag_user);
+    
+  }
+  
+  function testEntityFieldQuery() {
+     $node_settings = array(
+      'title' => $this->randomName(),
+      'body' => array(LANGUAGE_NONE => array(array('value' => $this->randomName(32)))),
+      'uid' => 1,
+      'type' => 'article',
+      'is_new' => TRUE,
+    );
+    $node = $this->drupalCreateNode($node_settings);
+     
+    flag('flag', 'test_flag_1', $node->nid, $this->flag_unflag_user);
+    flag('flag', 'test_flag_2', $node->nid, $this->flag_unflag_user);
+    
+    $query = new EntityFieldQuery();
+    $query->entityCondition('entity_type', 'flagging')
+        ->entityCondition('bundle', 'test_flag_1');
+    
+    $flagged = $query->execute();
+    $this->assertEqual(count($flagged['flagging']), 1);    
+     
+    $query = new EntityFieldQuery();
+    $query->entityCondition('entity_type', 'flagging')
+        ->entityCondition('bundle', 'test%', 'like');
+    $flagged = $query->execute();
+    $this->assertEqual(count($flagged['flagging']), 2);  
+    
+    $query = new EntityFieldQuery();
+    $query->entityCondition('entity_type', 'flagging')
+        ->entityCondition('bundle', array('test_flag_1', 'test_flag_2'), 'IN');
+    $this->assertEqual(count($flagged['flagging']), 2);  
+  }
+  
+}
-- 
1.8.1.3

