1

Asp.net MVC 4 および EF 5.0 の使用

問題:

ドロップダウンリストでユーザーを選択し、投稿をアクションに送信するたびに。次の 2 つのことが起こります。

  1. 次のように、ユーザーが DinnerEvent に追加されます。

  2. 選択したユーザーが複製されたため、データベースのユーザー テーブルにユーザーの 2 つのインスタンスが作成されました。これは悪いことです。:(




セットアップはこちら

私は、DinnerEvent と User の 2 つのエンティティを作成しました。

DinnerEvent クラスには、アテンダント (ユーザー) のコレクションへのナビゲーション プロパティがあります。

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

DinnerEvent と Users の両方のリポジトリを作成しました

DinnerEventコントローラーAddAttendantToEvent アクション

[HttpPost]
public ActionResult AddAttendantToEvent(int users  , int EventID )
{
    if (ModelState.IsValid)
    {
        var user = userRepository.Find(users);
        dinnereventRepository.Find(EventID).Attendants.Add(user); //Add the User to the Event.
        dinnereventRepository.Save();
        return RedirectToAction("Index");
    }
    else
    {
        return View();
    }
}

ビュー- すべてのイベントを反復処理し、すべてのユーザーが入力されたドロップダウン リストを各イベントに追加します。

 @model Madklub.Models.ViewModel

 @foreach (var item in Model.events) {

 //Code to display available events

     @using (Html.BeginForm("AddAttendantToEvent", "DinnerEvents")) {

     @Html.Hidden("EventID", item.DinnerEventID);
     @Html.DropDownListFor(m => m.users, new SelectList(Model.users, "UserID", "RoomNumber"));

     <input type="submit" value="Add" />
}

ViewModel:

public class ViewModel
{
    public IQueryable<DinnerEvent> events { get; set; }
    public IQueryable<User> users { get; set; }
}

which is initialized like this:

Index Action in DinnerEventController:

public ViewResult Index()
{
    ViewModel viewdata = new ViewModel();
    viewdata.events = dinnereventRepository.AllIncluding(m => m.Attendants);
    viewdata.users = userRepository.All;
    return View(viewdata);
}

What am I doing wrong?

要求されたリポジトリ コード:

Save() メソッドのみを含むように縮小されました。

これはすべて Scaffolding によって自動生成されたコードであることに注意してください。

public class DinnerEventRepository : IDinnerEventRepository
{
    MadklubContext context = new MadklubContext();

    public void Save()
    {
        context.SaveChanges();
    }        
}

public class MadklubContext : DbContext
 {     

   public DbSet<Madklub.Models.User> Users { get; set; }

   public DbSet<Madklub.Models.MadklubEvent> MadklubEvents { get; set; }

 }
4

1 に答える 1

2

Unit of Work パターン: (ところで、リポジトリの/uow IDisposable を作成して、DbContext インスタンスをクリーンアップできるようにします)

public class DinnerEventRepository : IDinnerEventRepository
{
    MadklubContext _context = new MadklubContext();

    public void Save()
    {
        _context.SaveChanges();
    }  

    public DinnerEventRepository( MadklubContext context = null )
    {
        _context = context ?? new MadklubContext();
    }      
}

public class UserRepository //: IUserRepository
{
    MadklubContext _context = new MadklubContext();

    public void Save()
    {
        _context.SaveChanges();
    }  

    public UserRepository( MadklubContext context = null )
    {
        _context = context ?? new MadklubContext();
    }      
}

public class RsvpUnitOfWork // come up with a better name
{
    MadklubContext _context = new MadklubContext();

    public DinnerEventRepository DinnerEventRepo { get; private set; }
    public UserRepository UserRepo { get; private set; }

    public RsvpUnitOfWork()
    {
        DinnerEventRepo = new DinnerEventRepository( _context );
        UserRepo = new UserRepository( _context );
    }

    public void Save()
    {
        _context.SaveChanges();
    }
}

使用法:

[HttpPost]
public ActionResult AddAttendantToEvent(int users  , int EventID )
{
    if (ModelState.IsValid)
    {
        // this should be a using statement once you implement IDisposable
        // e.g. using( var uow = new RsvpUnitOfWork() ) { ... }
        var uow = new RsvpUnitOfWork();
        // you need to validate that user != null
        var user = uow.UserRepo.Find(users);
        // possible null reference exception if dinner event not found for EventID
        uow.DinnerEventRepo.Find(EventID).Attendants.Add(user); //Add the User to the Event.
        uow.Save();
        return RedirectToAction("Index");
    }
    else
    {
        return View();
    }
}
于 2013-10-04T20:43:18.753 に答える