当前位置: 首页>>技术解读>>正文


‘eav_’表的目的

webfans 技术解读 , , 去评论

问题描述

我一直想知道表格的含义是什么:

eav_entity  
eav_entity_datetime
eav_entity_decimal
eav_entity_int
eav_entity_store
eav_entity_text

他们总是空着的。它们是在app/code/core/Mage/Eav/sql/eav_setup/mysql4-install-0.7.0.php中1.6之前的版本中创建的,后来它们被带到版本1.6+ /app/code/core/Mage/Eav/sql/eav_setup/install-1.6.0.0.php的安装脚本中我看到有一个资源模型链接到其中一个表Mage_Eav_Model_Resource_Entity_Store(可能还有其他表)但是它没有发生任何事情。

这些表是否有用,或者这是另一个”feature”,它已启动但未实现,例如layout versionadmin breadcrumbs

最佳解决思路

我的猜测是它是开发人员实现”generic”实体/模型的部分遗产和”convenience”模式。

如您所述,相关表通常是空的。原因是没有核心EAV实体使用此”default”实体表结构。这些是1.8安装的实体表:

mysql> select distinct(entity_table) from eav_entity_type;
+-------------------------+
| entity_table            |
+-------------------------+
| customer/entity         |
| customer/address_entity |
| sales/order             |
| sales/order_entity      |
| catalog/category        |
| catalog/product         |
| sales/quote             |
| sales/quote_address     |
| sales/quote_entity      |
| sales/quote_item        |
| sales/invoice           |
+-------------------------+
11 rows in set (0.00 sec)

以Customer模型为例,我们可以看到资源模型Mage_Customer_Model_Resource_Customer扩展了Mage_Eav_Model_Entity_AbstractSource

注意:在1.6之前,客户实体的资源模型是Mage_Customer_Model_Entity_Customer,它还扩展了Mage_Eav_Model_Entity_AbstractSource

如果我们检查Mage_Eav_Model_Entity_Abstract类,我们找到getEntityTable方法。此方法用于确定在常见CRUD操作期间构建查询时要使用的表。另一种感兴趣的方法是getValueTablePrefix。它确定数据表的前缀”type”表,*_datetime*_decimal*_varchar等。

偷看这些方法的来源(herehere)。

public function getEntityTable()
    {
        if (!$this->_entityTable) {
            $table = $this->getEntityType()->getEntityTable();
            if (!$table) {
                $table = Mage_Eav_Model_Entity::DEFAULT_ENTITY_TABLE;
            }
            $this->_entityTable = Mage::getSingleton('core/resource')->getTableName($table);
        }

        return $this->_entityTable;
    }

在上面的方法中,我们可以看到,如果实体类型没有定义自定义表,则默认为Mage_Eav_Model_Entity :: DEFAULT_ENTITY_TABLE。该常量的值为’eav/entity’,后者又变为eav_entity表(假设应用程序中没有配置的表前缀)。我提到的第二种方法是在没有为给定实体配置的情况下作为前缀返回此表。如果检查eav_entity_type表中value_table_prefix列的值,您会发现它们都是NULL。

public function getValueTablePrefix()
    {
        if (!$this->_valueTablePrefix) {
            $prefix = (string)$this->getEntityType()->getValueTablePrefix();
            if (!empty($prefix)) {
                $this->_valueTablePrefix = $prefix;
                /**
                * entity type prefix include DB table name prefix
                */
                //Mage::getSingleton('core/resource')->getTableName($prefix);
            } else {
                $this->_valueTablePrefix = $this->getEntityTable();
            }
        }

        return $this->_valueTablePrefix;
    }

方法中的逻辑相当简单,如果没有定义值前缀,则使用实体表名作为前缀。

我认为,由于这些表已经在Magento中存在了这么长时间,因此最好将它们留在任何向后兼容性中,而不是完全删除它们。我相信他们想要的想法是一个易于使用的实体/模型结构,其他开发人员可以扩展几个类并具有可以通过管理员更改的”dynamic”属性(请参阅目录产品和客户模型)。不幸的是,所述模式的实现和实践似乎不能很好地扩展并导致问题。我从未见过这种野外使用的结构,可能是由于缺乏文档和示例用例或性能不佳。

我不是核心开发人员(或考古学家),但这是我从代码和数据结构中收集的内容,希望它有助于解决问题。

次佳解决思路

考虑基本EAV资源模型中的这段代码。

#File: app/code/core/Mage/Eav/Model/Entity/Abstract.php
public function getEntityTable()
{
    if (!$this->_entityTable) {
        $table = $this->getEntityType()->getEntityTable();
        if (!$table) {
            $table = Mage_Eav_Model_Entity::DEFAULT_ENTITY_TABLE;
        }
        $this->_entityTable = Mage::getSingleton('core/resource')->getTableName($table);
    }

    return $this->_entityTable;
}

此方法获取用于存储的基本实体表名称。因此,对于产品的资源模型,此方法将返回catalog_product_entity(假设未设置表名前缀)

这四条线是最具启发性的。

#File: app/code/core/Mage/Eav/Model/Entity/Abstract.php
$table = $this->getEntityType()->getEntityTable();
if (!$table) {
    $table = Mage_Eav_Model_Entity::DEFAULT_ENTITY_TABLE;
}

如果实体没有表集,则使用以下常量

#File: app/code/core/Mage/Eav/Model/Entity.php
const DEFAULT_ENTITY_TABLE      = 'eav/entity';

然后使用此eav/entity字符串查找表名

#File: app/code/core/Mage/Eav/Model/Entity/Abstract.php
Mage::getSingleton('core/resource')->getTableName($table);

从配置中获取表名。

<!-- File: app/code/core/Mage/Eav/etc/config.xml -->
<entity>
    <table>eav_entity</table>
</entity>

啊哈!如果eav实体类型没有设置表名,则Magento将使用eav_entity表作为默认存储位置。

最初的Magento工程团队迷恋于EAV概念 – 而现代Magento已经缩减了这一点,EAV模型是许多问题的首选解决方案。

假设/推测初始pre-release EAV实现存储在此中央eav_entity类型表(企业平台中的常见模式)中的所有数据似乎是合理的,并且实体类型随后出现。

另一个(引人注目的)可能性是此功能旨在启用”tableless” CRUD模型。理论上,可以插入正确的EAV类型信息,设置模型/资源/集合类,并将数据存储在这些eav_entity表中。 Magento远离EAV,而post-launch专注于end-user上的工程团队,这意味着这个功能逐渐消失。虽然我很好奇这是否有效,但我不想依赖它,因为它不是一个受到很多关注的代码路径,并且TAF涵盖它的使用是值得怀疑的。

参考资料

本文由朵颐IT整理自网络, 文章地址: https://duoyit.com/article/2696.html,转载请务必附带本地址声明。