Я получаю SQL-запрос от NH, и он генерирует несуществующий столбец (таким образом вызывая исключение ADOException от 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=?
Моя проблема в том, что я не могу понять, откуда берется столбец CreatedBy
. Вот моя структура классов.
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; }
}
При запуске приложения я могу проверить конфигурацию и увидеть ColumnIterator
для карты классов ролей. В словаре есть 4 элемента: id, user_id, roledescription и createdby_id. Таким образом, запрос является допустимым на основе конфигурации, но я не могу определить конфигурацию на основе классов.
Да, я очистил свой кеш ASP.NET DLL, удалил каталоги bin и obj и все, что я мог придумать, в этом роде.
Изменить №1
Это мой оператор Fluently.Configure
_configuration = Fluently.Configure()
.Database(MsSqlConfiguration.MsSql2008.ConnectionString(_connectionString))
.Mappings(m => m.AutoMappings.Add(GetPersistenceModel()))
.BuildConfiguration();
И это мой призыв к 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>();
});
}
Моя настраиваемая конфигурация говорит, что нужно отображать только публичные автосвойства. Это сделано для того, чтобы я мог добавлять другие вычисляемые свойства к объектам моего домена. Переопределение пользовательской карты гарантирует, что имя таблицы - [User]
, потому что я получал ошибки SQL, используя только User
. Соглашение Custom HasMany устанавливает каскадное удаление-все-удаление-сирота, поскольку все имеет много взаимосвязей.
Изменить № 2
Это становится еще лучше. Это итератор столбца после создания объекта конфигурации, но перед созданием объекта фабрики сеанса.
Видеть? В списке сопоставленных столбцов нет createdby_id
столбца. Это итератор столбца после создания объекта фабрики сеанса.
А теперь есть столбец createdby_id
. Я действительно потерялся.
Изменить 3
Хорошо, я думаю, что сейчас кое-что понял.
На прошлой неделе я получил новое требование от моего клиента. Это требование заключалось в том, что они хотели знать, кто создал задание. Итак, у него есть следующее новое свойство.
public class Assignment : DomainEntity {
/* etc. */
public virtual User CreatedBy { get; set; }
/* etc. */
}
В моей таблице назначений теперь есть такой столбец.
[CreatedBy_id] INT NULL
И в этом новом столбце есть FK для таблицы User.
Если я закомментирую это свойство, все снова заработает. SQL возвращается к запросам user_id
, именно так, как я ожидал. Есть ли какое-то переопределение, которое я могу использовать, чтобы этого не произошло?
_id
указывает, что это отношение внешнего ключа, которое было сопоставлено, поэтому где-то в вашем домене должно быть свойство или классCreatedBy
; автоматизатор работает, отражая свойства и классы в ваших сборках, он не может просто создавать вещи. - person James Gregory   schedule 03.10.2010CustomHasManyConvention
&UserMapOverride
. - person Yogesh   schedule 03.10.2010