diff --git a/automatic_updates_9_3_shim/automatic_updates_9_3_shim.module b/automatic_updates_9_3_shim/automatic_updates_9_3_shim.module
new file mode 100644
index 0000000000000000000000000000000000000000..0734d6dafab92a0b0de1abdba9071d57074d0d07
--- /dev/null
+++ b/automatic_updates_9_3_shim/automatic_updates_9_3_shim.module
@@ -0,0 +1,43 @@
+<?php
+
+/**
+ * @file
+ * Contains hook implementations for Automatic Updates 9.3 shim module.
+ */
+
+/**
+ * Implements hook_page_top().
+ */
+function automatic_updates_9_3_shim_page_top() {
+  // @todo Rely on the route option after https://www.drupal.org/i/3236497 is
+  //   committed.
+  // @todo Remove 'system.batch_page.html' after
+  //   https://www.drupal.org/i/3238311 is committed.
+  $skip_routes = [
+    'system.batch_page.html',
+    'automatic_updates.confirmation_page',
+    'automatic_updates.report_update',
+    'automatic_updates.module_update',
+  ];
+  $route_name = \Drupal::routeMatch()->getRouteName();
+  if (!in_array($route_name, $skip_routes, TRUE) && function_exists('update_page_top')) {
+    update_page_top();
+  }
+}
+
+/**
+ * Implements hook_module_implements_alter().
+ *
+ * @todo Remove after https://www.drupal.org/i/3236497 is committed.
+ */
+function automatic_updates_9_3_shim_module_implements_alter(&$implementations, $hook) {
+  if ($hook === 'page_top') {
+    // Remove hook_page_top() implementation from the Update module. This '
+    // implementation displays error messages about security releases. We call
+    // this implementation in our own automatic_updates_page_top() except on our
+    // own routes to avoid stale messages about the security releases after an
+    // update.
+    unset($implementations['update']);
+  }
+
+}
diff --git a/tests/fixtures/release-history/drupal.0.0.xml b/tests/fixtures/release-history/drupal.0.0.xml
index 4d5268378ef31b4e9c59766f2572dd76c30c730e..dbcb825a86d351652f72f2ff04b74fff9f8de8d8 100644
--- a/tests/fixtures/release-history/drupal.0.0.xml
+++ b/tests/fixtures/release-history/drupal.0.0.xml
@@ -20,6 +20,7 @@
   <terms>
     <term><name>Release type</name><value>New features</value></term>
     <term><name>Release type</name><value>Bug fixes</value></term>
+    <term><name>Release type</name><value>Security update</value></term>
   </terms>
  </release>
  <release>
@@ -32,6 +33,7 @@
    <terms>
      <term><name>Release type</name><value>New features</value></term>
      <term><name>Release type</name><value>Bug fixes</value></term>
+     <term><name>Release type</name><value>Insecure</value></term>
    </terms>
  </release>
 </releases>
diff --git a/tests/src/Build/CoreUpdateTest.php b/tests/src/Build/CoreUpdateTest.php
index 763d554682f3c8aa26e49114adba11a356d34260..78612ad577f54ac39ecbdd9deb3f4085e3cd957c 100644
--- a/tests/src/Build/CoreUpdateTest.php
+++ b/tests/src/Build/CoreUpdateTest.php
@@ -118,14 +118,17 @@ class CoreUpdateTest extends UpdateTestBase {
     $mink = $this->getMink();
     $page = $mink->getSession()->getPage();
     $assert_session = $mink->assertSession();
-
-    $this->visit('/admin/modules/automatic-update');
+    $this->visit('/admin/modules');
+    $assert_session->pageTextContains('There is a security update available for your version of Drupal.');
+    $page->clickLink('Automatic Updates');
+    $assert_session->pageTextNotContains('There is a security update available for your version of Drupal.');
     $page->pressButton('Download these updates');
     $this->waitForBatchJob();
     $assert_session->pageTextContains('Ready to update');
     $page->pressButton('Continue');
     $this->waitForBatchJob();
     $assert_session->pageTextContains('Update complete!');
+    $assert_session->pageTextNotContains('There is a security update available for your version of Drupal.');
     $this->assertUpdateSuccessful();
   }
 
diff --git a/tests/src/Functional/UpdaterFormTest.php b/tests/src/Functional/UpdaterFormTest.php
index a28216cc805e4a72f29cfd6c9885b204333f3d87..73e0d983b114396f255cf8eddbd0deed665e3506 100644
--- a/tests/src/Functional/UpdaterFormTest.php
+++ b/tests/src/Functional/UpdaterFormTest.php
@@ -89,18 +89,20 @@ class UpdaterFormTest extends BrowserTestBase {
     $this->drupalPlaceBlock('local_tasks_block', ['primary' => TRUE]);
     $assert_session = $this->assertSession();
     $this->setCoreVersion('9.8.0');
-
     $this->drupalLogin($this->rootUser);
+    $this->checkForUpdates();
 
     // Navigate to the automatic updates form.
     $this->drupalGet('/admin');
     // @todo Add test coverage of accessing the form via the other path in
     //   https://www.drupal.org/i/3233564
     $this->clickLink('Extend');
+    $assert_session->pageTextContainsOnce('There is a security update available for your version of Drupal.');
     $this->clickLink('Update');
     $assert_session->pageTextContainsOnce('Drupal core updates are supported by the enabled Automatic Updates module');
     $this->clickLink('Automatic Updates module');
-    $cells = $assert_session->elementExists('css', '#edit-projects .update-recommended')
+    $assert_session->pageTextNotContains('There is a security update available for your version of Drupal.');
+    $cells = $assert_session->elementExists('css', '#edit-projects .update-update-security')
       ->findAll('css', 'td');
     $this->assertCount(3, $cells);
     $assert_session->elementExists('named', ['link', 'Drupal'], $cells[0]);