I'm getting a SQL query from NH, and it's generating a column that does not exist (thus producing an ADOException from NH).
SELECT roles0_.CreatedBy_id as CreatedBy4_1_,
roles0_.Id as Id1_,
roles0_.Id as Id18_0_,
roles0_.RoleDescription as RoleDesc2_18_0_,
roles0_.User_id as User3_18_0_
FROM [Role] roles0_
WHERE roles0_.CreatedBy_id=?
My problem is that I can't figure out where the CreatedBy
column is coming from. Here's my class structure.
public abstract class DomainEntity
{
public virtual int Id { get; set; }
}
public class User : DomainEntity
{
/* all the regular stuff you'd expect */
public virtual IList<Role> Roles { get; private set; }
}
public class Role : DomainEntity
{
public virtual User User { get; set; }
public virtual string RoleDescription { get; set; }
}
At app startup, I can inspect the configuration, and I can see the ColumnIterator
for the Role class map. It has 4 items in the dictionary: id, user_id, roledescription, and createdby_id. So the query is legit based on the configuration, but I can't figure out the configuration based on the classes.
Yes, I have cleared my ASP.NET DLL cache, deleted the bin and obj directories, and anything else like that I could think of.
Edit #1
This is my Fluently.Configure statement
_configuration = Fluently.Configure()
.Database(MsSqlConfiguration.MsSql2008.ConnectionString(_connectionString))
.Mappings(m => m.AutoMappings.Add(GetPersistenceModel()))
.BuildConfiguration();
And this is my call for GetPersistenceModel()
private static AutoPersistenceModel GetPersistenceModel()
{
var configuration = new CustomAutomappingConfiguration();
return AutoMap.AssemblyOf<User>(configuration)
.IgnoreBase(typeof(DomainEntity))
.UseOverridesFromAssemblyOf<UserMapOverride>()
.Conventions.Setup(c =>
{
c.Add<CustomHasManyConvention>();
});
}
My Custom config says to only map public autoproperties. This is so I can add other calculated properties to my domain entities. The user map override makes sure that the table name is [User]
, because I was getting SQL errors using just User
. The Custom HasMany convention sets cascade all-delete-orphan for all has many relationships.
Edit #2
This gets even better. This is the column iterator after creating the configuration object, but before creating the session factory object.
See? No createdby_id
column in the list of mapped columns. This is the column iterator after creating the session factory object.
And now there's a createdby_id
column. I am really lost now.
Edit 3
OK, I think I'm onto something now.
I got a new requirement from my customer last week. That requirement was that they wanted to know who had created an assignment. So it has a new property as follows.
public class Assignment : DomainEntity {
/* etc. */
public virtual User CreatedBy { get; set; }
/* etc. */
}
In my Assignment table, it now has a column like this.
[CreatedBy_id] INT NULL
And there's a FK to the User table on this new column.
If I comment out this property, everything works again. The SQL goes back to querying by user_id
, exactly the way I would it expect it to be. Is there some type of override I can use to keep this from happening like this?