Friday, October 12, 2012

Death by DDS - Count < TotalItemCount

Death by DDS - Count < TotalItemCount

I have a DDS based on a SQL query.  Query returns 41 Items.  This is confirmed at the SQL level as well as within VS (Server Explore .. "show results" of the query).  At the back end the object (RIA - LinqToE) is simple enough:

public IQueryable<qryInventory>   GetQryInventories()   {   return this.ObjectContext.qryInventories;   }  

On the page (a child window modal), I have the DDS defined in XAML

<riaControls:DomainDataSource AutoLoad="True" d:DesignData="{d:DesignInstance my1:qryInventory, CreateList=true}" Height="0"                                         LoadedData="qryInventoryDomainDataSource_LoadedData" Name="qryInventoryDomainDataSource" QueryName="GetQryInventoriesQuery" Width="0">              <riaControls:DomainDataSource.DomainContext>                  <my:RoasterWerksDomainContext />              </riaControls:DomainDataSource.DomainContext>          </riaControls:DomainDataSource>

And on its Loaded event I check the data:

private void qryInventoryDomainDataSource_LoadedData(object sender, LoadedDataEventArgs e)          {                if (e.HasError)              {                  System.Windows.MessageBox.Show(e.Error.ToString(), "Load Error", System.Windows.MessageBoxButton.OK);                  e.MarkErrorAsHandled();              }                             dg2.ItemsSource = qryInventoryDomainDataSource.Data;          }

I put a break on the ItemsSource assignment. The grid is only showing 3 Items. When I inspect the DDS.Data I show:

qryInventoryDomainDataSource.Data
{System.Windows.Controls.DomainDataSourceView}
    CanAdd: false
    CanChangePage: false
    CanRemove: false
    Count: 3
    CurrentItem: null
    CurrentPosition: -1
    IsEmpty: false
    IsPageChanging: false
    PageCount: 0
    PageIndex: -1
    PageSize: 0
    TotalItemCount: 41

I don't understand / can't explain why the Count = 3 (what is shown) versus TotalItemCount = 41 (what I want to show). There are no groupings, filters, etc. applied. This has been brutal!

Answers & Comments...

Answer: 1

I had a similar issue the other day and could for the life of me not figure it out. I was thinking it might be paging. I am sure it is something simple but could not figure it out.

I resolved to just manually loading data in my mvvm model and stop using the RiaControls.

If you do figure it out please post your answer. Guaranteed it will be something simple and overlooked. :)



Answer: 2

Although I didn't not figure out the cause .. here is what I did.  I tried to force paging by assignment.  Same result.

I created a new SL4 biz / WCF RIA project with just my single query (same db) to ensure no conflicts in code were causing it.  Same result.  Then I reinstalled WCF RIA SP1.  Same result.

Then I created a 2nd domain service on my origin project with just this query.  No issue.  Very very peculiar. 

If I had to throw my guess into the middle, I'd say there is a fundamental flaw in the DDS code that rears its ugly head at unknown times.  I wish I could provide more insight so it could be addressed but unfortunately this is all I have at the moment.



Answer: 3

Hi,

I have created a simple project for testing, But I can't reproduce your problem.

I'm not sure what's going on with your code. Maybe you have missed somthing.

I suggest you follow a simple Walkthrough below to check if there is the same issue (please following step by step):

http://msdn.microsoft.com/en-us/library/ee707376.aspx

If your have the same issu, please let me know.

Hope this helps.

 

Regards



Answer: 4

Thank you for trying to help. As I mentioned a bit earlier in the thread, I created a blank project with just the single query and the same result ocurred. There was no code other than that which is created automatically by the WCF RIA "drap and drop" of a standard Datagrid.

Moreover, if you look at what I posted - one cannot explain why Count < TotalItemCount when there is no paging (i.e. Pagesize = 0 and there are 41 Items). 



Answer: 5

Hi,

Could you provide a repro project so that we can test and investigate your issue?

Thanks.

 

Regards



Answer: 6

Hi and thank you for the continued effort to help.

Unfortunately after the steps I've taken outlined about (reinstall SP's / rebuild the SQL view, etc.) the problem no longer occurs.  If I do find another instance of this problem I will try and create a replica to share for investigation.



Answer: 7

This beauty is back.  Once again I have less than the entity set populating in a datagrid.

On inspection it shows (both DDS.Data & DDS.DataView) below.  Again the question is how can COUNT < TOTALITEMCOUNT when there is no paging or such being used.  The TOTALITEMCOUNT is correct at 18 and all items should be shown (should be in COUNT)

this.qryAtOriginDomainDataSource.Data  {System.Windows.Controls.DomainDataSourceView}      CanAdd: true      CanChangePage: false      CanRemove: true      Count: 5      CurrentItem: {qryAtOrigin : {False,False,False,False,False,False,Arabica}}      CurrentPosition: 0      IsEmpty: false      IsPageChanging: false      PageCount: 0      PageIndex: -1      PageSize: 0      TotalItemCount: 18


 

additionally, while trying to investigate in the immediate window I'm given the following ... how can a call be ambiguous to itself? .. clearly there are underlying problems.  I know a sample would be helpful.

The call is ambiguous between the following methods or properties: 'System.Windows.Controls.CollectionHelper.Count(System.Collections.IEnumerable)' and 'System.Windows.Controls.CollectionHelper.Count(System.Collections.IEnumerable)'  


 



Answer: 8

The cause seems to be in the EF and the way it infers from a SQL view making various fields part of the PK.  By altering my SQL view to include a CAST() to those items I wanted to ensure were not part of this PK, the entire collection was rendered.

In my view, there really needs to be a better approach than altering SQL.  A datawarehouse should be able to provide you a simple bonda-fide endpoint and EF should be able to adapt to it.

In any event hopefully this helps some others who have been banging their head.



Answer: 9

Silverlight 5, WCF Ria Services 1.0 SP2
press button new, cancel, debug then dds.DataView.Count == 0

if then exec dds.Load twice, will load third record.

using System;
using System.Windows;
using System.Windows.Controls;
using SilverlightApplication2.Web;
using System.ComponentModel;

namespace SilverlightApplication2
{
    public partial class MainPage : UserControl
    {
        DomainDataSource dds;
        public MainPage()
        {
            InitializeComponent();
            dds = new DomainDataSource()
            {
                DomainContext = new MiShopPolicyDomainContext(),
                AutoLoad = false,
                QueryName = "GetAaaTable",
                LoadSize = 1,
                PageSize = 1
            };
            this.DataContext = dds.Data;
            dds.Load();
        }

        private void New_Click(object sender, RoutedEventArgs e)
        {
            dds.DataView.Add(new AaaTable());
        }

        private void Cancel_Click(object sender, RoutedEventArgs e)
        {
            dds.RejectChanges();
        }

        private void NextRecord_Click(object sender, RoutedEventArgs e)
        {
            if (dds.DataView.PageIndex + 1 != dds.DataView.PageCount)
                dds.DataView.MoveToNextPage();
        }

        private void Debug_Click(object sender, RoutedEventArgs e)
        {
            if (dds.DataView.CurrentPosition == -1)
                MessageBox.Show("Error");
        }
    }
}

<UserControl x:Class="SilverlightApplication2.MainPage"
    xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
    xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
    xmlns:d="http://schemas.microsoft.com/expression/blend/2008"
    xmlns:mc="http://schemas.openxmlformats.org/markup-compatibility/2006"
    mc:Ignorable="d"
    d:DesignHeight="300" d:DesignWidth="600">

    <Grid x:Name="LayoutRoot" Background="White">
        <Grid.RowDefinitions>
            <RowDefinition Height="Auto"/>
            <RowDefinition Height="Auto"/>
            <RowDefinition Height="*"/>
        </Grid.RowDefinitions>
        <StackPanel Orientation="Horizontal">
            <Button Width="100" Content="New" Click="New_Click" />
            <Button Width="100" Content="Cancel" Click="Cancel_Click" />
            <Button Width="100" Content="Next" Click="NextRecord_Click" />
            <Button Width="100" Content="Debug" Click="Debug_Click" />
        </StackPanel>
        <StackPanel Grid.Row="1">
            <TextBlock Text="PolicyID:"/>
            <TextBox Text="{Binding PolicyID, Mode=TwoWay, NotifyOnValidationError=True, ValidatesOnExceptions=True}" />
            <TextBlock Text="PolicyName:"/>
            <TextBox Text="{Binding PolicyName, Mode=TwoWay, NotifyOnValidationError=True, ValidatesOnExceptions=True}" />
        </StackPanel>
    </Grid>
</UserControl>

namespace SilverlightApplication2.Web
{
    using System.Data;
    using System.Linq;
    using System.ServiceModel.DomainServices.EntityFramework;
    using System.ServiceModel.DomainServices.Hosting;

    [EnableClientAccess()]
    public class MiShopPolicyDomainService : LinqToEntitiesDomainService<RetailDBEntities>
    {
        public IQueryable<AaaTable> GetAaaTable()
        {
            return this.ObjectContext.AaaTable.OrderBy(e => e.PolicyID);
        }

        public void InsertAaaTable(AaaTable aaaTable)
        {
            if ((aaaTable.EntityState != EntityState.Detached))
                this.ObjectContext.ObjectStateManager.ChangeObjectState(aaaTable, EntityState.Added);
            else
                this.ObjectContext.AaaTable.AddObject(aaaTable);
        }
    }
}


create table [AaaTable] (
    [PolicyID] [varchar] (20) NOT NULL ,
    [PolicyName] [nvarchar] (50) NULL ,
     CONSTRAINT [PK_AaaTable] PRIMARY KEY CLUSTERED
     (        
         [PolicyID]
     )  ON [PRIMARY]         
) ON [PRIMARY]            
go

insert into AaaTable values ('001', '001NAME')
insert into AaaTable values ('002', '002NAME')
insert into AaaTable values ('003', '003NAME')





No comments:

Post a Comment

Send us your comment related to the topic mentioned on the blog