mhfmn
mhfmn

Reputation: 41

EF Many-To-Many Relation Adding Data

I am trying to achieve a many to many relationship between Users and Groups with the entity framework v6.1.3 in C# (so 1 User can be in more than 1 Groups and Groups are consisting of 1 or more users).

The User-Model looks as follows: User.cs

public User() { this.Usergroups = new HashSet<Usergroup>(); }

[Key]
[Required]
[MaxLength(150)]
public string UserName { get; set; }

public virtual ICollection<Usergroup> Usergroups { get; set; }

The Group-Model looks as follows: Usergroup.cs

public Usergroup() { this.Users= new HashSet<Users>(); }

[Key]
[Required]
[MaxLength(150)]
public string UserGroupName { get; set; }

public virtual ICollection<User> Users{ get; set; }

In the DbContext class I've inserted the DbSets and the code for the modelBuilder to automatically create the join table. SqlDbContext.cs

 public class SqlDbContext : DbContext, IUnitOfWork
{
    public DbSet<User> Users { get; set; }
    public DbSet<Usergroup> Usergroups{get; set;}


    protected override void OnModelCreating(DbModelBuilder modelBuilder)
    {
        modelBuilder.Entity<User>()
             .HasMany<Usergroup>(s => s.Usergroups)
             .WithMany(c => c.Users)
             .Map(cs =>
             {
                 cs.MapLeftKey("UserRefId");
                 cs.MapRightKey("UsergroupRefId");
                 cs.ToTable("UsergroupOverview");
             });
     }
 }

After adding the migration, the UsergroupOverview gets auto-created. In the Seed method of my Configuration.cs i was trying to create some sample groups and users and assign those to each other, but unfortunately both the column Usergroups in User and vice versa do not exist after the db migration. Configuration.cs

protected override void Seed(SqlDbContext context)
{
     var usergroups = new List<Usergroup> {
            new Usergroup{ UserGroupName="TestGroup", RoleName=roles[1].RoleName}
       };
     User sampleUser = context.Users.Find("user");

     sampleUser.Usergroups.Add(usergroups[1]); // add usergroup to user
     usergroups[1].Users.Add(sampleUser);      // add user to usergroup    

     context.SaveChanges();
  }

What do I miss here? Do I need to add users/usergroups within the created join table UsergroupOverview? Is it even the correct way to assign users to usergroups ?

database diagram

Thanks in advance

Upvotes: 1

Views: 150

Answers (1)

mrsWhite
mrsWhite

Reputation: 79

try:

var userToUpdate = db.sprawy
            .Include(i => i.Usergroups)
             .Where(i => i.UserName  == 'user')
             .Single();

it works for me:

 public ActionResult EditPost(int? id, string[] selectedGroups)
    {
        if (id == null)
        {
            return new HttpStatusCodeResult(HttpStatusCode.BadRequest);
        }
        // var courseToUpdate = db.Pracownicy.Find(id);
  var userToUpdate = db.sprawy
            .Include(i => i.Usergroups)
             .Where(i => i.UserName  == 'user')
             .Single();
        if (TryUpdateModel(userToUpdate, "",
          new string[] { "UserName","Email" }))
        {
            try
            {
                AddorUpdate(userToUpdate, selectedGroups);
                db.SaveChanges();

                return RedirectToAction("Index");
            }
            catch (RetryLimitExceededException /* dex */)
            {
                //Log the error (uncomment dex variable name and add a line here to write a log.
                ModelState.AddModelError("", "Unable to save changes. Try again, and if the problem persists, see your system administrator.");
            }
        }
        return View(userToUpdate);
    }



private void AddorUpdate(User spr, string[] selected)
    {
        spr.Usergroups = new List<Usergroup>();
        if (selected == null)
        {
            spr.Usergroups = new List<Usergroup>();
            return;
        }
        var selectedGroupHS = new HashSet<string>(selected);
        var Usergroup = new HashSet<int>(spr.Usergroups.Select(c => c.Group_Id));
        foreach (var ug in db.Usergroup)
        {
            if (selectedGroupHS.Contains(ug.Group_Id.ToString()))
            {
                if (!Usergroup.Contains(ug.Group_Id))
                {
                    spr.Usergroups.Add(ug);
                }
            }
            else
            {
                if (Usergroup.Contains(ug.Group_Id))
                {
                    spr.Usergroups.Remove(ug);
                }
            }
        }
    }
      modelBuilder.Entity<User>()
       .HasMany(c => c.Usergroups).
        WithMany(i => i.Users)
       .Map(t => t.MapLeftKey("User_ID")
           .MapRightKey("Usergroups_Id")
           .ToTable("UsergroupOverview"));

Upvotes: 1

Related Questions