Evite recargar todos los datos XML para cada repetidor - VB.NET
-
24-10-2019 - |
Pregunta
Estoy tratando de colocar un repetidor dentro de un repetidor usando datos XML. Lo tengo funcionando exactamente como quiero, pero el método que he usado recarga los datos para cada repetidor. Creo que necesito elegir como un XMLNode, pero seré honesto, no tengo idea de por dónde empezar.
Aquí está mi código: me gustaría mantener todo en el código atrás si es posible.
<script runat="server">
Public doc As New XmlDocument()
Public Sub Page_Load(ByVal Sender As Object, ByVal E As EventArgs)
If Not Page.IsPostBack then
doc.Load(Server.MapPath("~/myxml/bookstore.xml"))
Dim nodes As XmlNodeList = doc.SelectNodes("Bookings/Booking[@CLIENT_NO='SA33762']")
rpMyRepeater.DataSource = nodes
rpMyRepeater.DataBind()
End If
End Sub
Protected Sub itemDB(ByVal s As Object, ByVal e As RepeaterItemEventArgs)
If e.Item.ItemType = ListItemType.Item OrElse e.Item.ItemType = ListItemType.AlternatingItem Then
Dim rpt As Repeater = CType(e.Item.FindControl("books"), Repeater)
If Not (rpt Is Nothing) Then
doc.Load(Server.MapPath("~/myxml/bookstore.xml"))
Dim nodes2 As XmlNodeList = doc.SelectNodes("Bookings/Booking[@CLIENT_NO='SA33762']/Products/Book")
rpt.DataSource = nodes2
rpt.DataBind()
End If
End If
End Sub
</script>
¿Algunas ideas?
Solución
¿Me estoy perdiendo de algo?
¿No puede simplemente comentar/eliminar su doc.load (server.mappath ("~/myxml/bookstore.xml"))? ¿Desde que definió DOC "a nivel mundial" y ya lo cargó en la carga de la página? (Al hacerlo, ya evitará volver a cargar el XML)
Dicho esto, estoy de acuerdo con Caspar en que preferirías usar el XmlDataSource (especialmente por sus habilidades de almacenamiento en caché), no tiene que usar el xmlDataSource dentro de su marcado; siempre puede definirlo dentro de su código, ya que le preocupa las personas que vean su (ASP.NET Basado en el lado del servidor) marcado por alguna razón ...
p.ej
Public Sub Page_Load(ByVal Sender As Object, ByVal E As EventArgs) Handles Me.Load
If Not Page.IsPostBack Then
Dim source As New XmlDataSource()
source.DataFile = "~/myxml/bookstore.xml"
source.XPath = "Bookings/Booking[@CLIENT_NO='SA33762']"
rpMyRepeater.DataSource = source
rpMyRepeater.DataBind()
End If
End Sub
Margen:(Lo bueno que notarás aquí es que unimos el segundo repetidor usando la fuente del primer repetidor)
<asp:Repeater ID="rpMyRepeater" runat="server">
<ItemTemplate>
<%#XPath("//Booking/NAME/text()")%>
<asp:Repeater runat="server" ID='books' DataSource='<%#XPathSelect("//Booking/Products/Book") %>'>
<HeaderTemplate>
<h2>
Books</h2>
</HeaderTemplate>
<ItemTemplate>
<p>
Title:
<%#XPath("TITLE/text()")%></p>
<p>
<%#XPath("BOOKCODE/text()")%></p>
</ItemTemplate>
</asp:Repeater>
</ItemTemplate>
</asp:Repeater>
XML
<?xml version="1.0" encoding="utf-8" ?>
<Bookings>
<Booking CLIENT_NO="SA33762">
<NAME>Mr Pf_Test_15033</NAME>
<Products>
<Book>
<TITLE>My Book</TITLE>
<BOOKCODE>12345</BOOKCODE>
</Book>
<Book>
<TITLE>My Book2</TITLE>
<BOOKCODE>123456</BOOKCODE>
</Book>
</Products>
</Booking>
</Bookings>
La implementación utilizando el control ListView (Uno de mis controles favoritos de ASP.NET) se verá algo así:(Si no hay libros disponibles, mostrará el marcado dentro de la placa vacía)
<asp:Repeater ID="rpMyRepeater" runat="server">
<ItemTemplate>
<%#XPath("//Booking/NAME/text()")%>
<asp:ListView runat="server" ID="books" ItemPlaceholderID="phItems" DataSource='<%#XPathSelect("//Booking/Products/Book") %>'>
<LayoutTemplate>
<h2>
Books</h2>
<asp:PlaceHolder runat="server" ID="phItems"></asp:PlaceHolder>
</LayoutTemplate>
<ItemTemplate>
<p>
Title:
<%#XPath("TITLE/text()")%></p>
<p>
<%#XPath("BOOKCODE/text()")%></p>
</ItemTemplate>
<EmptyDataTemplate>
<p>
Sorry no books available</p>
</EmptyDataTemplate>
</asp:ListView>
</ItemTemplate>
</asp:Repeater>
Otros consejos
Usa un XmldataSource En lugar de código personalizado, mejor probado, ajustado, optimizado y cumple con sus requisitos. ¿Por qué escribir algo que ya está en el marco? ;)
<asp:xmldatasource
CacheDuration="Infinite"
id="XmlDataSource1"
runat="server"
XPath="Bookings/Booking[@CLIENT_NO='SA33762']" //<-- test this
datafile="~/myxml/bookstore.xml" />