/**
  * Build an EntityFieldQuery to get referencable entities.
  */
 public function buildEntityFieldQuery($match = NULL, $match_operator = 'CONTAINS')
 {
     global $user;
     $handler = EntityReference_SelectionHandler_Generic::getInstance($this->field, $this->instance, $this->entity_type, $this->entity);
     $query = $handler->buildEntityFieldQuery($match, $match_operator);
     // FIXME: http://drupal.org/node/1325628
     unset($query->tags['node_access']);
     // FIXME: drupal.org/node/1413108
     unset($query->tags['entityreference']);
     $query->addTag('entity_field_access');
     $query->addTag('og');
     $group_type = $this->field['settings']['target_type'];
     $entity_info = entity_get_info($group_type);
     if (!field_info_field(OG_GROUP_FIELD)) {
         // There are no groups, so falsify query.
         $query->propertyCondition($entity_info['entity keys']['id'], -1, '=');
         return $query;
     }
     // Show only the entities that are active groups.
     $query->fieldCondition(OG_GROUP_FIELD, 'value', 1, '=');
     if (empty($this->instance['field_mode'])) {
         return $query;
     }
     $field_mode = $this->instance['field_mode'];
     if ($field_mode == 'default' || $field_mode == 'admin') {
         $user_groups = oa_core_get_groups_by_user(NULL, $group_type);
         $user_groups = array_merge($user_groups, $this->getGidsForCreate());
         // This is a workaround for not being able to choice which default value for
         // 'my groups', which causes my groups to be lost.
         // @todo find a way to default my groups based on selection handler.
         $user_groups_only = og_get_entity_groups();
         $user_groups_only = !empty($user_groups_only['node']) ? $user_groups_only['node'] : array();
         // Show the user only the groups they belong to.
         if ($field_mode == 'default') {
             if ($user_groups && !empty($this->instance) && $this->instance['entity_type'] == 'node') {
                 // Determine which groups should be selectable.
                 $node = $this->entity;
                 $node_type = $this->instance['bundle'];
                 $has_create_access = array_keys(array_filter(oa_user_access_nids('node', $user_groups, "create {$node_type} content")));
                 $has_update_access = array();
                 $remaining = array_diff($user_groups, $has_create_access);
                 if (!empty($node->nid) && $remaining) {
                     $groups = og_get_entity_groups('node', $node->nid);
                     $node_groups = !empty($groups['node']) ? $groups['node'] : array();
                     if ($node_groups = array_diff($node_groups, $remaining)) {
                         $check_perms = array("update any {$node_type} content");
                         if ($user->uid == $node->uid) {
                             $check_perms = "update own {$node_type} content";
                         }
                         $has_update_access = array_keys(array_filter(oa_user_access_nids('node', $node_groups, $check_perms)));
                     }
                 }
                 $ids = array_merge($has_update_access, $has_create_access);
             } else {
                 $ids = $user_groups;
             }
             if ($ids) {
                 $query->propertyCondition($entity_info['entity keys']['id'], $ids, 'IN');
             } else {
                 // User doesn't have permission to select any group so falsify this
                 // query.
                 $query->propertyCondition($entity_info['entity keys']['id'], -1, '=');
             }
         } elseif ($field_mode == 'admin' && $user_groups_only) {
             // Show only groups the user doesn't belong to.
             if (!empty($this->instance) && $this->instance['entity_type'] == 'node') {
                 // Don't include the groups, the user doesn't have create
                 // permission.
                 $node_type = $this->instance['bundle'];
                 foreach ($user_groups_only as $delta => $gid) {
                     if (!og_user_access($group_type, $gid, "create {$node_type} content")) {
                         unset($user_groups_only[$delta]);
                     }
                 }
             }
             if ($user_groups) {
                 $query->propertyCondition($entity_info['entity keys']['id'], $user_groups_only, 'NOT IN');
             }
         }
     }
     return $query;
 }
 /**
  * Build an EntityFieldQuery to get referencable entities.
  */
 public function buildEntityFieldQuery($match = NULL, $match_operator = 'CONTAINS')
 {
     global $user;
     $handler = EntityReference_SelectionHandler_Generic::getInstance($this->field, $this->instance, $this->entity_type, $this->entity);
     $query = $handler->buildEntityFieldQuery($match, $match_operator);
     // FIXME: http://drupal.org/node/1325628
     unset($query->tags['node_access']);
     // FIXME: drupal.org/node/1413108
     unset($query->tags['entityreference']);
     $query->addTag('entity_field_access');
     $query->addTag('og');
     $group_type = $this->field['settings']['target_type'];
     $entity_info = entity_get_info($group_type);
     if (!field_info_field(OG_GROUP_FIELD)) {
         // There are no groups, so falsify query.
         $query->propertyCondition($entity_info['entity keys']['id'], -1, '=');
         return $query;
     }
     // Show only the entities that are active groups.
     $query->fieldCondition(OG_GROUP_FIELD, 'value', 1, '=');
     if (empty($this->instance['field_mode'])) {
         return $query;
     }
     $field_mode = $this->instance['field_mode'];
     $user_groups = oa_core_get_groups_by_user(NULL, $group_type);
     $user_groups = array_merge($user_groups, $this->getGidsForCreate());
     // Show the user only the groups they belong to.
     if ($field_mode == 'default') {
         if ($user_groups && !empty($this->instance) && $this->instance['entity_type'] == 'node') {
             // Determine which groups should be selectable.
             $node = $this->entity;
             $node_type = $this->instance['bundle'];
             $ids = array();
             foreach ($user_groups as $gid) {
                 // Check if user has "create" permissions on those groups.
                 // If the user doesn't have create permission, check if perhaps the
                 // content already exists and the user has edit permission.
                 if (og_user_access($group_type, $gid, "create {$node_type} content")) {
                     $ids[] = $gid;
                 } elseif (!empty($node->nid) && (og_user_access($group_type, $gid, "update any {$node_type} content") || $user->uid == $node->uid && og_user_access($group_type, $gid, "update own {$node_type} content"))) {
                     $node_groups = isset($node_groups) ? $node_groups : og_get_entity_groups('node', $node->nid);
                     if (in_array($gid, $node_groups['node'])) {
                         $ids[] = $gid;
                     }
                 }
             }
         } else {
             $ids = $user_groups;
         }
         if ($ids) {
             $query->propertyCondition($entity_info['entity keys']['id'], $ids, 'IN');
         } else {
             // User doesn't have permission to select any group so falsify this
             // query.
             $query->propertyCondition($entity_info['entity keys']['id'], -1, '=');
         }
     } elseif ($field_mode == 'admin' && $user_groups) {
         // Show only groups the user doesn't belong to.
         if (!empty($this->instance) && $this->instance['entity_type'] == 'node') {
             // Don't include the groups, the user doesn't have create
             // permission.
             $node_type = $this->instance['bundle'];
             foreach ($user_groups as $delta => $gid) {
                 if (!og_user_access($group_type, $gid, "create {$node_type} content")) {
                     unset($user_groups[$delta]);
                 }
             }
         }
         if ($user_groups) {
             $query->propertyCondition($entity_info['entity keys']['id'], $user_groups, 'NOT IN');
         }
     }
     return $query;
 }