0

I'm trying to access a DataItem of a parent repeater from a nested repeater, but I keep getting blanks/nothing returned.

Basic Example:

<asp:Repeater ID="Products">
    <ItemTemplate>
        <%# Eval("product_name") %>
        <asp:Repeater ID="SubProducts">
            <ItemTemplate>
                <%# DataBinder.Eval(Container.Parent.Parent, "DataItem.product_name")%>
                <%# Eval("subproduct_name")
            </ItemTemplate>
        </asp:Repeater>
    </ItemTemplate>
</asp:Repeater>

Formats I've tried:

<%# DataBinder.Eval(Container, "NamingContainer.NamingContainer.DataItem.MyRepeaterDataItem")%>

<%# DataBinder.Eval(Container.Parent.Parent, "DataItem.prod_name")%>

I've also tried replacing NamingContainer.NamingContainer with Parent.Parent in each of the above.

These were similar topics that didn't work for me:

How to read a dataitem from a parent repeater?

How to access Parent repeater id from code behind (though I don't want to access from code behind)

brendo234
  • 355
  • 2
  • 17
  • You shouldn't use `DataBinder.Eval` anymore: `` has supported strong-typing for years now: see https://stackoverflow.com/questions/12358589/using-itemtype-for-strongly-typed-repeater-control – Dai May 04 '23 at 18:23
  • ...also (and more importantly), why on earth are you using WebForms in 2023? (It was _effectively_ obsoleted back in 2008 when ASP.NET MVC came out (15 years ago...), and WebForms is removed entirely from .NET Core / .NET 5+). – Dai May 04 '23 at 18:23
  • Updates to an old site, customer didn't want to convert. – brendo234 May 04 '23 at 18:59
  • @Dai, web forms are legacy, but not depreciated, or even obsoleted. I agree that one should be learning newer things, but then again, why then is the BEST new feature in vs2022 for web forms then? Maybe the user has to maintain some legacy system. And that new best feature in vs2022, it is for web forms. So why would we get a great new web forms designer for vs2022, can you explain the logic of this? And that post here: https://devblogs.microsoft.com/visualstudio/design-your-web-forms-apps-with-web-live-preview-in-visual-studio-2022/ – Albert D. Kallal May 04 '23 at 18:59
  • @AlbertD.Kallal We've discussed this many times before - you know me. – Dai May 04 '23 at 19:01
  • @AlbertD.Kallal BTW, reckon you could answer this? https://stackoverflow.com/questions/76174999/how-to-use-azure-ad-with-webforms?noredirect=1#comment134338309_76174999 – Dai May 04 '23 at 19:02
  • Ok, then answer the question. What deprecated product gets a WHOLE new feature, and MAJOR one like a whole new web forms designer then? As long as you explain to everyone here why vs2022 received this big upgrade for web forms, then everyone can better see your point then, right? So, why is vs2022 BIG new feature for web forms? – Albert D. Kallal May 04 '23 at 19:02
  • @AlbertD.Kallal I used to work on that team at MS (HTML Design Tools). I'm still under NDA. – Dai May 04 '23 at 19:03
  • Don't need to break NDA to accept that the big new feature in vs2022 was for web forms. As for that other question? It was closed, but there no issue to use Azure authentication for webforms and using OAuth (so, I fail to see you point, and webforms supports Owin security). And I was under NDA with Microsoft for 13 years, and that NDA issue does not effect my ability's to to answer such questions here. So as far as I can tell, even using federation with domains hooked into office 365 accounts, including that of Azure can be used with webforms. – Albert D. Kallal May 04 '23 at 19:08

1 Answers1

0

Hum, what you have should work.

However, it WILL depend on how your binding (feeding) the data to the parent repeater. For example, if you feed the repeater a "reader", then for each row data bind, then "data item" does not exist.

so, for example, this works for me:

We have some hotels, and for EACH hotel, we list the booked people.

enter image description here

<asp:Repeater ID="Repeater1" runat="server" 
    OnItemDataBound="Repeater1_ItemDataBound">
    <ItemTemplate>
        <h3><%# Eval("HotelName") %> </h3>
        <h4><%# Eval("Description") %> </h4>

        <h4>Booked people in Hotel</h4>
        <asp:Repeater ID="Repeater2" runat="server">
            <ItemTemplate>
                Name: <%# Eval("FirstName") %> <%# Eval("LastName") %>
                <br />
                Show parent HotelName:
                <%# DataBinder.Eval(Container.Parent.Parent, "DataItem.HotelName")%> 
                <br />
            </ItemTemplate>
        </asp:Repeater>
        <hr />
    </ItemTemplate>
</asp:Repeater>

I am quite sure the data source being feed has to be inumerable.

Code beind:

    protected void Page_Load(object sender, EventArgs e)
    {
        if (!IsPostBack)
            LoadData();
    }


    void LoadData()
    {
        string strSQL =
            "SELECT * FROM tblHotelsA ORDER BY HotelName";
        DataTable rstData = General.MyRst(strSQL);

        Repeater1.DataSource= rstData;
        Repeater1.DataBind();

    }

And the row data bound for the main (parent repeater) is this:

    protected void Repeater1_ItemDataBound(object sender, RepeaterItemEventArgs e)
    {
        if (e.Item.ItemType == ListItemType.Item ||
            e.Item.ItemType == ListItemType.AlternatingItem)
        {
            DataRowView rData = (DataRowView)e.Item.DataItem;
            string HotelID = rData["ID"].ToString();
            string strSQL = $"SELECT * FROM People WHERE Hotel_ID = {HotelID}";

            Repeater rNested = e.Item.FindControl("Repeater2") as Repeater;
            rNested.DataSource = General.MyRst(strSQL);
            rNested.DataBind();
        }
    }

My "general" helper routine (MyRst) just returns a data table, and that was this:

public static DataTable MyRst(string strSQL, string sConn = "")
{
    DataTable rstData = new DataTable();

        if (sConn == "")
            sConn = Properties.Settings.Default.TEST4;

    using (SqlConnection conn = new SqlConnection(sConn))
    {
        using (SqlCommand cmdSQL = new SqlCommand(strSQL, conn))
        {
            cmdSQL.Connection.Open();
            rstData.Load(cmdSQL.ExecuteReader());
        }
    }
    return rstData;
}

So, what you have looks ok, but it will depend on HOW you filling out the main repeater.

Note how in the row data bind event, I have BOTH the repeater row AND ALSO the full data row - including columns that are NOT displayed in the repeater1.

That FULL data row (DataRowView) is ONLY available during the binding process, and THEN goes out of scope once data binding is complete. And if you feed a listview, gridview, or repeater a "reader" which is allowed? then as noted, the repeater will work, but the DatarowView item does not exist during the binding (row) event.

Albert D. Kallal
  • 42,205
  • 3
  • 34
  • 51