0

プロジェクトと顧客モデルがあります。プロジェクト モデルには、マッピングを持つ顧客オブジェクトがあり<many-to-one>ます。これは、顧客が存在するが、プロジェクト テーブルにエントリがない場合に発生する可能性があります。

ユーザーがプロジェクトまたは顧客名を入力できるCustomerSearch機能を実行しています。ユーザーが顧客名のみを入力した場合、顧客がプロジェクトを持っているかどうかを考慮せずに、CustomerNameと一致するすべてのレコードが必要です。

サービスでこれを試しました。

ICriteria criteria = session.CreateCriteria(typeof(Project),"Project")
                    .CreateAlias("Project.customer","customer",NHibernate.SqlCommand.JoinType.RightOuterJoin)
                    .CreateAlias("Project.Coordinator", "Coordinator", NHibernate.SqlCommand.JoinType.InnerJoin);

                if (!string.IsNullOrEmpty(custName))
                {
                    criteria.Add(Expression.Like("customer.Name", custName, MatchMode.Start));
                }
                if (!string.IsNullOrEmpty(projectName))
                {
                    criteria.Add(Expression.Like("Project.Name", projectName, MatchMode.Start));
                }

                projectList = criteria.List<Project>().ToList();

プロジェクトテーブルには顧客のレコードがない可能性がありますが、顧客テーブルにはそれらのレコードが必要なため、RightOuterJoin to Customer を使用しました。

このコードは、projectListリストが表示されていても、プロジェクトテーブルにnullのレコードがないアイテムがいくつかある場合でも、エラーを出していません。

どうすればそのような記録を取得できますか?

4

1 に答える 1

0

右結合を使用すると、プロジェクトのすべてのフィールドが null になるため、NH は有効なプロジェクト オブジェクトを作成できず (ID が見つからない)、null が返されます。

値を何らかのオブジェクトに投影して、NH が null プロジェクトをどう処理するかを知るか、プロジェクトを使用せずに顧客を個別にクエリする必要があります (Futures を使用すると、個別のラウンドトリップは必要ありません)。

class SearchResult
{
    public int ProjectId { get; set; }
    public string ProjectName { get; set; }
    public int CustomerId { get; set; }
    public string CustomerName { get; set; }
}


ICriteria criteria = session.CreateCriteria(typeof(Project))
    .CreateAlias("Customer","customer", JoinType.RightOuterJoin)
    .CreateAlias("Coordinator", "Coordinator", NHibernate.SqlCommand.JoinType.InnerJoin);

if (!string.IsNullOrEmpty(custName))
{
    criteria.Add(Expression.Like("customer.Name", custName, MatchMode.Start));
}
if (!string.IsNullOrEmpty(projectName))
{
    criteria.Add(Expression.Like("Name", projectName, MatchMode.Start));
}

criteria.SetProjection(Projection.List()
    .Add(Projections.Property("Id"), "ProjectId")
    .Add(Projections.Property("Name"), "ProjectName")
    .Add(Projections.Property("customer.Id"), "CustomerId")
    .Add(Projections.Property("customer.Name"), "CustomerName"));

projectList = criteria
    .SetTransforer(Transformers.AliasToBean<SearchResult>())
    .List<Project>();
于 2012-10-26T09:30:19.013 に答える