diff --git a/core/modules/content_moderation/content_moderation.services.yml b/core/modules/content_moderation/content_moderation.services.yml
index 904bc0dc33..256095a03a 100644
--- a/core/modules/content_moderation/content_moderation.services.yml
+++ b/core/modules/content_moderation/content_moderation.services.yml
@@ -19,4 +19,9 @@ services:
     class: Drupal\content_moderation\RevisionTracker
     arguments: ['@database']
     tags:
-     - { name: backend_overridable }
+      - { name: backend_overridable }
+  content_moderation.config_import_subscriber:
+    class: Drupal\content_moderation\EventSubscriber\ConfigImportSubscriber
+    arguments: ['@config.manager', '@entity_type.manager']
+    tags:
+      - { name: event_subscriber }
diff --git a/core/modules/content_moderation/src/EventSubscriber/ConfigImportSubscriber.php b/core/modules/content_moderation/src/EventSubscriber/ConfigImportSubscriber.php
new file mode 100644
index 0000000000..3555d736aa
--- /dev/null
+++ b/core/modules/content_moderation/src/EventSubscriber/ConfigImportSubscriber.php
@@ -0,0 +1,72 @@
+<?php
+
+namespace Drupal\content_moderation\EventSubscriber;
+
+use Drupal\Core\Config\ConfigImporterEvent;
+use Drupal\Core\Config\ConfigImportValidateEventSubscriberBase;
+use Drupal\Core\Config\ConfigManagerInterface;
+use Drupal\Core\Config\Entity\ConfigEntityStorage;
+use Drupal\Core\Entity\EntityTypeManagerInterface;
+
+/**
+ * Check moderation states are not being used before updating workflow config.
+ */
+class ConfigImportSubscriber extends ConfigImportValidateEventSubscriberBase  {
+
+  /**
+   * The config manager.
+   *
+   * @var \Drupal\Core\Config\ConfigManagerInterface
+   */
+  protected $configManager;
+
+  /**
+   * The entity type manager.
+   *
+   * @var \Drupal\Core\Entity\EntityTypeManagerInterface
+   */
+  protected $entityTypeManager;
+
+  /**
+   * Constructs the event subscriber.
+   *
+   * @param \Drupal\Core\Config\ConfigManagerInterface $config_manager
+   *   The config manager
+   * @param \Drupal\Core\Entity\EntityTypeManagerInterface $entity_type_manager
+   *   The entity manager.
+   */
+  public function __construct(ConfigManagerInterface $config_manager, EntityTypeManagerInterface $entity_type_manager) {
+    $this->configManager = $config_manager;
+    $this->entityTypeManager = $entity_type_manager;
+  }
+
+  /**
+   * {@inheritdoc}
+   */
+  public function onConfigImporterValidate(ConfigImporterEvent $event) {
+    $unprocessed_configurations = $event->getConfigImporter()->getUnprocessedConfiguration('update');
+    foreach ($unprocessed_configurations as $unprocessed_configuration) {
+      $entity_type_id = $this->configManager->getEntityTypeIdByName($unprocessed_configuration);
+      if ($entity_type_id == 'workflow') {
+        /** @var \Drupal\Core\Config\Entity\ConfigEntityTypeInterface $entity_type */
+        $entity_type = $this->entityTypeManager->getDefinition($entity_type_id);
+        $importer = $event->getConfigImporter();
+        $source_storage = $importer->getStorageComparer()
+          ->getSourceStorage()
+          ->read($unprocessed_configuration);
+        $target_storage = $importer->getStorageComparer()
+          ->getTargetStorage()
+          ->read($unprocessed_configuration);
+        $diff = array_diff_key($target_storage['states'], $source_storage['states']);
+        $entity_id = ConfigEntityStorage::getIDFromConfigName($unprocessed_configuration, $entity_type->getConfigPrefix());
+        /** @var \Drupal\workflows\WorkflowInterface $workflow */
+        $workflow = $this->entityTypeManager->getStorage($entity_type_id)->load($entity_id);
+        $state = $workflow->getState(key($diff));
+        if ($workflow->getTypePlugin()->isWorkflowStateUsed($workflow, $state)) {
+          $importer->logError($this->t('The moderation state @state_label is being used, but is not in the source storage.', ['@state_label' => $state->label()]));
+        }
+      }
+    }
+  }
+
+}
diff --git a/core/modules/content_moderation/src/Plugin/WorkflowType/ContentModeration.php b/core/modules/content_moderation/src/Plugin/WorkflowType/ContentModeration.php
index b80ccdda87..dcfe341b34 100644
--- a/core/modules/content_moderation/src/Plugin/WorkflowType/ContentModeration.php
+++ b/core/modules/content_moderation/src/Plugin/WorkflowType/ContentModeration.php
@@ -131,6 +131,31 @@ public function decorateState(StateInterface $state) {
   /**
    * {@inheritdoc}
    */
+  public function isWorkflowUsed(WorkflowInterface $workflow) {
+    return (bool) $this->entityTypeManager
+      ->getStorage('content_moderation_state')
+      ->getQuery()
+      ->count()
+      ->condition('workflow', $workflow->id())
+      ->execute();
+  }
+
+  /**
+   * {@inheritdoc}
+   */
+  public function isWorkflowStateUsed(WorkflowInterface $workflow, StateInterface $state) {
+    return (bool) $this->entityTypeManager
+      ->getStorage('content_moderation_state')
+      ->getQuery()
+      ->count()
+      ->condition('workflow', $workflow->id())
+      ->condition('moderation_state', $state->id())
+      ->execute();
+  }
+
+  /**
+   * {@inheritdoc}
+   */
   public function buildStateConfigurationForm(FormStateInterface $form_state, WorkflowInterface $workflow, StateInterface $state = NULL) {
     /** @var \Drupal\content_moderation\ContentModerationState $state */
     $is_required_state = isset($state) ? in_array($state->id(), $this->getRequiredStates(), TRUE) : FALSE;
diff --git a/core/modules/content_moderation/tests/src/Functional/ModerationFormTest.php b/core/modules/content_moderation/tests/src/Functional/ModerationFormTest.php
index 3882c764f1..6e34430e7f 100644
--- a/core/modules/content_moderation/tests/src/Functional/ModerationFormTest.php
+++ b/core/modules/content_moderation/tests/src/Functional/ModerationFormTest.php
@@ -205,4 +205,41 @@ public function testModerationFormSetsRevisionAuthor() {
     $this->assertText('by ' . $another_user->getAccountName());
   }
 
+  /**
+   * Tests ContentModeration::isWorkflowUsed().
+   *
+   * @see \Drupal\content_moderation\Plugin\WorkflowType\ContentModeration::isWorkflowUsed()
+   */
+  public function testWorkflowInUse() {
+    $this->drupalLogin($this->rootUser);
+    $paths = [
+      'archived_state' => 'admin/config/workflow/workflows/manage/editorial/state/archived/delete',
+      'editorial_workflow' => 'admin/config/workflow/workflows/manage/editorial/delete',
+    ];
+    foreach ($paths as $path) {
+      $this->drupalGet($path);
+      $this->assertSession()->statusCodeEquals(200);
+    }
+    // Create new moderated content in draft.
+    $this->drupalPostForm('node/add/moderated_content', [
+      'title[0][value]' => 'Some moderated content',
+      'body[0][value]' => 'First version of the content.',
+    ], t('Save and Create New Draft'));
+    // The archived state is not used yet, so can still be deleted.
+    $this->drupalGet($paths['archived_state']);
+    $this->assertSession()->statusCodeEquals(200);
+    // The workflow is being used, so can't be deleted.
+    $this->drupalGet($paths['editorial_workflow']);
+    $this->assertSession()->statusCodeEquals(403);
+
+    $node = $this->drupalGetNodeByTitle('Some moderated content');
+    $edit_path = sprintf('node/%d/edit', $node->id());
+    $this->drupalPostForm($edit_path, [], t('Save and Publish'));
+    $this->drupalPostForm($edit_path, [], t('Save and Archive'));
+    // Now the archived state is being used it can't be deleted either.
+    foreach ($paths as $path) {
+      $this->drupalGet($path);
+      $this->assertSession()->statusCodeEquals(403);
+    }
+  }
 }
diff --git a/core/modules/content_moderation/tests/src/Kernel/ContentModerationWorkflowConfigTest.php b/core/modules/content_moderation/tests/src/Kernel/ContentModerationWorkflowConfigTest.php
new file mode 100644
index 0000000000..97d9596d2b
--- /dev/null
+++ b/core/modules/content_moderation/tests/src/Kernel/ContentModerationWorkflowConfigTest.php
@@ -0,0 +1,125 @@
+<?php
+
+namespace Drupal\Tests\content_moderation\Kernel;
+
+use Drupal\Core\Config\ConfigImporterException;
+use Drupal\KernelTests\KernelTestBase;
+use Drupal\node\Entity\Node;
+use Drupal\node\Entity\NodeType;
+use Drupal\workflows\Entity\Workflow;
+
+/**
+ * Tests how Content Moderation handles workflow config changes.
+ *
+ * @group content_moderation
+ */
+class ContentModerationWorkflowConfigTest extends KernelTestBase {
+
+  /**
+   * {@inheritdoc}
+   */
+  public static $modules = [
+    'node',
+    'content_moderation',
+    'user',
+    'system',
+    'text',
+    'workflows',
+  ];
+
+  /**
+   * @var \Drupal\Core\Entity\EntityTypeManager
+   */
+  protected $entityTypeManager;
+
+  /**
+   * @var \Drupal\Core\Config\ConfigFactoryInterface
+   */
+  protected $configFactory;
+
+  /**
+   * @var \Drupal\workflows\Entity\Workflow
+   */
+  protected $workflow;
+
+  /**
+   * @var \Drupal\Core\Config\Entity\ConfigEntityStorage
+   */
+  protected $workflowStorage;
+
+  /**
+   * {@inheritdoc}
+   */
+  protected function setUp() {
+    parent::setUp();
+
+    $this->installSchema('node', 'node_access');
+    $this->installEntitySchema('node');
+    $this->installEntitySchema('user');
+    $this->installEntitySchema('content_moderation_state');
+    $this->installConfig('content_moderation');
+
+    NodeType::create([
+      'type' => 'example',
+    ])->save();
+
+    $workflow = Workflow::load('editorial');
+    $workflow->addState('test1', 'Test one');
+    $workflow->addState('test2', 'Test two');
+    $workflow->getTypePlugin()->setConfiguration([
+      'states' => [
+        'test1' => [
+          'published' => TRUE,
+          'default_revision' => TRUE,
+        ],
+        'test2' => [
+          'published' => TRUE,
+          'default_revision' => TRUE,
+        ],
+      ],
+    ]);
+    $workflow->getTypePlugin()->addEntityTypeAndBundle('node', 'example');
+    $workflow->save();
+    $this->workflow = $workflow;
+
+    $this->copyConfig($this->container->get('config.storage'), $this->container->get('config.storage.sync'));
+
+  }
+
+  /**
+   * Test deleting a state via config import.
+   */
+  public function testDeletingStateViaConfiguration() {
+    $config_data = $this->config('workflows.workflow.editorial')->get();
+    unset($config_data['states']['test1']);
+    \Drupal::service('config.storage.sync')->write('workflows.workflow.editorial', $config_data);
+
+    // There are no Nodes with the moderation state test, so this should run
+    // with no errors.
+    $this->configImporter()->reset()->import();
+
+    $node = Node::create([
+      'type' => 'example',
+      'title' => 'Test title',
+      'moderation_state' => 'test2',
+    ]);
+    $node->save();
+
+    $config_data = $this->config('workflows.workflow.editorial')->get();
+    unset($config_data['states']['test2']);
+    \Drupal::service('config.storage.sync')->write('workflows.workflow.editorial', $config_data);
+
+    // Now there is a Node with the moderation state unpub_test, this will fail.
+    try {
+      $this->configImporter()->reset()->import();
+      $this->fail('ConfigImporterException not thrown, invalid import was not stopped due to deleted state.');
+    }
+    catch (ConfigImporterException $e) {
+      $this->assertEqual($e->getMessage(), 'There were errors validating the config synchronization.');
+      $error_log = $this->configImporter->getErrors();
+      $expected = ['The moderation state Test two is being used, but is not in the source storage.'];
+      $this->assertEqual($expected, $error_log);
+    }
+  }
+
+}
diff --git a/core/modules/workflows/src/Plugin/WorkflowTypeBase.php b/core/modules/workflows/src/Plugin/WorkflowTypeBase.php
index 34af735e3d..4b9ca7f5be 100644
--- a/core/modules/workflows/src/Plugin/WorkflowTypeBase.php
+++ b/core/modules/workflows/src/Plugin/WorkflowTypeBase.php
@@ -58,6 +58,20 @@ public function checkWorkflowAccess(WorkflowInterface $entity, $operation, Accou
   /**
    * {@inheritdoc}
    */
+  public function isWorkflowUsed(WorkflowInterface $workflow) {
+    return FALSE;
+  }
+
+  /**
+   * {@inheritdoc}
+   */
+  public function isWorkflowStateUsed(WorkflowInterface $workflow, StateInterface $state) {
+    return FALSE;
+  }
+
+  /**
+   * {@inheritdoc}
+   */
   public function decorateState(StateInterface $state) {
     return $state;
   }
diff --git a/core/modules/workflows/src/WorkflowAccessControlHandler.php b/core/modules/workflows/src/WorkflowAccessControlHandler.php
index 156f0091cc..ea5aad4b8a 100644
--- a/core/modules/workflows/src/WorkflowAccessControlHandler.php
+++ b/core/modules/workflows/src/WorkflowAccessControlHandler.php
@@ -65,11 +65,15 @@ protected function checkAccess(EntityInterface $entity, $operation, AccountInter
       $admin_access = AccessResult::allowedIf(count($entity->getStates()) > 1)
         ->andIf(parent::checkAccess($entity, 'edit', $account))
         ->andIf(AccessResult::allowedIf(!in_array($state_id, $workflow_type->getRequiredStates(), TRUE)))
+        ->andIf(AccessResult::allowedIf(!$workflow_type->isWorkflowStateUsed($entity, $entity->getState($state_id))))
         ->addCacheableDependency($entity);
     }
     else {
       $admin_access = parent::checkAccess($entity, $operation, $account);
     }
+    if ($operation === 'delete') {
+      $admin_access = $admin_access->orIf(AccessResult::forbiddenIf($workflow_type->isWorkflowUsed($entity)))->setCacheMaxAge(0);
+    }
     return $workflow_type->checkWorkflowAccess($entity, $operation, $account)->orIf($admin_access);
   }
 
diff --git a/core/modules/workflows/src/WorkflowTypeInterface.php b/core/modules/workflows/src/WorkflowTypeInterface.php
index 2412bf99f4..159fe17fc0 100644
--- a/core/modules/workflows/src/WorkflowTypeInterface.php
+++ b/core/modules/workflows/src/WorkflowTypeInterface.php
@@ -57,6 +57,30 @@ public function label();
   public function checkWorkflowAccess(WorkflowInterface $entity, $operation, AccountInterface $account);
 
   /**
+   * Determines if the workflow is being used.
+   *
+   * @param \Drupal\workflows\WorkflowInterface $workflow
+   *   The workflow to check.
+   *
+   * @return bool
+   *   TRUE if the workflow is being used, FALSE if not.
+   */
+  public function isWorkflowUsed(WorkflowInterface $workflow);
+
+  /**
+   * Determines if the workflow state is being used.
+   *
+   * @param \Drupal\workflows\WorkflowInterface $workflow
+   *   The workflow to check.
+   * @param \Drupal\workflows\StateInterface $state
+   *   The workflow state to check.
+   *
+   * @return bool
+   *   TRUE if the workflow state is being used, FALSE if not.
+   */
+  public function isWorkflowStateUsed(WorkflowInterface $workflow, StateInterface $state);
+
+  /**
    * Decorates states so the WorkflowType can add additional information.
    *
    * @param \Drupal\workflows\StateInterface $state
