From 146a4056ff7c19ecb42fc98b8bf8fc9a822775e6 Mon Sep 17 00:00:00 2001
From: Bram Goffings <bramgoffings@gmail.com>
Date: Mon, 4 Jun 2012 12:59:20 +0200
Subject: [PATCH] merge controllers

---
 .../lib/Drupal/Core/File/FileStorageController.php |   10 +-
 .../Drupal/comment/CommentStorageController.php    |   16 +-
 core/modules/entity/entity.api.php                 |   27 ++--
 core/modules/entity/entity.module                  |   28 ++--
 ...ontroller.php => DatabaseStorageController.php} |  154 +++++++++++++++++++-
 .../Drupal/entity/EntityControllerInterface.php    |   52 -------
 .../entity/EntityDatabaseStorageController.php     |  154 --------------------
 .../entity/EntityStorageControllerInterface.php    |   42 +++++-
 core/modules/entity/tests/entity.test              |    2 +-
 .../tests/modules/entity_test/entity_test.module   |    2 +-
 .../field_test/TestEntityBundleController.php      |    6 +-
 .../node/lib/Drupal/node/NodeStorageController.php |   26 ++--
 core/modules/node/node.api.php                     |    4 +-
 .../lib/Drupal/taxonomy/TermStorageController.php  |   16 +-
 .../taxonomy/VocabularyStorageController.php       |   14 +-
 .../user/lib/Drupal/user/UserStorageController.php |   16 +-
 16 files changed, 274 insertions(+), 295 deletions(-)
 rename core/modules/entity/lib/Drupal/entity/{EntityController.php => DatabaseStorageController.php} (69%)
 delete mode 100644 core/modules/entity/lib/Drupal/entity/EntityControllerInterface.php
 delete mode 100644 core/modules/entity/lib/Drupal/entity/EntityDatabaseStorageController.php

diff --git a/core/lib/Drupal/Core/File/FileStorageController.php b/core/lib/Drupal/Core/File/FileStorageController.php
index deb8eca..940e1fd 100644
--- a/core/lib/Drupal/Core/File/FileStorageController.php
+++ b/core/lib/Drupal/Core/File/FileStorageController.php
@@ -7,16 +7,16 @@
 
 namespace Drupal\Core\File;
 
-use Drupal\entity\EntityDatabaseStorageController;
+use Drupal\entity\DatabaseStorageController;
 use Drupal\entity\EntityInterface;
 
 /**
  * File storage controller for files.
  */
-class FileStorageController extends EntityDatabaseStorageController {
+class FileStorageController extends DatabaseStorageController {
 
   /**
-   * Overrides Drupal\entity\EntityDatabaseStorageController::create().
+   * Overrides Drupal\entity\DatabaseStorageController::create().
    */
   public function create(array $values) {
     // Automatically detect filename if not set.
@@ -32,7 +32,7 @@ class FileStorageController extends EntityDatabaseStorageController {
   }
 
   /**
-   * Overrides Drupal\entity\EntityDatabaseStorageController::presave().
+   * Overrides Drupal\entity\DatabaseStorageController::presave().
    */
   protected function preSave(EntityInterface $entity) {
     $entity->timestamp = REQUEST_TIME;
@@ -47,7 +47,7 @@ class FileStorageController extends EntityDatabaseStorageController {
   }
 
   /**
-   * Overrides Drupal\entity\EntityDatabaseStorageController::preDelete().
+   * Overrides Drupal\entity\DatabaseStorageController::preDelete().
    */
   public function preDelete($entities) {
     foreach ($entities as $entity) {
diff --git a/core/modules/comment/lib/Drupal/comment/CommentStorageController.php b/core/modules/comment/lib/Drupal/comment/CommentStorageController.php
index 961c2f1..b25fb39 100644
--- a/core/modules/comment/lib/Drupal/comment/CommentStorageController.php
+++ b/core/modules/comment/lib/Drupal/comment/CommentStorageController.php
@@ -8,18 +8,18 @@
 namespace Drupal\comment;
 
 use Drupal\entity\EntityInterface;
-use Drupal\entity\EntityDatabaseStorageController;
+use Drupal\entity\DatabaseStorageController;
 
 /**
  * Defines the controller class for comments.
  *
- * This extends the Drupal\entity\EntityDatabaseStorageController class, adding
+ * This extends the Drupal\entity\DatabaseStorageController class, adding
  * required special handling for comment entities.
  */
-class CommentStorageController extends EntityDatabaseStorageController {
+class CommentStorageController extends DatabaseStorageController {
 
   /**
-   * Overrides Drupal\entity\EntityDatabaseStorageController::buildQuery().
+   * Overrides Drupal\entity\DatabaseStorageController::buildQuery().
    */
   protected function buildQuery($ids, $conditions = array(), $revision_id = FALSE) {
     $query = parent::buildQuery($ids, $conditions, $revision_id);
@@ -33,7 +33,7 @@ class CommentStorageController extends EntityDatabaseStorageController {
   }
 
   /**
-   * Overrides Drupal\entity\EntityDatabaseStorageController::attachLoad().
+   * Overrides Drupal\entity\DatabaseStorageController::attachLoad().
    */
   protected function attachLoad(&$comments, $revision_id = FALSE) {
     // Set up standard comment properties.
@@ -47,7 +47,7 @@ class CommentStorageController extends EntityDatabaseStorageController {
   }
 
   /**
-   * Overrides Drupal\entity\EntityDatabaseStorageController::preSave().
+   * Overrides Drupal\entity\DatabaseStorageController::preSave().
    *
    * @see comment_int_to_alphadecimal()
    * @see comment_increment_alphadecimal()
@@ -129,7 +129,7 @@ class CommentStorageController extends EntityDatabaseStorageController {
   }
 
   /**
-   * Overrides Drupal\entity\EntityDatabaseStorageController::postSave().
+   * Overrides Drupal\entity\DatabaseStorageController::postSave().
    */
   protected function postSave(EntityInterface $comment, $update) {
     // Update the {node_comment_statistics} table prior to executing the hook.
@@ -140,7 +140,7 @@ class CommentStorageController extends EntityDatabaseStorageController {
   }
 
   /**
-   * Overrides Drupal\entity\EntityDatabaseStorageController::postDelete().
+   * Overrides Drupal\entity\DatabaseStorageController::postDelete().
    */
   protected function postDelete($comments) {
     // Delete the comments' replies.
diff --git a/core/modules/entity/entity.api.php b/core/modules/entity/entity.api.php
index 87115bd..37263a6 100644
--- a/core/modules/entity/entity.api.php
+++ b/core/modules/entity/entity.api.php
@@ -21,20 +21,24 @@
  *   An array whose keys are entity type names and whose values identify
  *   properties of those types that the system needs to know about:
  *   - label: The human-readable name of the type.
+ *   - entity class: The name of the entity class, defaults to
+ *     Drupal\entity\Entity. The entity class must implement EntityInterface.
  *   - controller class: The name of the class that is used to load the objects.
- *     The class has to implement the Drupal\entity\EntityControllerInterface
- *     interface. Leave blank to use the Drupal\entity\EntityController
- *     implementation.
- *   - base table: (used by Drupal\entity\EntityController) The name of the
- *     entity type's base table.
- *   - static cache: (used by Drupal\entity\EntityController) FALSE to disable
- *     static caching of entities during a page request. Defaults to TRUE.
+ *     The class has to implement the
+ *     Drupal\entity\EntityStorageControllerInterface interface. Leave blank
+ *     to use the Drupal\entity\DatabaseStorageController implementation.
+ *   - base table: (used by Drupal\entity\DatabaseStorageController) The
+ *     name of the entity type's base table.
+ *   - static cache: (used by Drupal\entity\DatabaseStorageController)
+ *     FALSE to disable static caching of entities during a page request.
+ *     Defaults to TRUE.
  *   - field cache: (used by Field API loading and saving of field data) FALSE
  *     to disable Field API's persistent cache of field data. Only recommended
  *     if a higher level persistent cache is available for the entity type.
  *     Defaults to TRUE.
  *   - load hook: The name of the hook which should be invoked by
- *     Drupal\entity\EntityController::attachLoad(), for example 'node_load'.
+ *     Drupal\entity\DatabaseStorageController::attachLoad(), for example
+ *     'node_load'.
  *   - uri callback: A function taking an entity as argument and returning the
  *     uri elements of the entity, e.g. 'path' and 'options'. The actual entity
  *     uri can be constructed by passing these elements to url().
@@ -131,7 +135,8 @@ function hook_entity_info() {
   $return = array(
     'node' => array(
       'label' => t('Node'),
-      'controller class' => 'NodeController',
+      'entity class' => 'Drupal\node\Node',
+      'controller class' => 'Drupal\node\NodeStorageController',
       'base table' => 'node',
       'revision table' => 'node_revision',
       'uri callback' => 'node_uri',
@@ -211,8 +216,8 @@ function hook_entity_info() {
  */
 function hook_entity_info_alter(&$entity_info) {
   // Set the controller class for nodes to an alternate implementation of the
-  // Drupal\entity\EntityController interface.
-  $entity_info['node']['controller class'] = 'Drupal\mymodule\MyCustomNodeController';
+  // Drupal\entity\EntityStorageControllerInterface interface.
+  $entity_info['node']['controller class'] = 'Drupal\mymodule\MyCustomNodeStorageController';
 }
 
 /**
diff --git a/core/modules/entity/entity.module b/core/modules/entity/entity.module
index c167bd4..84153f6 100644
--- a/core/modules/entity/entity.module
+++ b/core/modules/entity/entity.module
@@ -68,7 +68,8 @@ function entity_get_info($entity_type = NULL) {
       foreach ($entity_info as $name => $data) {
         $entity_info[$name] += array(
           'fieldable' => FALSE,
-          'controller class' => 'Drupal\entity\EntityController',
+          'entity class' => 'Drupal\entity\Entity',
+          'controller class' => 'Drupal\entity\DatabaseStorageController',
           'static cache' => TRUE,
           'field cache' => TRUE,
           'load hook' => $name . '_load',
@@ -92,7 +93,7 @@ function entity_get_info($entity_type = NULL) {
           $entity_info[$name]['bundles'] = array($name => array('label' => $entity_info[$name]['label']));
         }
         // Prepare entity schema fields SQL info for
-        // Drupal\entity\EntityControllerInterface::buildQuery().
+        // Drupal\entity\DatabaseStorageControllerInterface::buildQuery().
         if (isset($entity_info[$name]['base table'])) {
           $entity_info[$name]['schema_fields_sql']['base table'] = drupal_schema_fields_sql($entity_info[$name]['base table']);
           if (isset($entity_info[$name]['revision table'])) {
@@ -206,8 +207,8 @@ function entity_create_stub_entity($entity_type, $ids) {
  *
  * @see hook_entity_info()
  * @see entity_load_multiple()
- * @see Drupal\entity\EntityControllerInterface
- * @see Drupal\entity\EntityController
+ * @see Drupal\entity\EntityStorageControllerInterface
+ * @see Drupal\entity\DatabaseStorageController
  * @see Drupal\entity\EntityFieldQuery
  */
 function entity_load($entity_type, $id, $reset = FALSE) {
@@ -223,13 +224,14 @@ function entity_load($entity_type, $id, $reset = FALSE) {
  * database access if loaded again during the same page request.
  *
  * The actual loading is done through a class that has to implement the
- * Drupal\entity\EntityControllerInterface interface. By default,
- * Drupal\entity\EntityController is used. Entity types can specify
- * that a different class should be used by setting the 'controller class' key
- * in hook_entity_info(). These classes can either implement the
- * Drupal\entity\EntityControllerInterface interface, or, most
- * commonly, extend the Drupal\entity\EntityController class. See
- * node_entity_info() and the NodeController in node.module as an example.
+ * Drupal\entity\EntityStorageControllerInterface interface. By default,
+ * Drupal\entity\DatabaseStorageController is used. Entity types can
+ * specify that a different class should be used by setting the
+ * 'controller class' key in hook_entity_info(). These classes can either
+ * implement the Drupal\entity\EntityStorageControllerInterface interface, or,
+ * most commonly, extend the Drupal\entity\DatabaseStorageController
+ * class. See node_entity_info() and the NodeController in node.module as an
+ * example.
  *
  * @param string $entity_type
  *   The entity type to load, e.g. node or user.
@@ -249,8 +251,8 @@ function entity_load($entity_type, $id, $reset = FALSE) {
  * @todo Remove $conditions in Drupal 8.
  *
  * @see hook_entity_info()
- * @see Drupal\entity\EntityControllerInterface
- * @see Drupal\entity\EntityController
+ * @see Drupal\entity\EntityStorageControllerInterface
+ * @see Drupal\entity\DatabaseStorageController
  * @see Drupal\entity\EntityFieldQuery
  */
 function entity_load_multiple($entity_type, $ids = FALSE, $conditions = array(), $reset = FALSE) {
diff --git a/core/modules/entity/lib/Drupal/entity/EntityController.php b/core/modules/entity/lib/Drupal/entity/DatabaseStorageController.php
similarity index 69%
rename from core/modules/entity/lib/Drupal/entity/EntityController.php
rename to core/modules/entity/lib/Drupal/entity/DatabaseStorageController.php
index 3edc4cc..20e303e 100644
--- a/core/modules/entity/lib/Drupal/entity/EntityController.php
+++ b/core/modules/entity/lib/Drupal/entity/DatabaseStorageController.php
@@ -2,7 +2,7 @@
 
 /**
  * @file
- * Definition of Drupal\entity\EntityController.
+ * Definition of Drupal\entity\DatabaseStorageController.
  */
 
 namespace Drupal\entity;
@@ -12,12 +12,12 @@ use PDO;
 /**
  * Defines a base entity controller class.
  *
- * Default implementation of Drupal\entity\EntityControllerInterface.
+ * Default implementation of Drupal\entity\DatabaseStorageControllerInterface.
  *
  * This class can be used as-is by most simple entity types. Entity types
  * requiring special handling can extend the class.
  */
-class EntityController implements EntityControllerInterface {
+class DatabaseStorageController implements EntityStorageControllerInterface {
 
   /**
    * Static cache of entities.
@@ -45,7 +45,7 @@ class EntityController implements EntityControllerInterface {
   /**
    * Additional arguments to pass to hook_TYPE_load().
    *
-   * Set before calling Drupal\entity\EntityController::attachLoad().
+   * Set before calling Drupal\entity\DatabaseStorageController::attachLoad().
    *
    * @var array
    */
@@ -84,7 +84,7 @@ class EntityController implements EntityControllerInterface {
   protected $cache;
 
   /**
-   * Implements Drupal\entity\EntityController::__construct().
+   * Implements Drupal\entity\EntityStorageControllerInterface::__construct().
    *
    * Sets basic variables.
    */
@@ -109,7 +109,7 @@ class EntityController implements EntityControllerInterface {
   }
 
   /**
-   * Implements Drupal\entity\EntityControllerInterface::resetCache().
+   * Implements Drupal\entity\EntityStorageControllerInterface::resetCache().
    */
   public function resetCache(array $ids = NULL) {
     if (isset($ids)) {
@@ -123,7 +123,7 @@ class EntityController implements EntityControllerInterface {
   }
 
   /**
-   * Implements Drupal\entity\EntityControllerInterface::load().
+   * Implements Drupal\entity\EntityStorageControllerInterface::load().
    */
   public function load($ids = array(), $conditions = array()) {
     $entities = array();
@@ -356,4 +356,144 @@ class EntityController implements EntityControllerInterface {
   protected function cacheSet($entities) {
     $this->entityCache += $entities;
   }
+
+  /**
+   * Implements Drupal\entity\EntityStorageControllerInterface::create().
+   */
+  public function create(array $values) {
+    $class = isset($this->entityInfo['entity class']) ? $this->entityInfo['entity class'] : 'Drupal\entity\Entity';
+    return new $class($values, $this->entityType);
+  }
+
+  /**
+   * Implements Drupal\entity\EntityStorageControllerInterface::delete().
+   */
+  public function delete($ids) {
+    $entities = $ids ? $this->load($ids) : FALSE;
+    if (!$entities) {
+      // If no IDs or invalid IDs were passed, do nothing.
+      return;
+    }
+    $transaction = db_transaction();
+
+    try {
+      $this->preDelete($entities);
+      foreach ($entities as $id => $entity) {
+        $this->invokeHook('predelete', $entity);
+      }
+      $ids = array_keys($entities);
+
+      db_delete($this->entityInfo['base table'])
+        ->condition($this->idKey, $ids, 'IN')
+        ->execute();
+      // Reset the cache as soon as the changes have been applied.
+      $this->resetCache($ids);
+
+      $this->postDelete($entities);
+      foreach ($entities as $id => $entity) {
+        $this->invokeHook('delete', $entity);
+      }
+      // Ignore slave server temporarily.
+      db_ignore_slave();
+    }
+    catch (Exception $e) {
+      $transaction->rollback();
+      watchdog_exception($this->entityType, $e);
+      throw new EntityStorageException($e->getMessage, $e->getCode, $e);
+    }
+  }
+
+  /**
+   * Implements Drupal\entity\EntityStorageControllerInterface::save().
+   */
+  public function save(EntityInterface $entity) {
+    $transaction = db_transaction();
+    try {
+      // Load the stored entity, if any.
+      if (!$entity->isNew() && !isset($entity->original)) {
+        $entity->original = entity_load_unchanged($this->entityType, $entity->id());
+      }
+
+      $this->preSave($entity);
+      $this->invokeHook('presave', $entity);
+
+      if (!$entity->isNew()) {
+        $return = drupal_write_record($this->entityInfo['base table'], $entity, $this->idKey);
+        $this->resetCache(array($entity->{$this->idKey}));
+        $this->postSave($entity, TRUE);
+        $this->invokeHook('update', $entity);
+      }
+      else {
+        $return = drupal_write_record($this->entityInfo['base table'], $entity);
+        // Reset general caches, but keep caches specific to certain entities.
+        $this->resetCache(array());
+
+        $entity->enforceIsNew(FALSE);
+        $this->postSave($entity, FALSE);
+        $this->invokeHook('insert', $entity);
+      }
+
+      // Ignore slave server temporarily.
+      db_ignore_slave();
+      unset($entity->original);
+
+      return $return;
+    }
+    catch (Exception $e) {
+      $transaction->rollback();
+      watchdog_exception($this->entityType, $e);
+      throw new EntityStorageException($e->getMessage(), $e->getCode(), $e);
+    }
+  }
+
+  /**
+   * Acts on an entity before the presave hook is invoked.
+   *
+   * Used before the entity is saved and before invoking the presave hook.
+   */
+  protected function preSave(EntityInterface $entity) { }
+
+  /**
+   * Acts on a saved entity before the insert or update hook is invoked.
+   *
+   * Used after the entity is saved, but before invoking the insert or update
+   * hook.
+   *
+   * @param $update
+   *   (bool) TRUE if the entity has been updated, or FALSE if it has been
+   *   inserted.
+   */
+  protected function postSave(EntityInterface $entity, $update) { }
+
+  /**
+   * Acts on entities before they are deleted.
+   *
+   * Used before the entities are deleted and before invoking the delete hook.
+   */
+  protected function preDelete($entities) { }
+
+  /**
+   * Acts on deleted entities before the delete hook is invoked.
+   *
+   * Used after the entities are deleted but before invoking the delete hook.
+   */
+  protected function postDelete($entities) { }
+
+  /**
+   * Invokes a hook on behalf of the entity.
+   *
+   * @param $hook
+   *   One of 'presave', 'insert', 'update', 'predelete', or 'delete'.
+   * @param $entity
+   *   The entity object.
+   */
+  protected function invokeHook($hook, EntityInterface $entity) {
+    if (!empty($this->entityInfo['fieldable']) && function_exists($function = 'field_attach_' . $hook)) {
+      $function($this->entityType, $entity);
+    }
+    // Invoke the hook.
+    module_invoke_all($this->entityType . '_' . $hook, $entity);
+    // Invoke the respective entity-level hook.
+    module_invoke_all('entity_' . $hook, $entity, $this->entityType);
+  }
 }
diff --git a/core/modules/entity/lib/Drupal/entity/EntityControllerInterface.php b/core/modules/entity/lib/Drupal/entity/EntityControllerInterface.php
deleted file mode 100644
index 703094f..0000000
--- a/core/modules/entity/lib/Drupal/entity/EntityControllerInterface.php
+++ /dev/null
@@ -1,52 +0,0 @@
-<?php
-
-/**
- * @file
- * Definition of Drupal\entity\EntityControllerInterface.
- */
-
-namespace Drupal\entity;
-
-/**
- * Defines a common interface for entity controller classes.
- *
- * All entity controller classes specified via the 'controller class' key
- * returned by hook_entity_info() or hook_entity_info_alter() have to implement
- * this interface.
- *
- * Most simple, SQL-based entity controllers will do better by extending
- * Drupal\entity\EntityController instead of implementing this interface
- * directly.
- */
-interface EntityControllerInterface {
-
-  /**
-   * Constructs a new Drupal\entity\EntityControllerInterface object.
-   *
-   * @param $entityType
-   *   The entity type for which the instance is created.
-   */
-  public function __construct($entityType);
-
-  /**
-   * Resets the internal, static entity cache.
-   *
-   * @param $ids
-   *   (optional) If specified, the cache is reset for the entities with the
-   *   given ids only.
-   */
-  public function resetCache(array $ids = NULL);
-
-  /**
-   * Loads one or more entities.
-   *
-   * @param $ids
-   *   An array of entity IDs, or FALSE to load all entities.
-   * @param $conditions
-   *   An array of conditions in the form 'field' => $value.
-   *
-   * @return
-   *   An array of entity objects indexed by their ids.
-   */
-  public function load($ids = array(), $conditions = array());
-}
diff --git a/core/modules/entity/lib/Drupal/entity/EntityDatabaseStorageController.php b/core/modules/entity/lib/Drupal/entity/EntityDatabaseStorageController.php
deleted file mode 100644
index 13a529a..0000000
--- a/core/modules/entity/lib/Drupal/entity/EntityDatabaseStorageController.php
+++ /dev/null
@@ -1,154 +0,0 @@
-<?php
-
-/**
- * @file
- * Definition of Drupal\entity\EntityDatabaseStorageController.
- */
-
-namespace Drupal\entity;
-
-/**
- * Implements the entity storage controller interface for the database.
- */
-class EntityDatabaseStorageController extends EntityController implements EntityStorageControllerInterface {
-
-  /**
-   * Implements Drupal\entity\EntityStorageControllerInterface::create().
-   */
-  public function create(array $values) {
-    $class = isset($this->entityInfo['entity class']) ? $this->entityInfo['entity class'] : 'Drupal\entity\Entity';
-    return new $class($values, $this->entityType);
-  }
-
-  /**
-   * Implements Drupal\entity\EntityStorageControllerInterface::delete().
-   */
-  public function delete($ids) {
-    $entities = $ids ? $this->load($ids) : FALSE;
-    if (!$entities) {
-      // If no IDs or invalid IDs were passed, do nothing.
-      return;
-    }
-    $transaction = db_transaction();
-
-    try {
-      $this->preDelete($entities);
-      foreach ($entities as $id => $entity) {
-        $this->invokeHook('predelete', $entity);
-      }
-      $ids = array_keys($entities);
-
-      db_delete($this->entityInfo['base table'])
-        ->condition($this->idKey, $ids, 'IN')
-        ->execute();
-      // Reset the cache as soon as the changes have been applied.
-      $this->resetCache($ids);
-
-      $this->postDelete($entities);
-      foreach ($entities as $id => $entity) {
-        $this->invokeHook('delete', $entity);
-      }
-      // Ignore slave server temporarily.
-      db_ignore_slave();
-    }
-    catch (Exception $e) {
-      $transaction->rollback();
-      watchdog_exception($this->entityType, $e);
-      throw new EntityStorageException($e->getMessage, $e->getCode, $e);
-    }
-  }
-
-  /**
-   * Implements Drupal\entity\EntityStorageControllerInterface::save().
-   */
-  public function save(EntityInterface $entity) {
-    $transaction = db_transaction();
-    try {
-      // Load the stored entity, if any.
-      if (!$entity->isNew() && !isset($entity->original)) {
-        $entity->original = entity_load_unchanged($this->entityType, $entity->id());
-      }
-
-      $this->preSave($entity);
-      $this->invokeHook('presave', $entity);
-
-      if (!$entity->isNew()) {
-        $return = drupal_write_record($this->entityInfo['base table'], $entity, $this->idKey);
-        $this->resetCache(array($entity->{$this->idKey}));
-        $this->postSave($entity, TRUE);
-        $this->invokeHook('update', $entity);
-      }
-      else {
-        $return = drupal_write_record($this->entityInfo['base table'], $entity);
-        // Reset general caches, but keep caches specific to certain entities.
-        $this->resetCache(array());
-
-        $entity->enforceIsNew(FALSE);
-        $this->postSave($entity, FALSE);
-        $this->invokeHook('insert', $entity);
-      }
-
-      // Ignore slave server temporarily.
-      db_ignore_slave();
-      unset($entity->original);
-
-      return $return;
-    }
-    catch (Exception $e) {
-      $transaction->rollback();
-      watchdog_exception($this->entityType, $e);
-      throw new EntityStorageException($e->getMessage(), $e->getCode(), $e);
-    }
-  }
-
-  /**
-   * Acts on an entity before the presave hook is invoked.
-   *
-   * Used before the entity is saved and before invoking the presave hook.
-   */
-  protected function preSave(EntityInterface $entity) { }
-
-  /**
-   * Acts on a saved entity before the insert or update hook is invoked.
-   *
-   * Used after the entity is saved, but before invoking the insert or update
-   * hook.
-   *
-   * @param $update
-   *   (bool) TRUE if the entity has been updated, or FALSE if it has been
-   *   inserted.
-   */
-  protected function postSave(EntityInterface $entity, $update) { }
-
-  /**
-   * Acts on entities before they are deleted.
-   *
-   * Used before the entities are deleted and before invoking the delete hook.
-   */
-  protected function preDelete($entities) { }
-
-  /**
-   * Acts on deleted entities before the delete hook is invoked.
-   *
-   * Used after the entities are deleted but before invoking the delete hook.
-   */
-  protected function postDelete($entities) { }
-
-  /**
-   * Invokes a hook on behalf of the entity.
-   *
-   * @param $hook
-   *   One of 'presave', 'insert', 'update', 'predelete', or 'delete'.
-   * @param $entity
-   *   The entity object.
-   */
-  protected function invokeHook($hook, EntityInterface $entity) {
-    if (!empty($this->entityInfo['fieldable']) && function_exists($function = 'field_attach_' . $hook)) {
-      $function($this->entityType, $entity);
-    }
-    // Invoke the hook.
-    module_invoke_all($this->entityType . '_' . $hook, $entity);
-    // Invoke the respective entity-level hook.
-    module_invoke_all('entity_' . $hook, $entity, $this->entityType);
-  }
-}
diff --git a/core/modules/entity/lib/Drupal/entity/EntityStorageControllerInterface.php b/core/modules/entity/lib/Drupal/entity/EntityStorageControllerInterface.php
index cacc57c..7f27e96 100644
--- a/core/modules/entity/lib/Drupal/entity/EntityStorageControllerInterface.php
+++ b/core/modules/entity/lib/Drupal/entity/EntityStorageControllerInterface.php
@@ -8,9 +8,47 @@
 namespace Drupal\entity;
 
 /**
- * Defines a common interface for entity storage controllers.
+ * Defines a common interface for entity controller classes.
+ *
+ * All entity controller classes specified via the 'controller class' key
+ * returned by hook_entity_info() or hook_entity_info_alter() have to implement
+ * this interface.
+ *
+ * Most simple, SQL-based entity controllers will do better by extending
+ * Drupal\entity\DatabaseStorageController instead of implementing this
+ * interface directly.
  */
-interface EntityStorageControllerInterface extends EntityControllerInterface {
+interface EntityStorageControllerInterface {
+
+  /**
+   * Constructs a new Drupal\entity\EntityStorageControllerInterface object.
+   *
+   * @param $entityType
+   *   The entity type for which the instance is created.
+   */
+  public function __construct($entityType);
+
+  /**
+   * Resets the internal, static entity cache.
+   *
+   * @param $ids
+   *   (optional) If specified, the cache is reset for the entities with the
+   *   given ids only.
+   */
+  public function resetCache(array $ids = NULL);
+
+  /**
+   * Loads one or more entities.
+   *
+   * @param $ids
+   *   An array of entity IDs, or FALSE to load all entities.
+   * @param $conditions
+   *   An array of conditions in the form 'field' => $value.
+   *
+   * @return
+   *   An array of entity objects indexed by their ids.
+   */
+  public function load($ids = array(), $conditions = array());
 
   /**
    * Constructs a new entity object, without permanently saving it.
diff --git a/core/modules/entity/tests/entity.test b/core/modules/entity/tests/entity.test
index 1047279..0f36d44 100644
--- a/core/modules/entity/tests/entity.test
+++ b/core/modules/entity/tests/entity.test
@@ -243,6 +243,6 @@ class EntityAPIInfoTestCase extends WebTestBase  {
     module_enable(array('entity_cache_test'));
     $info = variable_get('entity_cache_test');
     $this->assertEqual($info['label'], 'Entity Cache Test', 'Entity info label is correct.');
-    $this->assertEqual($info['controller class'], 'Drupal\entity\EntityController', 'Entity controller class info is correct.');
+    $this->assertEqual($info['controller class'], 'Drupal\entity\DatabaseStorageController', 'Entity controller class info is correct.');
   }
 }
diff --git a/core/modules/entity/tests/modules/entity_test/entity_test.module b/core/modules/entity/tests/modules/entity_test/entity_test.module
index 25def33..f97d2e9 100644
--- a/core/modules/entity/tests/modules/entity_test/entity_test.module
+++ b/core/modules/entity/tests/modules/entity_test/entity_test.module
@@ -12,7 +12,7 @@ function entity_test_entity_info() {
   $items['entity_test'] = array(
     'label' => t('Test entity'),
     'entity class' => 'Drupal\entity\Entity',
-    'controller class' => 'Drupal\entity\EntityDatabaseStorageController',
+    'controller class' => 'Drupal\entity\DatabaseStorageController',
     'base table' => 'entity_test',
     'fieldable' => TRUE,
     'entity keys' => array(
diff --git a/core/modules/field/tests/modules/field_test/lib/Drupal/field_test/TestEntityBundleController.php b/core/modules/field/tests/modules/field_test/lib/Drupal/field_test/TestEntityBundleController.php
index 7f74b9b..72996c5 100644
--- a/core/modules/field/tests/modules/field_test/lib/Drupal/field_test/TestEntityBundleController.php
+++ b/core/modules/field/tests/modules/field_test/lib/Drupal/field_test/TestEntityBundleController.php
@@ -7,16 +7,16 @@
 
 namespace Drupal\field_test;
 
-use Drupal\entity\EntityController;
+use Drupal\entity\DatabaseStorageController;
 
 /**
  * Controller class for the test_entity_bundle entity type.
  *
- * This extends the Drupal\entity\EntityController class, adding
+ * This extends the Drupal\entity\DatabaseStorageController class, adding
  * required special handling for bundles (since they are not stored in the
  * database).
  */
-class TestEntityBundleController extends EntityController {
+class TestEntityBundleController extends DatabaseStorageController {
 
   protected function attachLoad(&$entities, $revision_id = FALSE) {
     // Add bundle information.
diff --git a/core/modules/node/lib/Drupal/node/NodeStorageController.php b/core/modules/node/lib/Drupal/node/NodeStorageController.php
index dccec71..e201036 100644
--- a/core/modules/node/lib/Drupal/node/NodeStorageController.php
+++ b/core/modules/node/lib/Drupal/node/NodeStorageController.php
@@ -7,7 +7,7 @@
 
 namespace Drupal\node;
 
-use Drupal\entity\EntityDatabaseStorageController;
+use Drupal\entity\DatabaseStorageController;
 use Drupal\entity\EntityInterface;
 use Drupal\entity\EntityStorageException;
 use Exception;
@@ -15,13 +15,13 @@ use Exception;
 /**
  * Controller class for nodes.
  *
- * This extends the Drupal\entity\EntityDatabaseStorageController class, adding
+ * This extends the Drupal\entity\DatabaseStorageController class, adding
  * required special handling for node entities.
  */
-class NodeStorageController extends EntityDatabaseStorageController {
+class NodeStorageController extends DatabaseStorageController {
 
   /**
-   * Overrides Drupal\entity\EntityDatabaseStorageController::create().
+   * Overrides Drupal\entity\DatabaseStorageController::create().
    */
   public function create(array $values) {
     $node = parent::create($values);
@@ -35,7 +35,7 @@ class NodeStorageController extends EntityDatabaseStorageController {
   }
 
   /**
-   * Overrides Drupal\entity\EntityDatabaseStorageController::delete().
+   * Overrides Drupal\entity\DatabaseStorageController::delete().
    */
   public function delete($ids) {
     $entities = $ids ? $this->load($ids) : FALSE;
@@ -80,7 +80,7 @@ class NodeStorageController extends EntityDatabaseStorageController {
   }
 
   /**
-   * Overrides Drupal\entity\EntityDatabaseStorageController::save().
+   * Overrides Drupal\entity\DatabaseStorageController::save().
    */
   public function save(EntityInterface $entity) {
     $transaction = db_transaction();
@@ -152,7 +152,7 @@ class NodeStorageController extends EntityDatabaseStorageController {
   }
 
   /**
-   * Overrides Drupal\entity\EntityController::attachLoad().
+   * Overrides Drupal\entity\DatabaseStorageController::attachLoad().
    */
   protected function attachLoad(&$nodes, $revision_id = FALSE) {
     // Create an array of nodes for each content type and pass this to the
@@ -177,7 +177,7 @@ class NodeStorageController extends EntityDatabaseStorageController {
   }
 
   /**
-   * Overrides Drupal\entity\EntityController::buildQuery().
+   * Overrides Drupal\entity\DatabaseStorageController::buildQuery().
    */
   protected function buildQuery($ids, $conditions = array(), $revision_id = FALSE) {
     // Ensure that uid is taken from the {node} table,
@@ -192,7 +192,7 @@ class NodeStorageController extends EntityDatabaseStorageController {
   }
 
   /**
-   * Overrides Drupal\entity\EntityDatabaseStorageController::invokeHook().
+   * Overrides Drupal\entity\DatabaseStorageController::invokeHook().
    */
   protected function invokeHook($hook, EntityInterface $node) {
     if ($hook == 'insert' || $hook == 'update') {
@@ -241,7 +241,7 @@ class NodeStorageController extends EntityDatabaseStorageController {
   }
 
   /**
-   * Overrides Drupal\entity\EntityDatabaseStorageController::preSave().
+   * Overrides Drupal\entity\DatabaseStorageController::preSave().
    */
   protected function preSave(EntityInterface $node) {
     // Before saving the node, set changed and revision times.
@@ -257,14 +257,14 @@ class NodeStorageController extends EntityDatabaseStorageController {
   }
 
   /**
-   * Overrides Drupal\entity\EntityDatabaseStorageController::postSave().
+   * Overrides Drupal\entity\DatabaseStorageController::postSave().
    */
   function postSave(EntityInterface $node, $update) {
     node_access_acquire_grants($node, $update);
   }
 
   /**
-   * Overrides Drupal\entity\EntityDatabaseStorageController::preDelete().
+   * Overrides Drupal\entity\DatabaseStorageController::preDelete().
    */
   function preDelete($entities) {
     if (module_exists('search')) {
@@ -275,7 +275,7 @@ class NodeStorageController extends EntityDatabaseStorageController {
   }
 
   /**
-   * Overrides Drupal\entity\EntityDatabaseStorageController::postDelete().
+   * Overrides Drupal\entity\DatabaseStorageController::postDelete().
    */
   protected function postDelete($nodes) {
     // Delete values from other tables also referencing this node.
diff --git a/core/modules/node/node.api.php b/core/modules/node/node.api.php
index 915d906..55ce86d 100644
--- a/core/modules/node/node.api.php
+++ b/core/modules/node/node.api.php
@@ -529,7 +529,7 @@ function hook_node_insert(Drupal\node\Node $node) {
  * Act on nodes being loaded from the database.
  *
  * This hook is invoked during node loading, which is handled by entity_load(),
- * via classes NodeController and Drupal\entity\EntityController.
+ * via classes NodeController and Drupal\entity\DatabaseStorageController.
  * After the node information is read from the database or the entity cache,
  * hook_load() is invoked on the node's content type module, then
  * field_attach_node_revision() or field_attach_load() is called, then
@@ -1158,7 +1158,7 @@ function hook_insert(Drupal\node\Node $node) {
  * (use hook_node_load() to respond to all node loads).
  *
  * This hook is invoked during node loading, which is handled by entity_load(),
- * via classes NodeController and Drupal\entity\EntityController.
+ * via classes NodeController and Drupal\entity\DatabaseStorageController.
  * After the node information is read from the database or the entity cache,
  * hook_load() is invoked on the node's content type module, then
  * field_attach_node_revision() or field_attach_load() is called, then
diff --git a/core/modules/taxonomy/lib/Drupal/taxonomy/TermStorageController.php b/core/modules/taxonomy/lib/Drupal/taxonomy/TermStorageController.php
index 5f511be..7dedd10 100644
--- a/core/modules/taxonomy/lib/Drupal/taxonomy/TermStorageController.php
+++ b/core/modules/taxonomy/lib/Drupal/taxonomy/TermStorageController.php
@@ -8,15 +8,15 @@
 namespace Drupal\taxonomy;
 
 use Drupal\entity\EntityInterface;
-use Drupal\entity\EntityDatabaseStorageController;
+use Drupal\entity\DatabaseStorageController;
 
 /**
  * Defines a Controller class for taxonomy terms.
  */
-class TermStorageController extends EntityDatabaseStorageController {
+class TermStorageController extends DatabaseStorageController {
 
   /**
-   * Overrides Drupal\entity\EntityDatabaseStorageController::create().
+   * Overrides Drupal\entity\DatabaseStorageController::create().
    *
    * @param array $values
    *   An array of values to set, keyed by property name. A value for the
@@ -40,7 +40,7 @@ class TermStorageController extends EntityDatabaseStorageController {
   }
 
   /**
-   * Overrides Drupal\entity\EntityDatabaseStorageController::buildQuery().
+   * Overrides Drupal\entity\DatabaseStorageController::buildQuery().
    */
   protected function buildQuery($ids, $conditions = array(), $revision_id = FALSE) {
     $query = parent::buildQuery($ids, $conditions, $revision_id);
@@ -63,7 +63,7 @@ class TermStorageController extends EntityDatabaseStorageController {
   }
 
   /**
-   * Overrides Drupal\entity\EntityDatabaseStorageController::cacheGet().
+   * Overrides Drupal\entity\DatabaseStorageController::cacheGet().
    */
   protected function cacheGet($ids, $conditions = array()) {
     $terms = parent::cacheGet($ids, $conditions);
@@ -78,7 +78,7 @@ class TermStorageController extends EntityDatabaseStorageController {
   }
 
   /**
-   * Overrides Drupal\entity\EntityDatabaseStorageController::postDelete().
+   * Overrides Drupal\entity\DatabaseStorageController::postDelete().
    */
   protected function postDelete($entities) {
     // See if any of the term's children are about to be become orphans.
@@ -109,7 +109,7 @@ class TermStorageController extends EntityDatabaseStorageController {
   }
 
   /**
-   * Overrides Drupal\entity\EntityDatabaseStorageController::postSave().
+   * Overrides Drupal\entity\DatabaseStorageController::postSave().
    */
   protected function postSave(EntityInterface $entity, $update) {
     if (isset($entity->parent)) {
@@ -131,7 +131,7 @@ class TermStorageController extends EntityDatabaseStorageController {
   }
 
   /**
-   * Implements Drupal\entity\EntityControllerInterface::resetCache().
+   * Overrides Drupal\entity\DatabaseStorageController::resetCache().
    */
   public function resetCache(array $ids = NULL) {
     drupal_static_reset('taxonomy_term_count_nodes');
diff --git a/core/modules/taxonomy/lib/Drupal/taxonomy/VocabularyStorageController.php b/core/modules/taxonomy/lib/Drupal/taxonomy/VocabularyStorageController.php
index 8d64467..c0a2c61 100644
--- a/core/modules/taxonomy/lib/Drupal/taxonomy/VocabularyStorageController.php
+++ b/core/modules/taxonomy/lib/Drupal/taxonomy/VocabularyStorageController.php
@@ -8,15 +8,15 @@
 namespace Drupal\taxonomy;
 
 use Drupal\entity\EntityInterface;
-use Drupal\entity\EntityDatabaseStorageController;
+use Drupal\entity\DatabaseStorageController;
 
 /**
  * Defines a controller class for taxonomy vocabularies.
  */
-class VocabularyStorageController extends EntityDatabaseStorageController {
+class VocabularyStorageController extends DatabaseStorageController {
 
   /**
-   * Overrides Drupal\entity\EntityDatabaseStorageController::buildQuery().
+   * Overrides Drupal\entity\DatabaseStorageController::buildQuery().
    */
   protected function buildQuery($ids, $conditions = array(), $revision_id = FALSE) {
     $query = parent::buildQuery($ids, $conditions, $revision_id);
@@ -27,7 +27,7 @@ class VocabularyStorageController extends EntityDatabaseStorageController {
   }
 
   /**
-   * Overrides Drupal\entity\EntityDatabaseStorageController::postSave().
+   * Overrides Drupal\entity\DatabaseStorageController::postSave().
    */
   protected function postSave(EntityInterface $entity, $update) {
     if (!$update) {
@@ -39,7 +39,7 @@ class VocabularyStorageController extends EntityDatabaseStorageController {
   }
 
   /**
-   * Overrides Drupal\entity\EntityDatabaseStorageController::preDelete().
+   * Overrides Drupal\entity\DatabaseStorageController::preDelete().
    */
   protected function preDelete($entities) {
     // Only load terms without a parent, child terms will get deleted too.
@@ -48,7 +48,7 @@ class VocabularyStorageController extends EntityDatabaseStorageController {
   }
 
   /**
-   * Overrides Drupal\entity\EntityDatabaseStorageController::postDelete().
+   * Overrides Drupal\entity\DatabaseStorageController::postDelete().
    */
   protected function postDelete($entities) {
     // Load all Taxonomy module fields and delete those which use only this
@@ -79,7 +79,7 @@ class VocabularyStorageController extends EntityDatabaseStorageController {
   }
 
   /**
-   * Implements Drupal\entity\DrupalEntityControllerInterface::resetCache().
+   * Overrides Drupal\entity\DrupalDatabaseStorageController::resetCache().
    */
   public function resetCache(array $ids = NULL) {
     drupal_static_reset('taxonomy_vocabulary_get_names');
diff --git a/core/modules/user/lib/Drupal/user/UserStorageController.php b/core/modules/user/lib/Drupal/user/UserStorageController.php
index 78811c9..bde430c 100644
--- a/core/modules/user/lib/Drupal/user/UserStorageController.php
+++ b/core/modules/user/lib/Drupal/user/UserStorageController.php
@@ -9,18 +9,18 @@ namespace Drupal\user;
 
 use Drupal\entity\EntityInterface;
 use Drupal\entity\EntityMalformedException;
-use Drupal\entity\EntityDatabaseStorageController;
+use Drupal\entity\DatabaseStorageController;
 
 /**
  * Controller class for users.
  *
- * This extends the Drupal\entity\EntityDatabaseStorageController class, adding
+ * This extends the Drupal\entity\DatabaseStorageController class, adding
  * required special handling for user objects.
  */
-class UserStorageController extends EntityDatabaseStorageController {
+class UserStorageController extends DatabaseStorageController {
 
   /**
-   * Overrides Drupal\entity\EntityDatabaseStorageController::attachLoad().
+   * Overrides Drupal\entity\DatabaseStorageController::attachLoad().
    */
   function attachLoad(&$queried_users, $revision_id = FALSE) {
     // Build an array of user picture IDs so that these can be fetched later.
@@ -60,7 +60,7 @@ class UserStorageController extends EntityDatabaseStorageController {
   }
 
   /**
-   * Overrides Drupal\entity\EntityDatabaseStorageController::create().
+   * Overrides Drupal\entity\DatabaseStorageController::create().
    */
   public function create(array $values) {
     if (!isset($values['created'])) {
@@ -73,7 +73,7 @@ class UserStorageController extends EntityDatabaseStorageController {
   }
 
   /**
-   * Overrides Drupal\entity\EntityDatabaseStorageController::save().
+   * Overrides Drupal\entity\DatabaseStorageController::save().
    */
   public function save(EntityInterface $entity) {
     if (empty($entity->uid)) {
@@ -84,7 +84,7 @@ class UserStorageController extends EntityDatabaseStorageController {
   }
 
   /**
-   * Overrides Drupal\entity\EntityDatabaseStorageController::preSave().
+   * Overrides Drupal\entity\DatabaseStorageController::preSave().
    */
   protected function preSave(EntityInterface $entity) {
     // Update the user password if it has changed.
@@ -158,7 +158,7 @@ class UserStorageController extends EntityDatabaseStorageController {
   }
 
   /**
-   * Overrides Drupal\entity\EntityDatabaseStorageController::postSave().
+   * Overrides Drupal\entity\DatabaseStorageController::postSave().
    */
   protected function postSave(EntityInterface $entity, $update) {
 
-- 
1.7.4.msysgit.0

