Commit 7c732275 authored by borisson_'s avatar borisson_ Committed by borisson_

Issue #2772745 by borisson_, dermario, drunken monkey, jespermb, StryKaizer,...

Issue #2772745 by borisson_, dermario, drunken monkey, jespermb, StryKaizer, swentel, Nick_vh: Search API integration doesn't check/define feature support of backends
parent ed31ddef
CONTENTS OF THIS FILE
---------------------
* Introduction
* Requirements
* Installation
* Configuration
* FAQ
INTRODUCTION
------------
Todo
REQUIREMENTS
------------
No other modules required, we're supporting drupal core as a source for creating
......@@ -19,7 +14,7 @@ tested.
INSTALLATION
------------
* Install as you would normally install a contributed drupal module. See:
https://drupal.org/documentation/install/modules-themes/modules-7
https://www.drupal.org/docs/8/extending-drupal-8/installing-contributed-modules-find-import-enable-configure-drupal-8
for further information.
CONFIGURATION
......@@ -40,3 +35,68 @@ FAQ
Q: Why do the facets disappear after a refresh.
A: We don't support cached views, change the view to disable caching.
FEATURES
--------
If you are the developer of a search api backend implementation and want
to support facets with your service class, too, you'll have to support the
"search_api_facets" feature. In short, you'll just have to return facet terms
and counts according to the query's "search_api_facets" option, when executing a
query.
In order for the module to be able to tell that your server supports facets,
you will also have to change your service's supportsFeature() method to
something like the following:
```
public function getSupportedFeatures() {
return ['search_api_facets'];
}
```
If you don't do that, there's no way for the facet source to pick up facets.
The "search_api_facets" option looks as follows:
```
$query->setOption('search_api_facets', [
$facet_id => [
// The Search API field ID of the field to facet on.
'field' => (string),
// The maximum number of filters to retrieve for the facet.
'limit' => (int),
// The facet operator: "and" or "or".
'operator' => (string),
// The minimum count a filter/value must have to be returned.
'min_count' => (int),
// Whether to retrieve a facet for "missing" values.
'missing' => (bool),
],
// …
]);
```
The structure of the returned facets array should look like this:
```
$results->setExtraData('search_api_facets', [
$facet_id => [
[
'count' => (int),
'filter' => (string),
],
// …
],
// …
]);
```
A filter is a string with one of the following forms:
- `"VALUE"`: Filter by the literal value VALUE (always include the quotes, not
only for strings).
- `[VALUE1 VALUE2]`: Filter for a value between VALUE1 and VALUE2. Use
parantheses for excluding the border values and square brackets for including
them. An asterisk (*) can be used as a wildcard. E.g., (* 0) or [* 0) would be
a filter for all negative values.
- `!`: Filter for items without a value for this field (i.e., the "missing"
facet).
<?php
/**
* @file
* Update hooks for the facets module.
*/
use Drupal\facets\Entity\Facet;
use Drupal\facets\Entity\FacetSource;
/**
* Convert facets on Search Api facet sources to use the display plugin.
*/
function facets_update_8001() {
// We changed the way we work with search api facet sources, we're now using
// the SearchApiDisplay plugins that search api ships with. This consolidates
// the external points for facets, sorts, autocomplete and others. This
// refactor made us a better member of the Search API family. It also makes it
// easier for other modules that provide a display to support facets, for
// example, for the search_api_page module.
//
// This only works for the 3 default plugins that we previously shipped. So
// only views that have a page, block, or rest display. The id will get
// replaced from views_page:foo to search_api:views_page__foo.
$old_ids = ['views_page', 'views_block', 'views_rest'];
/** @var \Drupal\facets\FacetInterface[] $entities */
$entities = Facet::loadMultiple();
foreach ($entities as $entity) {
$facetSourceId = $entity->getFacetSourceId();
foreach ($old_ids as $id) {
if (strpos($facetSourceId, $id) !== FALSE) {
$new_id = str_replace($id . ':', 'search_api:' . $id . '__', $facetSourceId);
$entity->setFacetSourceId($new_id);
$entity->save();
}
}
}
/** @var \Drupal\facets\FacetSourceInterface[] $facetsources */
$facetsources = FacetSource::loadMultiple();
foreach ($facetsources as $facetsource) {
$as_array = $facetsource->toArray();
// Replace id and name to new naming scheme.
foreach ($old_ids as $id) {
if (strpos($as_array['id'], $id) !== FALSE) {
$as_array['id'] = str_replace($id . '__', 'search_api__' . $id . '__', $as_array['id']);
$as_array['name'] = str_replace($id . ':', 'search_api:' . $id . '__', $as_array['name']);
}
}
// Create new source.
FacetSource::create($as_array)->save();
// Delete old facet source.
$facetsource->delete();
}
}
......@@ -59,10 +59,14 @@ function facets_search_api_query_alter(QueryInterface &$query) {
/** @var \Drupal\facets\FacetManager\DefaultFacetManager $facet_manager */
$facet_manager = \Drupal::service('facets.manager');
$search_id = $query->getSearchId();
// It's safe to hardcode this to the search api scheme because this is in a
// search_api_query_alter method. If this generated source is not correct,
// implementing the same alter and directly calling
// $manager->alterQuery($query, $your_facetsource_id); will fix that.
$facet_source = 'search_api:' . str_replace(':', '__', $query->getSearchId());
// Add the active filters.
$facet_manager->alterQuery($query, $search_id);
$facet_manager->alterQuery($query, $facet_source);
}
}
......@@ -88,7 +92,7 @@ function facets_entity_presave(EntityInterface $entity) {
// Check if the current display is also a facet source plugin and that
// is removed from the view. We use the double underscore here to make
// sure that we use core convention of "plugin:derived_plugin".
$facets_source_plugin_id = 'views_page:' . $entity->id() . '__' . $display['id'];
$facets_source_plugin_id = 'search_api:views_' . $display['display_plugin'] . '__' . $entity->id() . '__' . $display['id'];
if (array_key_exists($facets_source_plugin_id, $definitions) && !array_key_exists($k, $entity->get('display'))) {
$entity_id = str_replace(':', '__', $facets_source_plugin_id);
$source_entity = FacetSource::load($entity_id);
......@@ -99,7 +103,6 @@ function facets_entity_presave(EntityInterface $entity) {
}
}
// Loop over all deleted sources and delete the facets that were linked to
// that source.
if (count($sources) > 0) {
......@@ -152,7 +155,7 @@ function facets_entity_predelete(EntityInterface $entity) {
}
foreach ($definitions as $plugin_id => $definition) {
if (strpos($plugin_id, 'views_page:' . $entity->id() . '__') !== FALSE) {
if (strpos($plugin_id, 'search_api:' . $entity->id() . '__') !== FALSE) {
try {
$facetManager = \Drupal::getContainer()->get('facets.manager');
} catch (ServiceNotFoundException $e) {
......
......@@ -3,6 +3,7 @@
namespace Drupal\core_search_facets\Plugin\facets\facet_source;
use Drupal\Core\Form\FormStateInterface;
use Drupal\Core\Url;
use Drupal\core_search_facets\Plugin\CoreSearchFacetSourceInterface;
use Drupal\facets\FacetInterface;
use Drupal\facets\FacetSource\FacetSourcePluginBase;
......@@ -110,9 +111,9 @@ class CoreNodeSearchFacetSource extends FacetSourcePluginBase implements CoreSea
public function getPath() {
$search_page = $this->request->attributes->get('entity');
if ($search_page instanceof SearchPageInterface) {
return '/search/' . $search_page->getPath();
return Url::fromUserInput('/search/' . $search_page->getPath());
}
return '/';
return Url::fromUserInput('/');
}
/**
......
......@@ -67,9 +67,9 @@ class CoreNodeSearchFacetSourceDeriver extends FacetSourceDeriverBase {
'id' => $base_plugin_id . PluginBase::DERIVATIVE_SEPARATOR . $machine_name,
'label' => $this->t('Core Search Page: %page_name', ['%page_name' => $page->get('label')]),
'description' => $this->t('Provides a facet source.'),
'display_id' => $machine_name,
] + $base_plugin_definition;
}
uasort($plugin_derivatives, array($this, 'compareDerivatives'));
$this->derivatives[$base_plugin_id] = $plugin_derivatives;
}
......
<?php
/**
* @file
* Update hooks for the facets summary module.
*/
use Drupal\facets_summary\Entity\FacetsSummary;
/**
* Convert summaries on Search Api facet sources to use the display plugin.
*/
function facets_summary_update_8001() {
/** @var \Drupal\facets_summary\FacetsSummaryInterface[] $entities */
$entities = FacetsSummary::loadMultiple();
foreach ($entities as $entity) {
$facetSourceId = $entity->getFacetSourceId();
$old_ids = ['views_page', 'views_block', 'views_rest'];
foreach ($old_ids as $id) {
if (strpos($facetSourceId, $id) !== FALSE) {
$new_id = str_replace($id . ':', 'search_api:' . $id . '__', $facetSourceId);
$entity->setFacetSourceId($new_id);
$entity->save();
}
}
}
}
......@@ -74,7 +74,7 @@ class IntegrationTest extends FacetsTestBase {
$values = [
'name' => 'Owl',
'id' => 'owl',
'facet_source_id' => 'views_page:search_api_test_view__page_1',
'facet_source_id' => 'search_api:views_page__search_api_test_view__page_1',
];
$this->drupalPostForm('admin/config/search/facets/add-facet-summary', $values, 'Save');
$this->drupalPostForm(NULL, [], 'Save');
......
......@@ -5,6 +5,7 @@ core: 8.x
package: Search
dependencies:
- facets:facets
- drupal:rest
test_dependencies:
- search_api:search_api
- facets:facets
......
......@@ -24,7 +24,7 @@ class FacetsSerializer extends Serializer {
/**
* Tha facet manager.
*
* @var DefaultFacetManager
* @var \Drupal\facets\FacetManager\DefaultFacetManager
*/
protected $facetsManager;
......@@ -80,7 +80,7 @@ class FacetsSerializer extends Serializer {
}
// Processing facets.
$facetsource_id = "views_page:{$this->view->id()}__{$this->view->getDisplay()->display['id']}";
$facetsource_id = "search_api:views_rest__{$this->view->id()}__{$this->view->getDisplay()->display['id']}";
$facets = $this->facetsManager->getFacetsByFacetSourceId($facetsource_id);
$this->facetsManager->updateResults($facetsource_id);
......
......@@ -60,11 +60,12 @@ class RestIntegrationTest extends FacetsTestBase {
*/
public function testRestResults() {
global $base_url;
$name = 'Type';
$id = 'type';
// Add a new facet to filter by content type.
$this->createFacet($name, $id, 'type', 'rest_export_1', 'search_api_rest_test_view');
$this->createFacet($name, $id, 'type', 'rest_export_1', 'views_rest__search_api_rest_test_view');
// Use the array widget.
$facet_edit_page = '/admin/config/search/facets/' . $id . '/edit';
......@@ -79,6 +80,7 @@ class RestIntegrationTest extends FacetsTestBase {
$values['facet_sorting[display_value_widget_order][status]'] = FALSE;
$values['facet_sorting[active_widget_order][status]'] = FALSE;
$values['facet_settings[query_operator]'] = 'or';
$values['facet_settings[only_visible_when_facet_source_is_visible]'] = TRUE;
$this->drupalPostForm(NULL, $values, $this->t('Save'));
......@@ -87,7 +89,7 @@ class RestIntegrationTest extends FacetsTestBase {
$name = 'Keywords';
$id = 'keywords';
// Add a new facet to filter by keywords.
$this->createFacet($name, $id, 'keywords', 'rest_export_1', 'search_api_rest_test_view');
$this->createFacet($name, $id, 'keywords', 'rest_export_1', 'views_rest__search_api_rest_test_view');
// Use the array widget.
$facet_edit_page = '/admin/config/search/facets/' . $id . '/edit';
......@@ -102,6 +104,7 @@ class RestIntegrationTest extends FacetsTestBase {
$values['facet_sorting[display_value_widget_order][status]'] = FALSE;
$values['facet_sorting[active_widget_order][status]'] = FALSE;
$values['facet_settings[query_operator]'] = 'or';
$values['facet_settings[only_visible_when_facet_source_is_visible]'] = TRUE;
$this->drupalPostForm(NULL, $values, $this->t('Save'));
......
......@@ -41,4 +41,11 @@ class FacetsFacetSource extends Plugin {
*/
public $description;
/**
* The id of the search api display, if one is used.
*
* @var string
*/
public $display_id;
}
......@@ -2,7 +2,6 @@
namespace Drupal\facets\FacetSource;
use Drupal\Core\Entity\EntityTypeManager;
use Drupal\Core\Entity\EntityTypeManagerInterface;
use Drupal\Core\Plugin\Discovery\ContainerDeriverInterface;
use Drupal\Core\StringTranslation\StringTranslationTrait;
......@@ -63,7 +62,7 @@ abstract class FacetSourceDeriverBase implements ContainerDeriverInterface {
/**
* Retrieves the entity manager.
*
* @return \Drupal\Core\Entity\EntityTypeManager
* @return \Drupal\Core\Entity\EntityTypeManagerInterface
* The entity manager.
*/
public function getEntityTypeManager() {
......@@ -91,23 +90,6 @@ abstract class FacetSourceDeriverBase implements ContainerDeriverInterface {
return isset($derivatives[$derivative_id]) ? $derivatives[$derivative_id] : NULL;
}
/**
* Compares two plugin definitions according to their labels.
*
* @param array $a
* A plugin definition, with at least a "label" key.
* @param array $b
* Another plugin definition.
*
* @return int
* An integer less than, equal to, or greater than zero if the first
* argument is considered to be respectively less than, equal to, or greater
* than the second.
*/
public function compareDerivatives(array $a, array $b) {
return strnatcasecmp($a['label'], $b['label']);
}
/**
* Sets search api's display plugin manager.
*
......@@ -128,4 +110,21 @@ abstract class FacetSourceDeriverBase implements ContainerDeriverInterface {
return $this->searchApiDisplayPluginManager;
}
/**
* Compares two plugin definitions according to their labels.
*
* @param array $a
* A plugin definition, with at least a "label" key.
* @param array $b
* Another plugin definition.
*
* @return int
* An integer less than, equal to, or greater than zero if the first
* argument is considered to be respectively less than, equal to, or greater
* than the second.
*/
public function compareDerivatives(array $a, array $b) {
return strnatcasecmp($a['label'], $b['label']);
}
}
......@@ -40,10 +40,11 @@ interface FacetSourcePluginInterface extends PluginFormInterface, DependentPlugi
public function getQueryTypesForFacet(FacetInterface $facet);
/**
* Returns the path where a facet should link to.
* Returns the url of the facet source, used to build the facet url.
*
* @return string
* The path of the facet.
* @return \Drupal\Core\Url
* The url object for the facet if it's set, a url object to the current
* page otherwise.
*/
public function getPath();
......
......@@ -2,6 +2,7 @@
namespace Drupal\facets\FacetSource;
use Drupal\Component\Plugin\Exception\PluginException;
use Drupal\Core\Cache\CacheBackendInterface;
use Drupal\Core\Extension\ModuleHandlerInterface;
use Drupal\Core\Plugin\DefaultPluginManager;
......@@ -22,4 +23,30 @@ class FacetSourcePluginManager extends DefaultPluginManager {
parent::__construct('Plugin/facets/facet_source', $namespaces, $module_handler, 'Drupal\facets\FacetSource\FacetSourcePluginInterface', 'Drupal\facets\Annotation\FacetsFacetSource');
}
/**
* {@inheritdoc}
*/
public function processDefinition(&$definition, $plugin_id) {
parent::processDefinition($definition, $plugin_id);
// At the very least - we need to have an ID in the definition of the
// plugin.
if (!isset($definition['id'])) {
throw new PluginException(sprintf('The facet source plugin %s must define the id property.', $plugin_id));
}
// If we're checking the search api plugin, only try to add it if search api
// is enabled.
if ($definition['id'] === 'search_api' && !$this->moduleHandler->moduleExists('search_api')) {
return;
}
// Check that other required labels are available.
foreach (['display_id', 'label'] as $required_property) {
if (empty($definition[$required_property])) {
throw new PluginException(sprintf('The facet source plugin %s must define the %s property.', $plugin_id, $required_property));
}
}
}
}
......@@ -6,6 +6,7 @@ use Drupal\Component\Utility\Html;
use Drupal\Core\Entity\EntityForm;
use Drupal\Core\Entity\EntityTypeManagerInterface;
use Drupal\Core\Form\FormStateInterface;
use Drupal\facets\Plugin\facets\facet_source\SearchApiDisplay;
use Drupal\facets\Processor\ProcessorInterface;
use Drupal\facets\Processor\ProcessorPluginManager;
use Drupal\facets\UrlProcessor\UrlProcessorInterface;
......@@ -373,7 +374,7 @@ class FacetForm extends EntityForm {
'#options' => [0 => $this->t('No limit')] + array_combine($hard_limit_options, $hard_limit_options),
'#description' => $this->t('Display no more than this number of facet items.'),
];
if (strpos($facet->getFacetSourceId(), 'views_') === FALSE) {
if (!$facet->getFacetSource() instanceof SearchApiDisplay) {
$form['facet_settings']['hard_limit']['#disabled'] = TRUE;
$form['facet_settings']['hard_limit']['#description'] .= '<br />';
$form['facet_settings']['hard_limit']['#description'] .= $this->t('This setting only works with Search API based facets.');
......@@ -391,7 +392,7 @@ class FacetForm extends EntityForm {
'#title' => $this->t('Use hierarchy'),
'#default_value' => $facet->getUseHierarchy(),
];
if (strpos($facet->getFacetSourceId(), 'views_') === FALSE) {
if (!$facet->getFacetSource() instanceof SearchApiDisplay) {
$form['facet_settings']['use_hierarchy']['#disabled'] = TRUE;
$form['facet_settings']['use_hierarchy']['#description'] = $this->t('This setting only works with Search API based facets.');
}
......@@ -439,7 +440,7 @@ class FacetForm extends EntityForm {
'#maxlength' => 4,
'#required' => TRUE,
];
if (strpos($facet->getFacetSourceId(), 'views_') === FALSE) {
if (!$facet->getFacetSource() instanceof SearchApiDisplay) {
$form['facet_settings']['min_count']['#disabled'] = TRUE;
$form['facet_settings']['min_count']['#description'] .= '<br />';
$form['facet_settings']['min_count']['#description'] .= $this->t('This setting only works with Search API based facets.');
......
......@@ -2,6 +2,7 @@
namespace Drupal\facets\Plugin\facets\facet_source;
use Drupal\Component\Plugin\PluginBase;
use Drupal\facets\FacetSource\FacetSourceDeriverBase;
/**
......@@ -11,39 +12,44 @@ use Drupal\facets\FacetSource\FacetSourceDeriverBase;
*
* @see \Drupal\facets\Plugin\facets\facet_source\SearchApi
*/
class SearchApiViewsDeriver extends FacetSourceDeriverBase {
class SearchApiDisplayDeriver extends FacetSourceDeriverBase {
/**
* {@inheritdoc}
*/
public function getDerivativeDefinitions($base_plugin_definition) {
$base_plugin_id = $base_plugin_definition['id'];
$plugin_derivatives = array();
$search_api_displays = $this->getSearchApiDisplayPluginManager();
$display_plugin_manager = $this->getSearchApiDisplayPluginManager();
foreach ($display_plugin_manager->getDefinitions() as $display_id => $display_definition) {
// If 'index' is not set on the plugin, we can't load the index.
if (!isset($display_definition['index'])) {
continue;
}
$plugin_derivatives = array();
foreach ($search_api_displays->getDefinitions() as $display) {
// Avoid providing corrupted displays.
if (isset($display['view_id']) && isset($display['view_display']) && isset($display['label'])) {
$machine_name = $display['view_id'] . '__' . $display['view_display'];
$plugin_derivatives[$machine_name] = [
'id' => $base_plugin_id . ':' . $machine_name,
'label' => $display['label'],
'description' => $this->t('Provides a facet source.'),
'view_id' => $display['view_id'],
'view_display' => $display['view_display'],
] + $base_plugin_definition;
$arguments = [
'%view' => $display['label'],
'%display' => $display['view_display'],
];
$sources[] = $this->t('Search API view: %view, display: %display', $arguments);
$display = $display_plugin_manager->createInstance($display_id);
$supports_facets = $display->getIndex()
->getServerInstance()
->supportsFeature('search_api_facets');
// If facets are not supported by the server, don't actually add this to
// the list of plugins.
if (!$supports_facets) {
continue;
}
$machine_name = str_replace(':', '__', $display->getPluginId());
$plugin_derivatives[$machine_name] = [
'id' => $base_plugin_id . PluginBase::DERIVATIVE_SEPARATOR . $machine_name,
'display_id' => $display_id,
'label' => $display->label(),
'description' => $display->getDescription(),
] + $base_plugin_definition;
}
uasort($plugin_derivatives, array($this, 'compareDerivatives'));
uasort($plugin_derivatives, [$this, 'compareDerivatives']);
$this->derivatives[$base_plugin_id] = $plugin_derivatives;
return $this->derivatives[$base_plugin_id];
......
<?php
namespace Drupal\facets\Plugin\facets\facet_source;
use Drupal\facets\FacetSource\SearchApiFacetSourceInterface;
use Drupal\search_api\Plugin\views\query\SearchApiQuery;
use Drupal\search_api\Query\ResultSetInterface;
use Drupal\views\Entity\View;
use Drupal\views\Views;
/**
* A facet source to support search api views trough display plugins.
*
* @FacetsFacetSource(
* id = "views_page",
* deriver = "Drupal\facets\Plugin\facets\facet_source\SearchApiViewsDeriver"
* )
*/
class SearchApiViews extends SearchApiBaseFacetSource implements SearchApiFacetSourceInterface {
/**
* The entity manager.
*
* @var \Drupal\Core\Entity\EntityTypeManager|null
*/
protected $entityTypeManager;
/**
* The typed data manager.
*
* @var \Drupal\Core\TypedData\TypedDataManager|null
*/
protected $typedDataManager;
/**
* The config factory.
*
* @var \Drupal\Core\Config\ConfigFactoryInterface|null
*/
protected $configFactory;
/**
* The search index the query should is executed on.
*
* @var \Drupal\search_api\IndexInterface
*/
protected $index;
/**
* {@inheritdoc}
*/
public function __construct(array $configuration, $plugin_id, array $plugin_definition, $query_type_plugin_manager, $search_results_cache) {
parent::__construct($configuration, $plugin_id, $plugin_definition, $query_type_plugin_manager, $search_results_cache);
// Load facet plugin definition and depending on those settings; load the
// corresponding view with the correct view with the correct display set.
// Get that display's query so we can check if this is a Search API based
// view.
$view = Views::getView($plugin_definition['view_id']);
if (!empty($view)) {
$view->setDisplay($plugin_definition['view_display']);
$query = $view->getQuery();
// Only add the index if the $query is a Search API Query.
if ($query instanceof SearchApiQuery) {
// Set the Search API Index.
$this->index = $query->getIndex();
}
}
}
/**
* {@inheritdoc}
*/
public function getPath() {
$display = View::load($this->pluginDefinition['view_id'])->getDisplay($this->pluginDefinition['view_display']);
switch ($display['display_plugin']) {
case 'page':
$view = Views::getView($this->pluginDefinition['view_id']);
$view->setDisplay($this->pluginDefinition['view_display']);
return '/' . $view->getDisplay()->getPath();
case 'block':
default:
$current_path = \Drupal::service('path.current')->getPath();
if (\Drupal::moduleHandler()->moduleExists('path')) {
return \Drupal::service('path.alias_manager')->getAliasByPath($current_path);
}
else {
return $current_path;
}
}
}
/**
* {@inheritdoc}
*/
public function fillFacetsWithResults(array $facets) {
// Check if there are results in the static cache.
$results = $this->searchApiQueryHelper->getResults($this->pluginId);
// If our results are not there, execute the view to get the results.
if ($results === NULL) {
// If there are no results, execute the view. and check for results again!
$view = Views::getView($this->pluginDefinition['view_id']);
$view->setDisplay($this->pluginDefinition['view_display']);
$view->execute();
$results = $this->searchApiQueryHelper->getResults($this->pluginId);
}
// Get the results from the cache. It is possible it still errored out.
if ($results instanceof ResultSetInterface) {
// Get our facet data.
$facet_results = $results->getExtraData('search_api_facets');
if ($facet_results === []) {
return;
}
// Loop over each facet and execute the build method from the given
// query type.
foreach ($facets as $facet) {
$configuration = array(
'query' => NULL,
'facet' => $facet,
'results' => isset($facet_results[$facet->getFieldIdentifier()]) ? $facet_results[$facet->getFieldIdentifier()] : [],
);
// Get the Facet Specific Query Type so we can process the results
// using the build() function of the query type.
$query_type = $this->queryTypePluginManager->createInstance($facet->getQueryType(), $configuration);
$query_type->build();
}
}
}
/**
* {@inheritdoc}
*/
public function isRenderedInCurrentRequest() {
$display = View::load($this->pluginDefinition['view_id'])->getDisplay($this->pluginDefinition['view_display']);
switch ($display['display_plugin']) {
case 'rest_export':
case 'page':
$request = \Drupal::requestStack()->getMasterRequest();
if ($request->attributes->get('_controller') === 'Drupal\views\Routing\ViewPageController::handle') {
list(, $view) = explode(':', $this->getPluginId());