 core/modules/search/src/Form/SearchBlockForm.php   | 10 +++-
 .../tests/src/Functional/SearchBlockTest.php       | 70 ++++++++++++++++++++++
 2 files changed, 79 insertions(+), 1 deletion(-)

diff --git a/core/modules/search/src/Form/SearchBlockForm.php b/core/modules/search/src/Form/SearchBlockForm.php
index 7a9405f..3a43db5 100644
--- a/core/modules/search/src/Form/SearchBlockForm.php
+++ b/core/modules/search/src/Form/SearchBlockForm.php
@@ -2,10 +2,12 @@
 
 namespace Drupal\search\Form;
 
+use Drupal\Core\Cache\CacheableMetadata;
 use Drupal\Core\Config\ConfigFactoryInterface;
 use Drupal\Core\Form\FormBase;
 use Drupal\Core\Form\FormStateInterface;
 use Drupal\Core\Render\RendererInterface;
+use Drupal\search\Entity\SearchPage;
 use Drupal\search\SearchPageRepositoryInterface;
 use Symfony\Component\DependencyInjection\ContainerInterface;
 
@@ -76,12 +78,18 @@ public function buildForm(array $form, FormStateInterface $form_state) {
     // Set up the form to submit using GET to the correct search page.
     $entity_id = $this->searchPageRepository->getDefaultSearchPage();
 
-    // SearchPageRepository::getDefaultSearchPage() depends on search.settings.
+    // SearchPageRepository::getDefaultSearchPage() depends on search.settings
+    // config as well as all SearchPage entities (due to its fallback behavior).
     // The dependency needs to be added before the conditional return, otherwise
     // the block would get cached without the necessary cacheablity metadata in
     // case there is no default search page and would not be invalidated if that
     // changes.
     $this->renderer->addCacheableDependency($form, $this->configFactory->get('search.settings'));
+    $search_page_entity_type = SearchPage::create([])->getEntityType();
+    $this->renderer->addCacheableDependency($form, (new CacheableMetadata())
+      ->addCacheTags($search_page_entity_type->getListCacheTags())
+      ->addCacheContexts($search_page_entity_type->getListCacheContexts())
+    );
 
     if (!$entity_id) {
       $form['message'] = [
diff --git a/core/modules/search/tests/src/Functional/SearchBlockTest.php b/core/modules/search/tests/src/Functional/SearchBlockTest.php
new file mode 100644
index 0000000..7563a7b
--- /dev/null
+++ b/core/modules/search/tests/src/Functional/SearchBlockTest.php
@@ -0,0 +1,70 @@
+<?php
+
+namespace Drupal\Tests\search\Functional;
+
+use Drupal\search\Entity\SearchPage;
+use Drupal\user\Entity\Role;
+
+/**
+ * @group search
+ */
+class SearchBlockTest extends SearchTestBase {
+
+  /**
+   * {@inheritdoc}
+   */
+  public static $modules = ['block'];
+
+  /**
+   * {@inheritdoc}
+   */
+  protected function setUp() {
+    parent::setUp();
+
+    // Place the "Search" block and let anonymous users use it.
+    $this->drupalPlaceBlock('search_form_block');
+    $this->grantPermissions(Role::load('anonymous'), ['search content']);
+
+    // Start with a blank slate.
+    $this->config('search.settings')->set('default_page', NULL)->save();
+    SearchPage::load('node_search')->disable()->save();
+    SearchPage::load('user_search')->disable()->save();
+  }
+
+  /**
+   * @covers \Drupal\search\Form\SearchBlockForm::buildForm
+   * @covers \Drupal\search\SearchPageRepository::getDefaultSearchPage
+   */
+  public function testSearchBlockContents() {
+    // Initially, the search block reports being disabled.
+    $this->assertSearchBlockContents(FALSE);
+
+    // After having >=1 enabled SearchPage entities, the search block
+    // automatically uses that.
+    SearchPage::load('node_search')->enable()->save();
+    $this->assertSearchBlockContents(TRUE);
+
+    // Changing the search.settings config also cuases
+    $this->config('search.settings')->set('default_page', 'node_search')->save();
+    $this->assertSearchBlockContents(TRUE);
+  }
+
+  /**
+   * Asserts the search block's contents.
+   *
+   * @param bool $expected_is_enabled
+   *   Whether the search block's functionality is expected to be enabled.
+   */
+  protected function assertSearchBlockContents($expected_is_enabled) {
+    $this->drupalGet('<front>');
+
+    $this->assertEquals(!$expected_is_enabled, $this->assertSession()->pageTextContains('Search is currently disabled'));
+    $this->assertEquals($expected_is_enabled, $this->cssSelect('input[type=search][title="Enter the terms you wish to search for."]'));
+    // Cache miss due to first request, or  due to invalidated cache tag.
+    $this->assertSession()->responseHeaderEquals('X-Drupal-Cache', 'MISS');
+
+    $this->drupalGet($this->getSession()->getCurrentUrl());
+    $this->assertSession()->responseHeaderEquals('X-Drupal-Cache', 'HIT');
+  }
+
+}
