I am trying to figure out the best way to ensure that a List of objects within another object are always ordered the same way.
I currently have my class Jobsite:
public class Jobsite
{
#region Class Properties
[Key]
public long Id { get; set; }
...
private DateTime? _createdOn;
public DateTime CreatedOn
{
get
{
if (_createdOn.HasValue)
return _createdOn.Value;
else
return DateTime.UtcNow;
}
set { _createdOn = value; }
}
public long? CreatedById { get; set; }
#endregion
#region Navigation Properties
[ForeignKey("CustomerId")]
public Customer Customer { get; set; }
public List<Job> Jobs { get; set; }
public List<JobsiteNote> JobsiteNotes { get; set; }
#endregion
}
This class is being populated by Entity Framework like so:
public class EFJobsiteRepository : IJobsiteRepository
{
private EFDbContext _context = new EFDbContext();
public IQueryable<Jobsite> Jobsites
{
get
{
return _context.Jobsite
.Include("JobsiteNotes.CreatedBy")
.Include("Customer")
.Include("Jobs.JobType");
}
}
public void Save(Jobsite jobsite)
{
if (jobsite.Id == 0)
{
_context.Jobsite.Add(jobsite);
}
else
{
_context.Entry(jobsite).State = EntityState.Modified;
}
_context.SaveChanges();
}
}
Pretty standard stuff. Everything works fine. In my view, I want to list all the "JobsiteNotes", however I want them to be ordered decending
So right now, I have in my view:
<div>
@foreach (var note in Model.Jobsite.JobsiteNotes.OrderByDescending(x => x.CreatedOn))
{
@Html.Partial("Note", note)
}
</div>
This works fine, however I think ideally, this sorting should be done in the getter/setter of that list. This way, I don't have to explicitly order the list of notes in every view I want to use them.
I figured I could just do something like this:
private List<JobsiteNote> _jobsiteNotes;
public List<JobsiteNote> JobsiteNotes
{
get
{
return _jobsiteNotes.OrderByDescending(x => x.CreatedOn).ToList();
}
set
{
_jobsiteNotes = value;
}
}
However, the list is empty... This is probably something silly, but how come I can't add the Order logic here?
EDIT The Jobsite class is being initialized in the controller. I'm using the Ninject library for dependency injection.
This code below is what populates the _jobsiteNotes List in the Jobsite class. EF does this all for me. When I get the jobsite from the repository, it brings it back with all the notes associated with it.
public class JobsiteController : Controller
{
private IJobsiteRepository _jobsiteRepository;
public JobsiteController(IJobsiteRepository jobsiteRepo)
{
_jobsiteRepository = jobsiteRepo;
}
// GET: Jobsite
public ActionResult Index()
{
return View();
}
public ActionResult Manage(long id)
{
var jobsite = _jobsiteRepository.Jobsites.FirstOrDefault(x => x.Id == id);
var model = new JobsiteViewModel
{
ActiveJobId = jobsite.Jobs.FirstOrDefault().Id,
Jobsite = jobsite
};
return View(model);
}
}
EDIT 2 I found this SO question: How to include sorted navigation properties with Entity Framework
I am trying to order the navigation property. However, that solution doesn't seem like the best way to do this.
When Entity Framework is populating the JobsiteNotes, it doesn't use the setter at all. I put a breakpoint right after this line in my controller:
var jobsite = _jobsiteRepository.Jobsites.FirstOrDefault(x => x.Id == id);
And all the notes get populated into the list, however it never hits the setter.