0
votes

I'm trying to model a tree structure for orders in Entity Framework. Right now I've go the following:

public class ProjectModel
{
    [Key]
    public int Id { get; set; }

    [Required]
    public string Name { get; set; }

    [Required]
    public int CustomerId { get; set; }

    public virtual List<ProjectNode> Nodes { get; set; }
}

public class ProjectNode
{
    [Key]
    public int Id { get; set; }

    [Required]
    public string Name { get; set; }

    public string Path { get; set; }

    public int? ParentId { get; set; }

    [ForeignKey("ParentId")]
    public virtual List<ProjectNode> Children { get; set; }
}

What I need to be able to do is get a reference to the root ProjectModel at any level of ProjectNode in order to authorize a given user actually having permission to view and change the project which contains the ProjectNode.

public class ProjectNode {
    public int ProjectId { get; set; }  //<-- this
...

public class ProjectModel {
    [Key]
    public int Id { get; set; }         //<-- containing the value of this
}

My question is whether its possible to have a theoretical ProjectId property populated at every level of the tree structure, or if I need to set it manually.

I had something working that at first blush appeared to allow this functionality, but upon further investigation only populated the ProjectId for ProjectNodes contained in the ProjectModel's Nodes property.

It seems to me like it would be super inefficient to recurse backwards through the structure to get to the root.

1
You should keep key names the same across tables. Id under ProjectModel should be ProjectModelID and have the same name under ProjectNode. It keeps everything easy to read. As for your question, are you asking if children can exist without parents? - TestWell
My question (which I may have phrased poorly) is: is there a way to automatically propagate the root ProjectModel Id to all ProjectNodes underneath it? Or now that I think about it more, even better, to propagate the ProjectModel's CustomerId to any and all descendants? I have it working so that all descendants directly under the root ProjectModel automatically get a field from the model... - Jony Thrive

1 Answers

1
votes

Credit due to @TestWell for this answer -

Apparently, all I needed to do for EF to automatically populate the ProjectId property on the ProjectNode was to change the name of the Id property in ProjectModel to ProjectId.

Unfortunately, this doesn't appear to work if I add a CustomerId property to the ProjectNode that I would like automatically populated from the property of the same name on the node's root ProjectModel, which I realized is the more efficient solution to what I'm trying to do.