类型转换实体框架导致ItemDataBound

时间:2015-06-06 13:39:23

标签: asp.net linq entity-framework

所以我试图优化生成网站导航菜单的页面的性能。基本上有一个名为T_product_cat的表,它包含我关心的4个字段:

  • product_cat_name(产品类别名称)
  • product_cat_uid(行的唯一标识符)
  • product_cat_thumbnail_path(代表类别的图片)
  • product_cat_parent_uid(产品类别的唯一标识符 我们坐在下面 - 因为这些“产品文件夹”可以嵌套)

我需要创建一个顶部导航栏,其中只包含顶级产品类别的名称,然后我需要输出子产品类别及其图像和链接等下拉导航。我有一个基本的ASP:使用嵌套ASP的Repeater控件:Repeater来处理子产品类别

基本上我想开始使用EF开始查询我的数据。最初我做了一个查询,只是拉出顶级项目,然后在转发器的ItemDataBound事件中,我将访问数据并再次查询数据库中的子类别。但这是8x的数据库(因为我有7个顶级类别)。为了加快速度,我一直在尝试初始查询的不同迭代。这是我的最后一个参考:

Using db As New RmpEntities
    ' query all the items and then all their subitems at the same time so that we don't have to repeatedly hit the database
    Dim qry = (
        From
            productCat In db.T_product_cat
        Where
            productCat.company_uid = WmsSession.company_uid AndAlso
            productCat.enabled = 1 AndAlso
            productCat.product_cat_parent_uid = GUIDs.GlobalGuids.RootCategoryUid AndAlso
            productCat.product_cat_hide <> 1
        Order By
            productCat.product_cat_sequence
        Select
            categoryName = productCat.product_cat_name,
            categoryUid = productCat.product_cat_uid,
            imagePath = productCat.product_cat_thumbnail_path,
            subCategories = (
                From
                    productSubCat In db.T_product_cat
                Where
                    productSubCat.company_uid = WmsSession.company_uid AndAlso
                    productSubCat.enabled = 1 AndAlso
                    productSubCat.product_cat_parent_uid = productCat.product_cat_uid AndAlso
                    productSubCat.product_cat_hide <> 1
                Order By
                    productSubCat.product_cat_sequence
                Select
                    categoryName = productSubCat.product_cat_name,
                    categoryUid = productSubCat.product_cat_uid,
                    imagePath = productSubCat.product_cat_thumbnail_path
            )
    )
    rptMainNav.DataSource = qry.ToList()
    rptMainNav.DataBind()
End Using

当转发器的ItemDataBound事件触发时,我确实有工作代码来分离结果并将数据绑定到子转发器(此代码有效):

Protected Class CategoryInfo
    Public Property categoryName As String
    Public Property categoryUid As Guid
    Public Property imagePath As String
End Class

Private Sub rptMainNav_ItemDataBound(sender As Object, e As RepeaterItemEventArgs) Handles rptMainNav.ItemDataBound
    Dim rItem As RepeaterItem = e.Item
    Select Case rItem.ItemType
        Case ListItemType.Item, ListItemType.AlternatingItem
            Dim dataItem = rItem.DataItem
            Dim subRepeater As Repeater = rItem.FindControl("rptSubNav")
            Dim parentUid As Guid = dataItem.categoryUid
            Dim st = DateTime.Now
            Dim x As New List(Of CategoryInfo)
            For Each item In dataItem.subCategories
                x.Add(New CategoryInfo With {.categoryName = item.categoryName, .categoryUid = item.categoryUid, .imagePath = item.imagePath})
            Next
            subRepeater.DataSource = x
            dTime.Add(New MyTimes With {.g = parentUid, .ts = DateTime.Now - st})
            subRepeater.DataBind()
    End Select
End Sub

但是如何将通过访问转发器的DataItem返回的Object类型转换为更强类型的对象,以便我可以获得intellisense? 或者有什么方法可以放弃对打字的担忧,只是将查询结果直接用作子转发器的数据源?这是我的第一个目标,但是当我试图采取

dataItem.subCategories.ToList()

失败了:

Public member 'ToList' on type 'CompensatingCollection(Of VB$AnonymousType_1(Of String,Guid,String))' not found.

当我尝试修改我的CategoryInfo类以使另一个属性保存CategoryInfo类(子类别)列表并让主查询返回结构化数据时(因此我有一个类型要在ItemDataBound中转换)事情失败了更糟。原始查询的.ToList失败,所以我甚至无法进行初始绑定。

处理此问题的正确方法是什么?继续处理表示匿名类型的Object的属性?当然必须有更好的东西。

编辑: 罗伯特 - 谢谢你的建议。事实证明,我没有SubCategories的导航属性。原因是我前面的人设计了数据库,所有顶级类别最终都是人工产品product_cat_parent_uid(只是一些随机的GUID)。它没有指向数据库中的真实产品类别 - 它只是作为占位符。我怀疑为什么他们不只是使用NULL,但改变它为时已晚。无论如何,由于数据库中不存在该项,因此数据库本身没有外键,因为它伪造了链接。数据库不会创建指向不在数据库中的产品类别的产品类别的链接。我确实使用了您的建议来查找有关可以执行的操作的更多信息,并使用本文(Entity Framework - Add Navigation Property Manually)添加了我需要的链接。

问题仍然存在 - 我可以在ItemDataBind事件中获得强类型吗?

0 个答案:

没有答案
相关问题