StrataFrame Forum

Exception has been thrown by the target of an invocation.

http://forum.strataframe.net/Topic19496.aspx

By Bill Cunnien - 9/18/2008

I received the following error when navigating away from an instance of the DevEx XtraGrid (bound to a BO via a BBS):

">

I have tried updating the framework (1.6.6 released version), then I tried updating to the most recent DevEx version (8.2.4).  I have removed the grid and replaced it with another instance.  All attempts have resulted in the same behavior.

Does anyone have any idea why the XtraGrid is causing this error to popup?  Btw, I can answer 'No' and continue using the form.  I'd really like to use the XtraGrid rather than the EnhancedList (which is nice, but lacks a couple of necessary features). 

Thanks for your help!
Bill

By Bill Cunnien - 9/18/2008

I'll try the image again:

In case the image upload fails again, it states, "Exception has been thrown by the target of an invocation.  Do you want to correct the value?"  The options are "Yes" and "No".

By Bill Cunnien - 9/18/2008

Throw a datagridview on the form, bind it to the same datasource and run it.

Now, I have an error I can work with...one of the columns referenced does not belong to the table.  It is a custom property. 

This is the point where things get really, really fuzzy for me.

If I have a grid that is using a BBS to represent the data. 
And I have a BO that is pulling a subset of the original table (include some fields, exclude others) with additional fields for the presentation (field which are defined as custom properties in the BO). 
And I match a grid up to the BBS and select only the certain fields that I want displayed

Why would any other field not included in the query or the BO or the underlying datatable be accessed by the grid at any time?  This just doesn't make sense.

Thought I had a handle on the custom field thing, but I guess I don't.

Bill

By Bill Cunnien - 9/18/2008

Here is the code for the column that is generating the error:


public decimal LastInvQty
{
   
get
   
{
       
object mLastInvQty;
        mLastInvQty =
this.CurrentRow["LastInvQty"];
       
if (mLastInvQty == null)
        {
           
return 0;
        }
       
else
       
{
           
return (decimal)this.CurrentRow["LastInvQty"];
        }
    }
}

Should I be checking on the viability of this.CurrentRow["LastInvQty"] before assigning it to a variable?  Or, just don't assign it?  Like this:


public decimal LastInvQty
{
   
get
   
{
       
if (this.CurrentRow["LastInvQty"] == null)
        {
           
return 0;
        }
       
else
       
{
           
return (decimal)this.CurrentRow["LastInvQty"];
        }
    }
}

The second option seems to work...I will test a bit more.

Thanks,
Bill

By Bill Cunnien - 9/18/2008

Nope.  Still not behaving correctly.  Even if I add the custom fields to my stored procedure with 0 as the value, I am still getting the error.
By Bill Cunnien - 9/18/2008

Trent L. Taylor (08/27/2008)
You can take a mapped BO and bring any data into that you want.  If the strong-typed properties do not have an underlying column within the result set, then an error would occur if you referenced that strong-typed property.

I scrapped the BBS and decided to use a dataset derived from the BO, instead.  That has resolved the problem entirely.

By Trent L. Taylor - 9/18/2008

Sonds goods...Smile
By Bill Cunnien - 10/10/2008

Hey Trent,

Sorry to bring this up again...but I am now working on a window where I really need a BBS to interact with a DevExpress DataGrid.  To solve the previous problem, I resorted to a dataset (view only).  Now, I need to update the data and I would really like to take advantage of the existing plumbing.  Can you provide any direction on this?

Thanks,
Bill

By Bill Cunnien - 10/10/2008

Just to reiterate...the error does not appear with a DataGridView control...only with the DevEx XtraGrid control.  Same BBS.  Same BO.  I'll keep working on it.
By Trent L. Taylor - 10/10/2008

We have developers using a DevExpress grid and BBS objects every day.  So I really don't know what you are referring to here and exactly what issue that you are having.  A sample or more details would be helpful. 
By Trent L. Taylor - 10/10/2008

From going back and rereading your previous posts, it just sounds like it is a simple matter of creating a custom property and setting using a ReflectionPropertyDescriptor defined in the GetCustomBindablePropertyDescriptors methods.  Just create a custom property that is properly exposed to respect a BBS (look at a property built through the BO Mapper for the required attributes).
By Bill Cunnien - 10/10/2008

The details are quite simple (sample app attached). 

1)  Create form.
2)  Add BO (the BO must have a custom property).
3)  Add DevEx GridView.
4)  Add BBS.
5)  Connect BO to BBS and BBS to Grid.
6)  Remove several columns from the grid, including the custom property.
7)  Run the app.

The grid will appear with data filling it (Movies).  Simply close the form and the error will appear.

I know the error is because of the custom property, but I cannot determine why.

By Bill Cunnien - 10/10/2008

The following data retrieval method was not updated properly before I zipped...sorry...

FillDataTable("SELECT * AS ItemCount FROM Movies");

Just delete the " AS ItemCount" from the select statement.  All will be well after that.  I was trying to pull a value for the custom property, but it does not matter.

By Bill Cunnien - 10/10/2008

I duplicated the details I found in the designer file of a BO and this is what I ended up with:


[Browsable(false),
BusinessFieldDisplayInEditor(),
Description("Items Count"),
DesignerSerializationVisibility(DesignerSerializationVisibility.Hidden)]
public int ItemsCount
{
   
get
   
{
       
object loValue;
        loValue =
this.CurrentRow["ItemsCount"];
       
if (loValue == DBNull.Value)
        {
           
return 0;
        }
       
else
       
{
           
return (int)this.CurrentRow["ItemsCount"];
        }
    }
}

protected override FieldPropertyDescriptor[] GetCustomBindablePropertyDescriptors()
{
   
return new FieldPropertyDescriptor[]
    {
       
new ReflectionPropertyDescriptor("ItemsCount", typeof(BusinessObject1))
    };
}

It does not make any difference.  I still get the same error.

By Bill Cunnien - 10/10/2008

Adding the following fixes the problem. 


private void BusinessObject1_CurrentDataTableInitialized()
{
   
if (CurrentDataTable.Columns["ItemsCount"] == null) { CurrentDataTable.Columns.Add(new DataColumn("ItemsCount", typeof(int))); }
}

private void BusinessObject1_CurrentDataTableRefilled()
{
   
if (CurrentDataTable.Columns["ItemsCount"] == null) { CurrentDataTable.Columns.Add(new DataColumn("ItemsCount", typeof(int))); }
}

I will make sure to add these to every BO in which I have created custom properties. 

By Bill Cunnien - 10/10/2008

It worked on the test solution, but my application is not responding the same way.  I am still getting the elusive error.  Any ideas would be appreciated.
By Bill Cunnien - 10/13/2008

Here is the most recent error message for us to work with...
By Trent L. Taylor - 10/13/2008

This looks like you may need to take something into account within your BO and properties.  For example, the LastInvQty looks as thought it may be a custom property (it may not) but in either case, there is an illegal cast exception.  So the property may be getting evaluated earlier or in a different way than normal.  Put a break point in the Get of the property and see when and how it is being accessed.  Work backwards from there. 
By Bill Cunnien - 10/13/2008

Yup...you are right...it is a custom property.  Here is the code (the corresponding FieldPropertyDescriptor exists):


[Browsable(false),
BusinessFieldDisplayInEditor(),
Description("Last Inventory Quantity"),
DesignerSerializationVisibility(DesignerSerializationVisibility.Hidden)]
public decimal LastInvQty
{
   
get
   
{
       
object loValue;
        loValue =
this.CurrentRow["LastInvQty"];
       
if (loValue == null)
        {
           
return 0.00M;
        }
       
else
       
{
           
return (decimal)this.CurrentRow["LastInvQty"];
        }
    }
}

I even forced the 0 value, if null, to be a decimal (even though I should not have to do that).  What is extremely odd is that the value of the object is {} rather than null (see attached).  Why would the object come back as an empty set rather than null?

By Bill Cunnien - 10/13/2008

Here is another exception.  This one comes about by removing the following code from CurrentDataTableInitialized and CurrentDataTableRefilled events:


if (CurrentDataTable.Columns["LastInvQty"] == null) { CurrentDataTable.Columns.Add(new DataColumn("LastInvQty", typeof(decimal))); }

So, using the above code causes the column to evaluate as {} rather than null (how do I work with a {}?) and not using the code makes the application complain that the column does not exist in the datatable.  I am using a standard DataGridView...no DevEx object involved at this point.  The three objects used are SF BO (with custom properties), SF BBS and the DataGridView.

Thanks for helping!!
Bill

By Bill Cunnien - 10/13/2008

EUREKA!!  w00t w00t w00t

Instead of evaulating the object against null, I must evaluate the object against DBNull.Value.  Wow!  How did I miss that?!?!  Perhaps I have a vitamin difficiency somewhere.

Now, I will reintroduce the DevEx grid and see if this solution applies there, too.

To quote Paul Harvey, "Stand by for news!"

By Bill Cunnien - 10/13/2008

Stop the presses!  The DevEx XtraGrid is not behaving.  It still pops the generic error when either accessing the column (CurrInvQty) or simply closing the window.  No additional information or debug data available.

Sad.  Truly sad.  Thought I had it.  Crying

I am still needing help on this one.  It would be great if a DevEx user chimes in here and let's me know how they solved their custom property issues with the DevEx grid.

I must keep at this...now is not the time to cash in my 401K and retire. BigGrin

By Greg McGuffey - 10/13/2008

Bill,



Doubt that this is it, but you probably ought to check value against null AND DbNull.Value, in that order. The first checks if any record was returned, the second if the value returned was NULL. Again, I doubt this is your problem, but it could bite you at some point.
By Trent L. Taylor - 10/13/2008

Without you setting up a sample that reproduces the behavior it is going to be hard for me to tell you what to do exactly.  I do know, however, that this is more than likely something that needs to be first addressed in the BO to account for NULLs, and then you may have to set a property somewhere in the grid if the problem persists...so past some of the recommendations that I have made or Greg has made it is going to be hard to give you any answers....sorry Ermm
By Bill Cunnien - 10/13/2008

I did provide a sample project that does exactly what I am describing (see earlier post).  I will try the double null/DBNull.value check.  Thanks.
By Bill Cunnien - 10/13/2008

if (loValue == null || loValue == DBNull.Value)

This does not change anything.

By Trent L. Taylor - 10/13/2008

I ran your sample, and it did not work.  Not SF, but your query would not ever work.  I did reproduce your problem once I made the query work.  The bottom line is that you are using a this.CurrentRow["ItemsCount"] without actually having that column in the data table.  When the Dispose fires, that strong-type field is being evaluated and thus the error.

I have reattached the sample (I had to change the references to 8.1 since I haven't dowloaded 8.2).  But this had nothing to do with the grid or or SF for that matter. 

If you want to reference a field in the data table, make sure it is there otherwise the error will occur.  You can also do real-time aggregate calculations if you have the need when the property is evaluated....though you could run into performance issues there if an additional query is taking place.

Also, your query would not work

SELECT * AS ItemsCount FROM Movies

That query will never work since you cannot place a wildcard into a single column name.  I changed to this just to create the column, but you could do a query and figure out your aggregates, etc.

SELECT Movies.*, Movies.mv_pk AS ItemsCount FROM Movies

I know that pushing the PK into this column doesn't do anything of value here, but it should at least get the point across.

But in regards to your problem, that was it here.

By Bill Cunnien - 10/13/2008

Please read all of my posts...I am trying to be as thorough as I can so I can get the surgical, precision-type help that I need.

The thread immediately following my sample post explained the incorrect SQL that was in the sample.

And, yes, I also subsequently provided information about manually adding the column to the datatable during data table initialization or refill.  It appeared to solve the problem in the test sample, but failed to solve the problem in my application.

If the column exists because I manually add it, then I get the casting problem. 

Using either a check on "null" and/or "DBNull.Value" does nothing to get me past the error.

The error popup does not supply any debug information.  I am lost when it comes to "seeing" what actually is causing the problem.  I am assuming a casting issue because the DataGridView responds with more information which I assume is the same problem that the DevEx GridView is having.  Big assumption on my part, I think.

I'll keep trying and continue to post results on this thread.

By Bill Cunnien - 10/13/2008

When the Dispose fires, that strong-type field is being evaluated and thus the error.

This statement intrigues me.  If the custom property object is null then the return value is always zero (0) of type decimal.  Why would there be an error thrown at that time?  It is not thrown when the object is created.

By Bill Cunnien - 10/13/2008

Change this . . .


public void FillAll()
{
    FillDataTable(
"SELECT Movies.*, mv_pk As ItemsCount FROM Movies");
}

. . . to this . . .


public void FillAll()
{
    FillDataTable(
"SELECT Movies.* FROM Movies");
}

. . . and the error occurs.  I do not understand.  The column should evaluate as null, therefore return a value of zero.  Why does this error?  What if all I wanted was to list the movie titles (SELECT mv_Title FROM Movies) and display the results in a grid, would this not be a valid query since custom properties are involved in the BO?  Should I always have to fill the custom properties with something (SELECT mv_Title, 0 AS ItemCount FROM Movies) even if I am not going to reference the custom property(-ies), or any other property (e.g. mv_Year, mv_Rating, etc.)?

By Trent L. Taylor - 10/13/2008

Bill, as I have mentioned in previous posts as well, I cannot help you without a good sample.  I don't want to have to piece all of this together in hopes that I reproducing your problem.  I would rather have a sample in my hands that reproduces your problem so that I can help you.  I downloaded your sample, reproduced the error, made it work and reposted it.  If that was not your problem, then please post another sample that does accurately reproduce the issue.  Going back and forth will not get your problem resolved otherwise it would have happened already. 
By Trent L. Taylor - 10/13/2008

That was exactly my point, Bill!!!!!

YOU MUST either pull back a value from the server as a column that represents the custom property you are trying to pull (ItemsCount) or perform some type of calculationo with the data that you did pull back...using your query YOU DO NOT HAVE A COLUMN named ItemsCount that can be accessed from the CUrrentRow of the BO!!!!!

By Bill Cunnien - 10/13/2008

Bill, as I have mentioned in previous posts as well, I cannot help you without a good sample.  I don't want to have to piece all of this together in hopes that I reproducing your problem.  I would rather have a sample in my hands that reproduces your problem so that I can help you.  I downloaded your sample, reproduced the error, made it work and reposted it.  If that was not your problem, then please post another sample that does accurately reproduce the issue.  Going back and forth will not get your problem resolved otherwise it would have happened already. 

I have already shown you how to reproduce the error.  You can reproduce the error even with your updated sample project.  It's easy to reproduce.  I am unable to provide you more than that.

That was exactly my point, Bill!!!!!

YOU MUST either pull back a value from the server as a column that represents the custom property you are trying to pull (ItemsCount) or perform some type of calculationo with the data that you did pull back...using your query YOU DO NOT HAVE A COLUMN named ItemsCount that can be accessed from the CUrrentRow of the BO!!!!!

I don't think I see your point.  What point are you referencing?  Do you see my point?  I do not want the custom property referenced in the grid.  Why should I even reference it in my query?  If the custom property has to be reference in every query, then to fill the BO "Select * from MyTable" should never work.  I should always get an eval error along the way somewhere.


Here's another piece of the puzzle...remove the grid and throw text boxes onto the form to reference the same three fields.  Open the form, navigate to a few records, then close the form.  NO ERROR!!!  So, something is up with the grid via the BBS.  I should be able to add a grid, connect it to the same BO through a BBS, show the same three fields in the grid and it should work.  It doesn't.  Closing the form generates an error.

That is what I am looking for an explanation on.  If the BBS somehow forces the custom property to be evaluated, then how do I turn that off on an instance by instance basis?  On some forms, I want that custom property to show on a grid...on others, like this one, I do not.

By Greg McGuffey - 10/13/2008

Bill,



I'm not sure if this will help (the last suggestion didn't Sad ), but maybe...



When you have a custom property that is using code like:



this.CurrentRow["ItemsCount"]




this means that there must a column in the data table named "ItemsCount". Apparently, this column will get called when the BO is disposed (didn't know that), if the data table doesn't have that column it will break. So, you just have to code for that. In cases like this (were I don't always want or need the value from a custom property and want to get the data from the underlying data table), I've started using code like this within my property getter:



if this.CurrentDataTable.Columns.Contains("ItemsCount")

{

  if this.CurrentRow["ItemsCount"] != null && this.CurrentRow["ItemsCount"] != DbNull.Value

  {

    return this.CurrentRow["ItemsCount"];

  } else

    return 0;

  }

} else

{

  return 0;

}




With this code (hopefully my C# is close enough to understand), it returns the value from the datatable if the column has been loaded and if the value is set, otherwise it returns zero. For any situations where I need to use the custom property, I make sure I include the appropriate SQL to load that column.



Hope this gets you closer! I know your frustration in learning this stuff! Pinch
By Bill Cunnien - 10/14/2008

Thanks, Greg.  The code works in the test project using a simple "SELECT * FROM Movies" query.  I will see how it behaves in my application.  Stand by.
By Bill Cunnien - 10/14/2008

Using a DataGridView . . . success.

Using a DevEx GridControl . . . failure. 

The same error popup on window close: "Exception has been thrown by the target of an invocation. Do you want to correct the value?  Yes.  No."  If I select "Yes" the window stays open.  If I select "No" the window closes.

The version of the DevEx GridControl is 8.2.4.  I am running on the latest SF release 1.6.6.  I will try to put this into the support and forums of DevEx.  Maybe someone there can provide some further direction.

By Trent L. Taylor - 10/14/2008

You can put this on the DevEx support forum, but it won't help you any.  This has nothing to do with the grid other than the fact that the field is being evaluated on a Dispose.

I know that you don't get what I am telling you, and Greg has tried to tell you the very same thing that I have been trying to tell you.

So let's start over.  You have asked for help, you created a sample that reproduced the problem.  I downloaded the sample that you gave and reproduced the problem on the version 8.1 grid.  I showed you an example of how to resolve the error by trying to make you understand that if you are going to create a custom property that relies on an underlying column pulled back from a query...that column must exist in the result set!!! 

For example, you can't create a custom property that attempts to pull from the CurrentRow if that column isn't within the CurrentDataTable.

You are welcome to post another sample if your first sample did not accurately depict your problem, which at this point it apparently did not since I corrected it and reposted it and you are still not pleased with the results.

If you do not supply "surgical precision-type" help, then you need to supply "surgical precision-type" details, otherwise we cannot help.

We have tried for a week now to help you with this problem and have gotten nowhere other than some frustrated and caustic remarks.  So let's take the emotion out of the equation and start over....by starting with a sample that accurately depicts your problem.  Past that, the bantering back and forth has not gotten anywhere and we are a week into the problem with no resolution....though I and Greg both seem to understand your problem, we cannot seem to make you understand the underlying issue.  So at this point, let's go back to the sample, create one that shows exactly what you are trying to do since you did not like my previous answer, I will correct it and repost it.

Thanks.

By Bill Cunnien - 10/14/2008

You have misinterpreted what I have been writing.  I am not at all intending to be caustic in my remarks.  There is no professionalism in that.  I am extremely grateful for every snippet of help given.  As I implement the ideas supplied here and attempt to fix my problem, I only report back to the forum what is happening.  If I do not follow a certain logic, I mention it.  Not trying to be a dork here.  Perhaps it looks that way.  Sorry.
By Trent L. Taylor - 10/14/2008

No worries, we are good, I just want to help you get your problem resolved...and I am sure that you have no issue with that goal either Hehe

So that is why I was suggesting going at another sample that more accurately represents your problem so that we can hopefully get to the bottom of this.