简体   繁体   English

Nhibernate查询

[英]Nhibernate query

I have this domain model, 我有这个领域模型,

class UserInfo{
    int UserId{get;set;}
    string UserName{get;set;}
    IList<Task> Tasks{get;set;}
}

class Task{
    int TaskId{get;set;}
    string TaskName{get;set;}
    UserInfo AssignedTo{get;set;}
}

class UserMap: ClassMap<UserInfo>
{ 
    public UserMap()
    {
        Id(x=>x.UserId);
        Map(x=>x.UserName)
        HasMany(x=>x.Tasks);
    }
 }

Now, a user may have any number of tasks assigned to him, but Active is always none or one. 现在,可以为用户分配任意数量的任务,但是“活动”始终是一个或一个。 This is stored in another table and defined through another entity. 它存储在另一个表中并通过另一个实体定义。 So, if there is an active task for a child, there exists a record in ActiveTask table. 因此,如果有一个孩子的活动任务,则ActiveTask表中存在一条记录。

class ActiveTask{
    int Id{get;set;}
    int UserId{get;set;}
    int TaskId{get;set;}
    datetime CreatedOn{get;set;}
}

Questions, 问题,

  • How to map ACTIVETASK with USERINFO 如何使用USERINFO映射ACTIVETASK
  • I want to fetch a list of users, along with active task (if any). 我想获取用户列表以及活动任务(如果有)。

Please suggest how to do it 请提出建议

I think you'd be hard-pressed to find the one good answer because it will depend on other factors such as the number of tasks you expect a given user to have. 我认为您很难找到一个好的答案,因为这将取决于其他因素,例如您希望给定用户执行的任务数量。 That said, it sounds like you're trying to use a single collection of Task and simply mark one as active. 就是说,这听起来像您正在尝试使用单个Task集合并将其简单标记为活动。 From a domain perspective, I'd bet this is the reality of things. 从领域的角度来看,我敢打赌这是事物的现实。 People have many tasks, one is active. 人们有许多任务,其中一项是活跃的。 An active task is still a task. 活动任务仍然是一项任务。

If that's the case, then one option is to add an IsActive property to your Task object, then set your fetch strategy in the mapping to be eager (otherwise you'll have a select n+1 issue). 如果是这种情况,那么一个选择是将IsActive属性添加到Task对象,然后将映射中的获取策略设置为急切(否则将出现select n + 1问题)。 Then, your ActiveTask property could use linq to select the Task in the collection that has Active == true . 然后,您的ActiveTask属性可以使用linq在具有Active == true的集合中选择Task

If you went this route, then you'd want to add logic in your class to set a task active such that all other tasks were set to inactive. 如果走了这条路线,那么您想在课堂上添加逻辑以将任务设置为活动状态,以便将所有其他任务设置为不活动状态。 Something like this: 像这样:

class UserInfo
{
    public virtual int UserId{get;set;}
    public virtual string UserName{get;set;}
    public virtual IList<Task> Tasks{get;set;}

    public virtual Task ActiveTask
    {
        get
        {
            return Tasks.FirstOrDefault(t => t.IsActive == true);
        {
    }

    public void SetActive(Task task)
    {
        // Set all tasks to inactive
        // Set the task in question to active
    }
}

If it were me I would probably also change the Tasks collection from an autoproperty to having a backing field and use protected internal for setting so you could ensure that the list is only assigned during mapping. 如果是我,我可能还会将Tasks集合从自动属性更改为具有后备字段,并使用protected internal进行设置,以便您可以确保仅在映射期间分配列表。

Note that if you have a large number of users or tasks the eager fetch strategy could become costly. 请注意,如果您有大量的用户或任务,那么急切的获取策略可能会变得昂贵。 In this case, then you probably would want to use a separate table to track which task is active and map that way. 在这种情况下,您可能希望使用一个单独的表来跟踪哪个任务处于活动状态并以这种方式进行映射。

Update 更新资料

I went back and checked on some other projects I had done that had similar requirements, and in one case I actually changed it so the parent object held a reference to the active child object. 我回去检查了我做过的其他一些项目,这些项目有类似的要求,在一种情况下,我实际上进行了更改,因此父对象持有对活动子对象的引用。 So your UserInfo table in the database would have an FK column of ActiveTask_Id which would relate to the Task table's PK. 因此,数据库中的UserInfo表将具有ActiveTask_Id的FK列,该列与Task表的PK有关。 Then your mapping of the user would be like (assuming you're overriding an automap): 然后,您对用户的映射就像(假设您要覆盖自动映射):

public class UserInfoOverride : IAutoMappingOverride<UserInfo>
{
    public void Override(AutoMapping<UserInfo> mapping)
    {
        mapping.References(x => x.ActiveTask).Fetch.Join();
    }
}

You would then simply set a task to the ActiveTask property of your UserInfo object and save. 然后,您只需将一个任务设置为UserInfo对象的ActiveTask属性并保存。

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM