2013-11-22 3 views
0

asp.net mvc4, C# 및 Entity Framework 5를 사용하고 있습니다. 사용자를 만들고 동시에 사용자에게 역할을 할당하려고합니다. 간단한 회원 (데이터베이스 첫 번째 방법),하지만 Roles.AddUserToRole("nuser", "Admin");SimpleMembership의 AddUserToRole을 사용하는 중 오류 : INSERT 문이 FOREIGN KEY 제약 조건과 충돌했습니다.

에서 FOREIGN KEY 제약 "FK_webpages_UsersInRoles_webpages_Roles"와 충돌 INSERT 문을 다음과 같은 오류가 발생. 충돌이 데이터베이스 "DbClick2Eat", 테이블 "dbo.webpages_Roles", 열 'RoleId'에서 발생했습니다. 명세서가 종료되었습니다. 여기

내 코드입니다 : -

[HttpPost] 
     [ValidateAntiForgeryToken] 
     public ActionResult CreateUserByAdmin(RegisterModel register, string role) 
     { 
      try 
      { 
       if (Roles.RoleExists(role)) 
       { 
        var model = register ?? new RegisterModel(); 
        WebSecurity.CreateUserAndAccount(model.UserName, model.Password); 
        if (WebSecurity.UserExists(model.UserName)) 
         Roles.AddUserToRole("admin1", "Admin"); 
       } 
       else 
        ModelState.AddModelError("NoRole", "Please select a role."); 

       var roles = Roles.GetAllRoles().ToList(); 
       ViewBag.DeliveryArea = new SelectList(roles.Select(x => new { Value = x, Text = x }), "Value", "Text"); 
       return View(); 
      } 
      catch (MembershipCreateUserException e) 
      { 
       ModelState.AddModelError("", AccountController.ErrorCodeToString(e.StatusCode)); 
      } 
      return View(); 
     } 

DB 스키마

CREATE TABLE [dbo].[webpages_Roles](
    [RoleId] [int] IDENTITY(1,1) NOT NULL, 
    [RoleName] [nvarchar](256) NOT NULL, 
CONSTRAINT [PK_webpages_Roles] PRIMARY KEY CLUSTERED 
(
    [RoleId] ASC 
)WITH (PAD_INDEX = OFF, STATISTICS_NORECOMPUTE = OFF, IGNORE_DUP_KEY = OFF, ALLOW_ROW_LOCKS = ON, ALLOW_PAGE_LOCKS = ON) ON [PRIMARY] 
) ON [PRIMARY] 

CREATE TABLE [dbo].[webpages_UsersInRoles](
    [RoleId] [int] NOT NULL, 
    [UserId] [int] NOT NULL, 
CONSTRAINT [PK_webpages_UsersInRoles] PRIMARY KEY NONCLUSTERED 
(
    [RoleId] ASC, 
    [UserId] ASC 
)WITH (PAD_INDEX = OFF, STATISTICS_NORECOMPUTE = OFF, IGNORE_DUP_KEY = OFF, ALLOW_ROW_LOCKS = ON, ALLOW_PAGE_LOCKS = ON) ON [PRIMARY] 
) ON [PRIMARY] 

ALTER TABLE [dbo].[webpages_UsersInRoles] WITH CHECK ADD CONSTRAINT [FK_webpages_UsersInRoles_UserProfile] FOREIGN KEY([UserId]) 
REFERENCES [dbo].[UserProfile] ([UserId]) 
GO 
ALTER TABLE [dbo].[webpages_UsersInRoles] CHECK CONSTRAINT [FK_webpages_UsersInRoles_UserProfile] 
GO 
ALTER TABLE [dbo].[webpages_UsersInRoles] WITH CHECK ADD CONSTRAINT [FK_webpages_UsersInRoles_webpages_Roles] FOREIGN KEY([RoleId]) 
REFERENCES [dbo].[webpages_Roles] ([RoleId]) 
GO 
ALTER TABLE [dbo].[webpages_UsersInRoles] CHECK CONSTRAINT [FK_webpages_UsersInRoles_webpages_Roles] 

-> "관리자는"역할 이름

역할 ID = 1, RoleName = 관리자

,

"관리자"역할을 고칠 수 줬음에 존재 ... 필요는 줄에

+1

자세한 내용은 역할 테이블 (DB Scheme 및 Admin 레코드)을 제공해 주시겠습니까? –

+0

@stefchri, 답장을 보내 주셔서 감사합니다. 나는 DB 스키마를 추가했다. – NeoDeveloper

답변

1

도움말 :

if (WebSecurity.UserExists(model.UserName)) roles.AddUserToRole("admin1", "Admin") 

당신이 purpous에 하드 "관리자 1"로 설정 했습니까? 왜냐하면이 조합이 이미 데이터베이스에있을 수 있으므로 외부 키 오류가 발생하는 이유 일 수 있습니다.

if (WebSecurity.UserExists(model.UserName)) roles.AddUserToRole(model.Username, "Admin") 

이 문제를 해결해야 :

그래서이 변경.

컨텍스트 CreateUserByAdmin에서 다음으로 나는 당신이 무엇을하려고하는지 잘 모르겠습니다. 관리자가 DB에 사용자를 추가하려고합니까, 아니면 관리자가되어야하는 사용자입니까?

는 업데이트

는이 같은 코드를 변경할 수 있습니까? {

  var model = register ?? new RegisterModel(); 
      if (!WebSecurity.UserExists(model.UserName)) 
      { 
       WebSecurity.CreateUserAndAccount(model.UserName, model.Password); 
      } 
      if (Roles.RoleExists(role)) 
      { 
       Roles.AddUserToRole(model.UserName, role); 
      } 
      else ModelState.AddModelError("NoRole", "Please select a role."); 

      var roles = Roles.GetAllRoles().ToList(); 
      ViewBag.DeliveryArea = new SelectList(roles.Select(x => new { Value = x, Text = x }), "Value", "Text"); 
      return View(); 
     } 
     catch (MembershipCreateUserException e) 
     { 
      ModelState.AddModelError("", AccountController.ErrorCodeToString(e.StatusCode)); 
     } 
     return View(); 

우리가 적어도 이미 기존 사용자에 FK 오류를 제외이 방법을 시도해보십시오. 이것이 작동하지 않으면 전체 예외 스택을 포함시킬 수 있습니까?

+0

답장을 보내 주셔서 감사합니다. 1. 처음에 다음 코드를 사용했습니다 // 모델에서 모델명과 사용자 이름 역할 Roles.AddUserToRole (model.UserName, role); 2. DBContext를 사용하여 데이터를 저장할 수 있지만 회원 생성 문제가 발생하는 이유를 알고 싶습니다. – NeoDeveloper

0

UserIdRoleId의 스왑 순서는 webpages_UsersInRoles입니다. UserId은 첫 번째 열이어야합니다.

+0

thnx이 문제를 해결해주었습니다. – NeoDeveloper

0

SimpleMembershp를 사용하는 경우 WebMatrix.WebData.SimpleRoleProvider을 사용하고 있습니다. 이 클래스의 정의를 살펴보면 AddUserToRole 메서드가 정의되어 있지 않으며 어떤 메서드를 사용하는지 알 수 없습니다. 이 방법을 사용할 수있는 이유는 System.Web.Security를 ​​사용하고 있기 때문입니다.역할 SimpleRoleProvider 인 실제 공급자로 전송하지 않고 역할을 전달합니다. 아, frustrations of the provider model. SimpleMembership을 사용할 때이 작업을 수행하는 안전한 방법은 다음과 같습니다.

var roles = (WebMatrix.WebData.SimpleRoleProvider)Roles.Provider; 
if (!roles.GetRolesForUser(model.UserName).Contains("Admin")) 
{ 
    roles.AddUsersToRoles(new[] { model.UserName }, new[] { "Admin" }); 
} 

코드에서는 코드를 사용자가 역할에 매핑하기 전에 사용자의 존재 여부 만 확인하면됩니다. 위 코드 스 니펫과 같이 역할에 사용자를 추가하기 전에 매핑이 이미 있는지 확인해야합니다. 이렇게하면 외래 키 위반이 제거됩니다.