1

I have a application that tracks school projects. Projects have subjects and those subjects have tasks. Though a project and a team have set leaders. Students are meant to take turn being leaders of different tasks and subjects( Subjects are sections of the different books we are covering) . What i noticed was that inside my subject's and task's objects, the leaders of those objects were not getting loaded. So I'm trying to add a nested include, that i have seen online, in my entity framework query, so that they get loaded.However, when i run my query it gives me this error. Can anyone see what I'm doing wrong and know how to fix this?

            string name = data.value;
            var project = await context.Projects
            .Include(p => p.Subjects)
                .ThenInclude(s => s.Tasks)
            .Include(p => p.Subjects.Select(s => s.Leader))
            .Include(p => p.Students)
                //.ThenInclude(h => h)
            .Include(p => p.Leader)
            .Include(p => p.Team)
                .ThenInclude(t => t.Leader)
            .Include(p => p.Type)
            .AsNoTracking()
            .FirstOrDefaultAsync(p => p.Name == name);

Project.cs

public class Project
    {
        [Key]
        public int ID { get; set; }

        public int TypeID { get; set; }
        public int? TeamID { get; set; }
        public int? LeaderID { get; set; }

        public string Name { get; set; }
        public string Number { get; set; }
        public string Details { get; set; }
        public bool IsActive { get; set; }


        [ForeignKey("TypeID")]
        public virtual ProjectType Type { get; set; }
        [ForeignKey("TeamID")]
        public virtual Team Team { get; set; }
        [ForeignKey("LeaderID")]
        public virtual User Leader { get; set; }

        public virtual ICollection<Subject> Subjects{ get; set; }
        public virtual ICollection<User> Students { get; set; }


 public Project()
        {
            Subjects= new List<Subject>();
            Students = new List<User>();
        }
    }

Subjects.cs

public class Subject
{
    [Key]
    public int ID { get; set; }
    // 
    public int? ProjectID { get; set; }
    public int TypeID { get; set; }
    public int? LeaderID{ get; set; }

    public string Name { get; set; }
    public string Details { get; set; }
    public Decimal Estimate { get; set; }


    [ForeignKey("ProjectID")]
    public virtual Project Project { get; set; }
    [ForeignKey("TypeID")]
    public virtual SubjectType Type { get; set; }
    [ForeignKey("LeaderID")]
    public virtual User Leader { get; set; }

    public virtual ICollection<Task> Tasks { get; set; }

    public Subject()
    {
        Tasks = new List<Task>();
    }

Tasks

  public class Task
    {
        [Key]
        public int ID { get; set; }
        public int? SubjectID { get; set; }
        public int? TypeID { get; set; }
        public int? LeaderID{ get; set; }

        public string Name { get; set; }
        public string Details { get; set; }
        public Decimal Estimate { get; set; }

        [ForeignKey("SubjectID")]
        public virtual Subject Subject { get; set; }
        [ForeignKey("TypeID")]
        public virtual TaskType Type { get; set; }
        [ForeignKey("LeaderID")]
        public virtual User Leader { get; set; }
        public Task() { }
    }

Error

Message = "The property expression 'p => {from Subjects s in [p].Subjects select [s].Leader}' is not valid. The expression should represent a property access: 't => t.MyProperty'. For more information on including related data, see http://go.microsoft.com/fwl...
2
  • You might consider using the tag entity-framework-core. Commented Apr 20, 2017 at 18:38
  • Thank, i updated it to include entity-framework-core. Commented Apr 20, 2017 at 18:39

1 Answer 1

5

The error messages tells you already.

You have .Include(p => p.Subjects.Select(s => s.Leader)), which is how you did nested includes in EF6. In EF Core you have to use .ThenInclude!

So just change .Include(p => p.Subjects.Select(s => s.Leader)) to .Include(p => p.Subjects).ThenInclude(s => s.Leader))

Sign up to request clarification or add additional context in comments.

3 Comments

So i have to do two includes of subjects? .Include(p => p.Subjects) .ThenInclude(s => s.Tasks) .Include(p => p.Subjects) .ThenInclude(s => s.Leader)
Once for every navigation property of Subjects, yes.
Don't think so. Alternatively you use Projections (.Select(m => new { Tasks = m.Subjects.Tasks, ... } since then Includes will be ignored and IF finds out via projection which entities it needs to load. You should use SSDT though to validate it

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.