MonkeyCoder
MonkeyCoder

Reputation: 2620

Castle ActiveRecord: 'System.Int32' cannot be converted to type 'System.Boolean'

I'm having some problems with the SqlNamedQuery attribute that has been added to the newer version of Castle's ActiveRecord. I have specified it like this:

[assembly: SqlNamedQuery(Queries.GetItemName, "EXEC [dbo].[GetItemName] :id")]

Apart from that I have a property in the result mapping declared as:

...
[Property(Access = PropertyAccess.AutomaticProperty, NotNull = true)]
public virtual bool IsPrimaryName { get; set; }
...

Nhibernate query:

IQuery query = Session.GetNamedQuery(Queries.GetItemName);
query.SetParameter("id", 1212, NHibernateUtil.Int64);
query.SetResultTransformer(Transformers.AliasToBean<Mapping>());

After execution I receive the following exception:

Object of type 'System.Int32' cannot be converted to type 'System.Boolean'.

I have also added the below web.config entry but with no success (probably it only applies to hql queries).

<add key="query.substitutions" value="true 1, false 0, yes 'Y', no 'N'" />

So, my question is - how can I resolve this problem? The stored procedure returns 0 or 1 but I've also tried with '1', 'true', 'TRUE' etc. How can I get around this? Or maybe I should just drop the SqlNamedQueries?

UPDATE: Stack Trace

[ArgumentException: Object of type 'System.Int32' cannot be converted to type 'System.Boolean'.]
System.RuntimeType.TryChangeType(Object value, Binder binder, CultureInfo culture, Boolean needsSpecialCast) +4070954
System.RuntimeType.CheckValue(Object value, Binder binder, CultureInfo culture, BindingFlags invokeAttr) +9631414
System.Reflection.MethodBase.CheckArguments(Object[] parameters, Binder binder, BindingFlags invokeAttr, CultureInfo culture, Signature sig) +151
System.Reflection.RuntimeMethodInfo.Invoke(Object obj, BindingFlags invokeAttr, Binder binder, Object[] parameters, CultureInfo culture, Boolean skipVisibilityChecks) +223
System.Reflection.RuntimeMethodInfo.Invoke(Object obj, BindingFlags invokeAttr, Binder binder, Object[] parameters, CultureInfo culture) +28
System.Reflection.RuntimePropertyInfo.SetValue(Object obj, Object value, BindingFlags invokeAttr, Binder binder, Object[] index, CultureInfo culture) +101
System.Reflection.RuntimePropertyInfo.SetValue(Object obj, Object value, Object[] index) +25
NHibernate.Properties.BasicSetter.Set(Object target, Object value) +68

UPDATE: Select statement:

SELECT  
        itm.ItemId AS ItemId,
        itm.Value AS Value,
        itm.Id AS ParentId,
        1 AS IsPrimaryName
FROM    
        [dbo].[Item] AS itm
...

As I've mentioned above I have tried several different scenarios on the sp side, including: '1', 'true', 'TRUE' + declaring a BIT variable and returning it directly from the select statement but it all fails with similar exception.

Thx!

Upvotes: 2

Views: 4819

Answers (3)

Diego Mijelshon
Diego Mijelshon

Reputation: 52725

Query substitutions are used to map HQL literals to SQL, so they won't help here.

Your stacktrace is incomplete (you ate the inner exception) so I can't be sure, but I'd guess the error is that GetItemName returns an int column which you're trying to map that to a bool property.

Can you post the relevant SELECT from the SP, and your DTO class Mapping (It IS a DTO and not a mapped entity, right?)


Update: your SELECT statement needs a cast

SELECT ...
       CAST(1 as bit) IsPrimaryName
FROM ...

Upvotes: 5

jishi
jishi

Reputation: 24614

SQL Server supports boolean types IIRC so why don't you just rewrite your stored procedure "GetItemName" to return a boolean instead?

Otherwise I guess you need to modify the Dialect to support 1/0 as substitute for true/false.

Upvotes: 0

Arthur P
Arthur P

Reputation: 1060

Named queries are fine as long as you're sure that stored procedures will bring you additional benefits over ad hoc queries. Query.substitution parameter is transforming the data for SQL query, not back. Could you show the call stack please?

Upvotes: 0

Related Questions