32

介绍

我正面临Ext.data.ModelExtJS 中的类的应用程序设计问题。我将在这里尝试将我的想法发展为一个非常常见的在线商店场景,因此您可以关注我。我真的很感激任何对我的想法和结论的评论!

楷模

假设您想将“每个客户都可以订购多种产品”这一事实映射到 ExtJS。从简单的话可以识别出这三个模型:CustomerOrderProduct。在Order这种情况下,连接Customers 和 Products。

协会

我发现 ExtJS 实际上允许您使用and类来指定这种(Customer)1-n(Order)1-n(Product)关系。但这就是人们想要的吗?您是否希望 a始终属于 a ?如果你想拥有一个与s 没有任何联系的s 列表怎么办?Ext.data.HasManyAssociationExt.data.BelongsToAssociationProductOrderProductOrder

专卖店

这是它获得更多 ExtJS 特定的地方。在 ExtJS 中,您必须Ext.data.Stores 来保存所有数据。对我来说,组织数据的一种自然方式是为Ext.data.Store我的每个模型设置一个:

  1. CustomerStore
  2. OrderStore
  3. ProductStore

考虑Ext.grid.Panel并排放置一个 3 s;每个商店一个。在一个网格中选择客户时,他的订单会自动显示在第二个网格中。在第二个网格中选择订单时,相关产品会出现在第三个网格中。

这听起来自然吗?如果没有,请发表评论!

把这一切放在一起

所以现在我们需要把三件事放在一起:

  1. 模型及其
  2. 关联 ( hasMany, belongsTo) 和
  3. 数据(Store秒)

是否可以仅从模型-模型关系的一侧定义关联?例如,我可以指定一个Order hasMany Products 但忽略那个 a Product belongsToanOrder吗?因为一个Product实际上可以属于多个Order。因此,我指定Product模型hasMany Order如下。

以下是 ExtJS 中的模型:

顾客

Ext.define('Customer', {
    extend   : 'Ext.data.Model',
    requires : [
        'Order',
    ],
    fields   : [
           {name : 'id',          type : 'int'},
           {name : 'lastname',    type : 'string'}
           {name : 'firstname',   type : 'string'}
    ],
    hasMany: 'Order' /* Generates a orders() method on every Customer instance */
});

命令

Ext.define('Order', {
    extend   : 'Ext.data.Model',
    fields   : [
            {name : 'id',          type : 'int'},
            {name : 'customer_id', type : 'int'}, /* refers to the customer that this order belongs to*/
            {name : 'date',        type : 'date'}
    ],
    belongsTo: 'Customer', /* Generates a getCustomer method on every Order instance */
    hasMany: 'Product' /* Generates a products() method on every Order instance */
});

产品

Ext.define('Product', {
    extend   : 'Ext.data.Model',
    fields   : [
            {name : 'id',          type : 'int'},
            {name : 'name',        type : 'string'},
            {name : 'description', type : 'string'},
            {name : 'price',       type : 'float'}
    ],
    /*
        I don't specify the relation to the "Order" model here
        because it simply doesn't belong here.

        Will it still work?
    */
    hasMany: 'Order'
});

这里是商店:

客户商店

Ext.define('CustomerStore', {
    extend      : 'Ext.data.Store',
    storeId     : 'CustomerStore',
    model       : 'Customer',
    proxy   : {
        type   : 'ajax',
        url    : 'data/customers.json',
        reader : {
            type           : 'json',
            root           : 'items',
            totalProperty  : 'total'
        }
    }
});

订单商店

Ext.define('OrderStore', {
    extend      : 'Ext.data.Store',
    storeId     : 'OrderStore',
    model       : 'Order',
    proxy   : {
        type   : 'ajax',
        url    : 'data/orders.json',
        reader : {
            type           : 'json',
            root           : 'items',
            totalProperty  : 'total'
        }
    }
});

产品商店

Ext.define('ProductStore', {
    extend      : 'Ext.data.Store',
    storeId     : 'ProductStore',
    model       : 'Product',
    proxy   : {
        type   : 'ajax',
        url    : 'data/products.json',
        reader : {
            type           : 'json',
            root           : 'items',
            totalProperty  : 'total'
        }
    }
});

这是公司及其产品的示例(不是我的)http://superdit.com/2011/05/23/extjs-load-grid-from-another-grid/。它使用两个模型和两个商店,但没有定义关联。

先感谢您

-康拉德

4

4 回答 4

15

康拉德。我最近面临处理Models+Associations+Stores. 这不是很愉快的经历。这是我学到的:

假设我们有 Store1、Store2、Model1、Model2、Grid1、Grid2。Grid1 使用 Store1,Store1 使用 Model1,同样 Grid2 使用 Store2,Store2 使用 Model2。

到目前为止一切正常,数据正在加载等等。

但现在我们要向 Model1 添加hasMany关联。好的,我们正在向 Model1 的配置中添加:

hasMany: {model: 'Model2', name: 'model2'}

在此之后,您认为可以通过执行以下操作来使用 Grid1 上的数据填充 Store2 itemclick

Grid1.on('itemclick', function(view, item_which_uses_model1){
  //item_which_uses_model1.model2() supposed to return Model2's store
  item_which_uses_model1.model2().load();
}

您期望 Grid2 填充 Grid1 上的数据itemclick。但什么也没有发生。实际上正在发布请求,并获得响应。但是 Grid2 没有填充数据。
一段时间后,您意识到这item_which_uses_model1.model2() 不是 Store2

当 Model2 “看到”它与 Model1 有关联时,它会创建 Model1 自己的商店,该商店不等于 Store2。

这并不酷,因为 Grid2 正在使用 Store2。

实际上,您可以通过例如添加到 Grid2 的配置来破解它:

store: new Model1().model2(),

但是如果你使用 ExtJS mvc 模式呢?Grid2 不必知道有关 Model1 的任何信息。

不建议associations在现实世界的项目中使用。至少现在。而是使用示例中显示的方法:模型+存储+过滤。

于 2011-07-31T08:51:42.920 回答
9

这一切在 ExtJS 4 中运行良好,只是很难在第一次就做好。嗯,前几次。

是的,您可以避免指定子项的 belongsTo 关联,并且仍然在 Has Many 关系中使用它。

在我的项目中,我们有几十个模型,其中很多都有很深的关系,而且效果很好。

关于多对多关系,你应该要么

客户 -< 客户订单 >- 订单

这是三个模型,

或者,您可以通过在服务器上进行大量工作来“伪造”它,以假装客户有很多订单。嵌套的 json 可以在这里提供帮助。

于 2012-05-24T20:01:42.010 回答
3

我完全同意分子人。通过阅读 ExtJS 文档,当您使用分布到不同商店的树集结构时,它似乎更多地证明了这是一条很好的路线。坦率地说,只有当这种关联以任何方式引用商店来拨打电话时,这一切才可能是真的。从我测试的情况来看,情况并非如此。模型关联没有这种关系。过滤是跟上顺序更新其模型依赖于其他网格的其他网格的最佳方式。

于 2012-05-24T14:58:47.600 回答
0

请注意您的假设:

(客户)1-n(订单)1-n(产品)

是错的。您的实际模型应该是:

(客户)1-n(订单) n -n(产品)

这就是为什么您在使用 hasMany-belongsTo 建模时也发现了困难

于 2013-01-23T08:44:29.093 回答