diff --git a/core/modules/block_content/block_content.install b/core/modules/block_content/block_content.install
index 6af2ac4..c6556e7 100644
--- a/core/modules/block_content/block_content.install
+++ b/core/modules/block_content/block_content.install
@@ -6,6 +6,23 @@
  */
 
 use Drupal\Core\Field\BaseFieldDefinition;
+use Drupal\Core\StringTranslation\TranslatableMarkup;
+
+/**
+ * Implements hook_update_dependencies().
+ */
+function block_content_update_dependencies() {
+  // The update function that adds the status field must run after
+  // content_translation_update_8400() which fixes NULL values for the
+  // 'content_translation_status' field.
+  if (\Drupal::moduleHandler()->moduleExists('content_translation')) {
+    $dependencies['block_content'][8400] = [
+      'content_translation' => 8400,
+    ];
+
+    return $dependencies;
+  }
+}
 
 /**
  * Add 'revision_translation_affected' field to 'block_content' entities.
@@ -70,5 +87,54 @@ function block_content_update_8300() {
   $entity_type = $definition_update_manager->getEntityType('block_content');
   $entity_type->set('revision_data_table', 'block_content_field_revision');
   $definition_update_manager->updateEntityType($entity_type);
+}
+
+/**
+ * Add a publishing status field for block_content entities.
+ */
+function block_content_update_8400() {
+  $definition_update_manager = \Drupal::entityDefinitionUpdateManager();
+
+  // Add the published entity key to the block_content entity type.
+  $entity_type = $definition_update_manager->getEntityType('block_content');
+  $entity_keys = $entity_type->getKeys();
+  $entity_keys['published'] = 'status';
+  $entity_type->set('entity_keys', $entity_keys);
+  $definition_update_manager->updateEntityType($entity_type);
+
+  // Add the publishing status field to the block_content entity type.
+  $status = BaseFieldDefinition::create('boolean')
+    ->setLabel(new TranslatableMarkup('Publishing status'))
+    ->setDescription(new TranslatableMarkup('A boolean indicating the published state.'))
+    ->setRevisionable(TRUE)
+    ->setTranslatable(TRUE)
+    ->setDefaultValue(TRUE);
+
+  $has_content_translation_status_field = \Drupal::moduleHandler()->moduleExists('content_translation') && $definition_update_manager->getFieldStorageDefinition('content_translation_status', 'block_content');
+  if ($has_content_translation_status_field) {
+    $status->setInitialValueFromField('content_translation_status');
+  }
+  else {
+    $status->setInitialValue(TRUE);
+  }
+  $definition_update_manager->installFieldStorageDefinition('status', 'block_content', 'block_content', $status);
+
+  // Uninstall the 'content_translation_status' field if needed.
+  $database = \Drupal::database();
+  if ($has_content_translation_status_field) {
+    // First we have to remove the field data.
+    $database->update($entity_type->getDataTable())
+      ->fields(['content_translation_status' => NULL])
+      ->execute();
+
+    // A site may have disabled revisionability for this entity type.
+    if ($entity_type->isRevisionable()) {
+      $database->update($entity_type->getRevisionDataTable())
+        ->fields(['content_translation_status' => NULL])
+        ->execute();
+    }
 
+    $content_translation_status = $definition_update_manager->getFieldStorageDefinition('content_translation_status', 'block_content');
+    $definition_update_manager->uninstallFieldStorageDefinition($content_translation_status);
+  }
 }
diff --git a/core/modules/block_content/src/BlockContentAccessControlHandler.php b/core/modules/block_content/src/BlockContentAccessControlHandler.php
index d0c19c5..7079ef4 100644
--- a/core/modules/block_content/src/BlockContentAccessControlHandler.php
+++ b/core/modules/block_content/src/BlockContentAccessControlHandler.php
@@ -19,7 +19,8 @@ class BlockContentAccessControlHandler extends EntityAccessControlHandler {
    */
   protected function checkAccess(EntityInterface $entity, $operation, AccountInterface $account) {
     if ($operation === 'view') {
-      return AccessResult::allowed();
+      return AccessResult::allowedIf($entity->isPublished())->addCacheableDependency($entity)
+        ->orIf(AccessResult::allowedIfHasPermission($account, 'administer blocks'));
     }
     return parent::checkAccess($entity, $operation, $account);
   }
diff --git a/core/modules/block_content/src/BlockContentInterface.php b/core/modules/block_content/src/BlockContentInterface.php
index 130cae1..75fdc59 100644
--- a/core/modules/block_content/src/BlockContentInterface.php
+++ b/core/modules/block_content/src/BlockContentInterface.php
@@ -4,12 +4,13 @@
 
 use Drupal\Core\Entity\ContentEntityInterface;
 use Drupal\Core\Entity\EntityChangedInterface;
+use Drupal\Core\Entity\EntityPublishedInterface;
 use Drupal\Core\Entity\RevisionLogInterface;
 
 /**
  * Provides an interface defining a custom block entity.
  */
-interface BlockContentInterface extends ContentEntityInterface, EntityChangedInterface, RevisionLogInterface {
+interface BlockContentInterface extends ContentEntityInterface, EntityChangedInterface, RevisionLogInterface, EntityPublishedInterface {
 
   /**
    * Returns the block revision log message.
diff --git a/core/modules/block_content/src/Entity/BlockContent.php b/core/modules/block_content/src/Entity/BlockContent.php
index 76071df..7430fd9 100644
--- a/core/modules/block_content/src/Entity/BlockContent.php
+++ b/core/modules/block_content/src/Entity/BlockContent.php
@@ -2,8 +2,7 @@
 
 namespace Drupal\block_content\Entity;
 
-use Drupal\Core\Entity\ContentEntityBase;
-use Drupal\Core\Entity\EntityChangedTrait;
+use Drupal\Core\Entity\EditorialContentEntityBase;
 use Drupal\Core\Entity\EntityStorageInterface;
 use Drupal\Core\Entity\EntityTypeInterface;
 use Drupal\Core\Field\BaseFieldDefinition;
@@ -51,7 +50,8 @@
  *     "bundle" = "type",
  *     "label" = "info",
  *     "langcode" = "langcode",
- *     "uuid" = "uuid"
+ *     "uuid" = "uuid",
+ *     "published" = "status",
  *   },
  *   revision_metadata_keys = {
  *     "revision_user" = "revision_user",
@@ -68,9 +68,7 @@
  * caching.
  * See https://www.drupal.org/node/2284917#comment-9132521 for more information.
  */
-class BlockContent extends ContentEntityBase implements BlockContentInterface {
-
-  use EntityChangedTrait;
+class BlockContent extends EditorialContentEntityBase implements BlockContentInterface {
 
   /**
    * The theme the block is being created in.
@@ -174,6 +172,8 @@ public static function baseFieldDefinitions(EntityTypeInterface $entity_type) {
     $fields['type']->setLabel(t('Block type'))
       ->setDescription(t('The block type.'));
 
+    $fields['revision_log']->setDescription(t('The log entry explaining the changes in this revision.'));
+
     $fields['info'] = BaseFieldDefinition::create('string')
       ->setLabel(t('Block description'))
       ->setDescription(t('A brief description of your block.'))
@@ -187,35 +187,12 @@ public static function baseFieldDefinitions(EntityTypeInterface $entity_type) {
       ->setDisplayConfigurable('form', TRUE)
       ->addConstraint('UniqueField', []);
 
-    $fields['revision_log'] = BaseFieldDefinition::create('string_long')
-      ->setLabel(t('Revision log message'))
-      ->setDescription(t('The log entry explaining the changes in this revision.'))
-      ->setRevisionable(TRUE)
-      ->setDisplayOptions('form', [
-        'type' => 'string_textarea',
-        'weight' => 25,
-        'settings' => [
-          'rows' => 4,
-        ],
-      ]);
-
     $fields['changed'] = BaseFieldDefinition::create('changed')
       ->setLabel(t('Changed'))
       ->setDescription(t('The time that the custom block was last edited.'))
       ->setTranslatable(TRUE)
       ->setRevisionable(TRUE);
 
-    $fields['revision_created'] = BaseFieldDefinition::create('created')
-      ->setLabel(t('Revision create time'))
-      ->setDescription(t('The time that the current revision was created.'))
-      ->setRevisionable(TRUE);
-
-    $fields['revision_user'] = BaseFieldDefinition::create('entity_reference')
-      ->setLabel(t('Revision user'))
-      ->setDescription(t('The user ID of the author of the current revision.'))
-      ->setSetting('target_type', 'user')
-      ->setRevisionable(TRUE);
-
     $fields['revision_translation_affected'] = BaseFieldDefinition::create('boolean')
       ->setLabel(t('Revision translation affected'))
       ->setDescription(t('Indicates if the last edit of a translation belongs to current revision.'))
diff --git a/core/modules/block_content/src/Tests/BlockContentUpdateTest.php b/core/modules/block_content/src/Tests/Update/BlockContentUpdateTest.php
similarity index 57%
rename from core/modules/block_content/src/Tests/BlockContentUpdateTest.php
rename to core/modules/block_content/src/Tests/Update/BlockContentUpdateTest.php
index 77c12c6..888607e 100644
--- a/core/modules/block_content/src/Tests/BlockContentUpdateTest.php
+++ b/core/modules/block_content/src/Tests/Update/BlockContentUpdateTest.php
@@ -1,6 +1,6 @@
 <?php
 
-namespace Drupal\block_content\Tests;
+namespace Drupal\block_content\Tests\Update;
 
 use Drupal\Core\Field\BaseFieldDefinition;
 use Drupal\system\Tests\Update\UpdatePathTestBase;
@@ -8,6 +8,7 @@
 /**
  * Tests update functions for the Block Content module.
  *
+ * @group block_content
  * @group Update
  */
 class BlockContentUpdateTest extends UpdatePathTestBase {
@@ -17,7 +18,7 @@ class BlockContentUpdateTest extends UpdatePathTestBase {
    */
   protected function setDatabaseDumpFiles() {
     $this->databaseDumpFiles = [
-      __DIR__ . '/../../../system/tests/fixtures/update/drupal-8.bare.standard.php.gz',
+      __DIR__ . '/../../../../system/tests/fixtures/update/drupal-8-rc1.filled.standard.php.gz',
     ];
   }
 
@@ -43,4 +44,27 @@ public function testSimpleUpdates() {
     $this->assertEqual('block_content_field_revision', $entity_type->getRevisionDataTable());
   }
 
+  /**
+   * Tests adding a status field to the block content entity type.
+   *
+   * @see block_content_update_8400()
+   */
+  public function testStatusFieldAddition() {
+    $schema = \Drupal::database()->schema();
+    $entity_definition_update_manager = \Drupal::entityDefinitionUpdateManager();
+
+    // Run updates.
+    $this->runUpdates();
+
+    // Check that the field exists and has the correct label.
+    $updated_field = $entity_definition_update_manager->getFieldStorageDefinition('status', 'block_content');
+    $this->assertEqual('Publishing status', $updated_field->getLabel());
+
+    $content_translation_status = $entity_definition_update_manager->getFieldStorageDefinition('content_translation_status', 'block_content');
+    $this->assertNull($content_translation_status);
+
+    $this->assertFalse($schema->fieldExists('block_content_field_revision', 'content_translation_status'));
+    $this->assertFalse($schema->fieldExists('block_content_field_data', 'content_translation_status'));
+  }
+
 }
diff --git a/core/modules/block_content/tests/src/Functional/UnpublishedBlockTest.php b/core/modules/block_content/tests/src/Functional/UnpublishedBlockTest.php
new file mode 100644
index 0000000..026b0e5
--- /dev/null
+++ b/core/modules/block_content/tests/src/Functional/UnpublishedBlockTest.php
@@ -0,0 +1,47 @@
+<?php
+
+namespace Drupal\Tests\block_content\Functional;
+
+use Drupal\block_content\Entity\BlockContent;
+use Drupal\simpletest\BlockCreationTrait;
+use Drupal\Tests\BrowserTestBase;
+
+/**
+ * Tests unpublishing of block_content entities.
+ *
+ * @group block_content
+ */
+class UnpublishedBlockTest extends BrowserTestBase {
+
+  use BlockCreationTrait;
+
+  /**
+   * {@inheritdoc}
+   */
+  public static $modules = ['block_content'];
+
+  /**
+   * Tests unpublishing of block_content entities.
+   */
+  public function testViewShowsCorrectStates() {
+    $block_content = BlockContent::create([
+      'info' => 'Test block',
+      'type' => 'basic',
+    ]);
+    $block_content->save();
+
+    $this->placeBlock('block_content:' . $block_content->uuid());
+
+    $this->drupalGet('<front>');
+    $page = $this->getSession()->getPage();
+    $this->assertTrue($page->has('css', '.block-block-content' . $block_content->uuid()));
+
+    $block_content->setPublished(FALSE);
+    $block_content->save();
+
+    $this->drupalGet('<front>');
+    $page = $this->getSession()->getPage();
+    $this->assertFalse($page->has('css', '.block-block-content' . $block_content->uuid()));
+  }
+
+}
diff --git a/core/modules/content_translation/content_translation.install b/core/modules/content_translation/content_translation.install
index 67b161c..5ee9ea8 100644
--- a/core/modules/content_translation/content_translation.install
+++ b/core/modules/content_translation/content_translation.install
@@ -59,6 +59,7 @@ function content_translation_update_8400() {
   $entity_type_manager = \Drupal::entityTypeManager();
   $entity_definition_update_manager = \Drupal::entityDefinitionUpdateManager();
 
+  $entity_type_manager->clearCachedDefinitions();
   foreach ($content_translation_manager->getSupportedEntityTypes() as $entity_type_id => $entity_type_definition) {
     $storage = $entity_type_manager->getStorage($entity_type_id);
     if ($storage instanceof SqlEntityStorageInterface) {
