NHibernate3.3.2.4000でOracleデータベースを使用しています。
テーブルからエンティティコレクションを選択できることを確認するために単体テストを設定しています。外観は次のとおりです。
[TestFixture]
public class UnitOfWorkIntegrationTests
{
private IUnitOfWork _unitOfWork;
private INHibernateSessionFactory _nHibernateSessionFactory;
private IActiveSessionManager _activeSessionManager;
[SetUp]
public void BeforeEachTest()
{
_nHibernateSessionFactory = new NHibernateSessionFactory();
_activeSessionManager = new ActiveSessionManager();
_unitOfWork = new UnitOfWork(_nHibernateSessionFactory, _activeSessionManager);
}
[Test]
public void ShouldFetchOAuthMemberships()
{
var oauths = _unitOfWork.OAuthMemberships.ToArray();
oauths.ShouldNotBeNull();
}
}
OAuthMembershipsコレクションをフェッチする行は、次の例外をスローしています。
クエリを実行出来ませんでした
[bckgrd_booklet_app.OAuthMembershipoauthmembe0_からid13_としてoauthmembe0_.idを選択します]
[SQL:bckgrd_booklet_app.OAuthMembershipoauthmembe0_からid13_としてoauthmembe0_.idを選択します]
私のOAuthMembershipクラスとマッピングは以下のとおりです。ご覧のとおり、テーブル名を「OAUTH_MEMBERSHIP」として定義していますが、生成されたSQLには、代わりにキャメルケースのクラス名が含まれています。テーブル名の規則が定義されていません。NHibernateがOracleで大文字と小文字を区別するテーブル名を無視するのはなぜですか?
public class OAuthMembership
{
public virtual int Id { get; set; }
public virtual string Provider { get; set; }
public virtual string ProviderUserId { get; set; }
public virtual UserProfile UserProfile { get; set; }
}
public class OAuthMembershipMap : ClassMapping<OAuthMembership>
{
public void OAuthMembership()
{
Table("OAUTH_MEMBERSHIP");
Id(x => x.Id, m => m.Column("ID"));
Property(x => x.Provider, m => m.Column("PROVIDER"));
Property(x => x.ProviderUserId, m => m.Column("PROVIDER_USER_ID"));
ManyToOne(x => x.UserProfile, m => m.Column("USER_PROFILE_ID"));
}
}
これが私のNHibernateSessionFactoryです。
public interface INHibernateSessionFactory
{
ISession Create();
}
public class NHibernateSessionFactory : INHibernateSessionFactory
{
private static readonly ILog Log = LogManager.GetLogger(typeof(NHibernateSessionFactory).Name);
private readonly static ISessionFactory SessionFactory;
public static string ConnectionString
{
get
{
return ConfigurationManager.ConnectionStrings["MyConnection"].Return(x => x.ConnectionString,
"Data Source=myServer;User ID=bckgrd_booklet_app;Password=myPass;");
}
}
static NHibernateSessionFactory()
{
try
{
var mapper = new ModelMapper();
mapper.AddMappings(Assembly.GetExecutingAssembly().GetExportedTypes());
HbmMapping domainMapping = mapper.CompileMappingForAllExplicitlyAddedEntities();
var configure = new NHibernate.Cfg.Configuration().Configure();
configure.AddMapping(domainMapping);
configure.BuildMappings();
configure.DataBaseIntegration(x =>
{
x.Driver<OracleClientDriver>();
x.Dialect<Oracle10gDialect>();
x.ConnectionStringName = ConnectionString;
})
.CurrentSessionContext<WebSessionContext>();
SessionFactory = configure.BuildSessionFactory();
}
catch (Exception ex)
{
Log.Error("NHibernateSessionFactory did not initialize correctly.", ex);
throw;
}
}
public ISession Create()
{
Log.Debug("Creating new session.");
return SessionFactory.OpenSession();
}
}
私のActiveSessionManager:
public interface IActiveSessionManager
{
void ClearActiveSession();
NHibernate.ISession GetActiveSession();
void SetActiveSession(NHibernate.ISession session);
}
public class ActiveSessionManager : IActiveSessionManager
{
[ThreadStatic]
private static ISession _current;
public ISession GetActiveSession()
{
return _current;
}
public void SetActiveSession(ISession session)
{
_current = session;
}
public void ClearActiveSession()
{
_current = null;
}
}
UnitOfWork定義の関連部分:
public interface IUnitOfWork
{
//...
IQueryable<OAuthMembership> OAuthMemberships { get; }
IQueryable<T> All<T>();
//...
}
public class UnitOfWork : IUnitOfWork
{
private readonly ISession _session;
//...
public IQueryable<OAuthMembership> OAuthMemberships
{
get { return All<OAuthMembership>(); }
}
public UnitOfWork(
INHibernateSessionFactory sessionFactory,
IActiveSessionManager activeSessionManager)
{
_session = sessionFactory.Create();
activeSessionManager.SetActiveSession(_session);
}
public IQueryable<T> All<T>()
{
return _session.Query<T>();
}
//...
}