사용자에 역할 할당(C#)Assigning Roles to Users (C#)

Scott Mitchellby Scott Mitchell

코드 다운로드 또는 PDF 다운로드Download Code or Download PDF

이 자습서에서는 사용자가 어떤 역할에 속하는지를 관리 하는 데 도움을 주는 두 개의 ASP.NET 페이지를 빌드합니다.In this tutorial we will build two ASP.NET pages to assist with managing what users belong to what roles. 첫 번째 페이지에는 지정 된 역할에 속한 사용자, 특정 사용자가 속한 역할 및 특정 역할에서 특정 사용자를 할당 하거나 제거 하는 기능을 확인 하는 기능이 포함 됩니다.The first page will include facilities to see what users belong to a given role, what roles a particular user belongs to, and the ability to assign or remove a particular user from a particular role. 두 번째 페이지에서는 새로 만든 사용자가 속한 역할을 지정 하는 단계가 포함 되도록 CreateUserWizard 컨트롤을 보강 합니다.In the second page we will augment the CreateUserWizard control so that it includes a step to specify what roles the newly created user belongs to. 이는 관리자가 새 사용자 계정을 만들 수 있는 시나리오에서 유용 합니다.This is useful in scenarios where an administrator is able to create new user accounts.

소개Introduction

이전 자습서 에서는 역할 프레임 워크 및 SqlRoleProvider를 검사 합니다. Roles 클래스를 사용 하 여 역할을 만들고, 검색 하 고, 삭제 하는 방법을 살펴보았습니다.The previous tutorial examined the Roles framework and the SqlRoleProvider; we saw how to use the Roles class to create, retrieve, and delete roles. 역할을 만들고 삭제 하는 것 외에도 역할에서 사용자를 할당 하거나 제거할 수 있어야 합니다.In addition to creating and deleting roles, we need to be able to assign or remove users from a role. 아쉽게도 ASP.NET는 사용자가 어떤 역할에 속해 있는지를 관리 하기 위한 웹 컨트롤과 함께 제공 되지 않습니다.Unfortunately, ASP.NET does not ship with any Web controls for managing what users belong to what roles. 대신, 이러한 연결을 관리 하기 위해 고유한 ASP.NET 페이지를 만들어야 합니다.Instead, we must create our own ASP.NET pages to manage these associations. 좋은 소식은 사용자를 역할에 추가 하 고 제거 하는 것입니다.The good news is that adding and removing users to roles is quite easy. Roles 클래스는 하나 이상의 역할에 하나 이상의 사용자를 추가 하는 여러 메서드를 포함 합니다.The Roles class contains a number of methods for adding one or more users to one or more roles.

이 자습서에서는 사용자가 어떤 역할에 속하는지를 관리 하는 데 도움을 주는 두 개의 ASP.NET 페이지를 빌드합니다.In this tutorial we will build two ASP.NET pages to assist with managing what users belong to what roles. 첫 번째 페이지에는 지정 된 역할에 속한 사용자, 특정 사용자가 속한 역할 및 특정 역할에서 특정 사용자를 할당 하거나 제거 하는 기능을 확인 하는 기능이 포함 됩니다.The first page will include facilities to see what users belong to a given role, what roles a particular user belongs to, and the ability to assign or remove a particular user from a particular role. 두 번째 페이지에서는 새로 만든 사용자가 속한 역할을 지정 하는 단계가 포함 되도록 CreateUserWizard 컨트롤을 보강 합니다.In the second page we will augment the CreateUserWizard control so that it includes a step to specify what roles the newly created user belongs to. 이는 관리자가 새 사용자 계정을 만들 수 있는 시나리오에서 유용 합니다.This is useful in scenarios where an administrator is able to create new user accounts.

이제 시작하겠습니다.Let's get started!

어떤 역할에 속한 사용자 나열Listing What Users Belong To What Roles

이 자습서의 첫 번째 비즈니스 순서는 사용자를 역할에 할당할 수 있는 웹 페이지를 만드는 것입니다.The first order of business for this tutorial is to create a web page from which users can be assigned to roles. 사용자를 역할에 할당 하는 방법을 고려 하기 전에 먼저 어떤 역할에 속하는 사용자를 확인 하는 방법을 집중적으로 살펴보겠습니다.Before we concern ourselves with how to assign users to roles, let's first concentrate on how to determine what users belong to what roles. 이러한 정보를 표시 하는 방법에는 "role" 또는 "by user"와 같은 두 가지가 있습니다.There are two ways to display this information: "by role" or "by user." 방문자가 역할을 선택한 다음 해당 역할에 속하는 모든 사용자를 표시 하거나 ("역할 기준" 표시) 방문자에 게 사용자를 선택 하 고 해당 사용자에 게 할당 된 역할 ("사용자" 표시)을 표시할 수 있습니다.We could allow the visitor to select a role and then show them all of the users that belong to the role (the "by role" display), or we could prompt the visitor to select a user and then show them the roles assigned to that user (the "by user" display).

"역할별" 보기는 방문자가 특정 역할에 속한 사용자 집합을 알고자 하는 경우에 유용 합니다. 방문자가 특정 사용자의 역할을 알고 있어야 하는 경우 "사용자" 보기가 적합 합니다.The "by role" view is useful in circumstances where the visitor wants to know the set of users that belong to a particular role; the "by user" view is ideal when the visitor needs to know a particular user's role(s). 페이지에 "역할 기준" 및 "사용자" 인터페이스를 모두 포함 해 보겠습니다.Let's have our page include both "by role" and "by user" interfaces.

"사용자" 인터페이스 만들기를 시작 합니다.We will start with creating the "by user" interface. 이 인터페이스는 드롭다운 목록과 확인란 목록으로 구성 됩니다.This interface will consist of a drop-down list and a list of checkboxes. 드롭다운 목록은 시스템의 사용자 집합으로 채워집니다. 이 확인란은 역할을 열거 합니다.The drop-down list will be populated with the set of users in the system; the checkboxes will enumerate the roles. 드롭다운 목록에서 사용자를 선택 하면 사용자가 속한 역할이 검사 됩니다.Selecting a user from the drop-down list will check those roles the user belongs to. 그러면 페이지를 방문 하는 사용자가 확인란을 선택 하거나 선택 취소 하 여 해당 역할에서 선택한 사용자를 추가 하거나 제거할 수 있습니다.The person visiting the page can then check or uncheck the checkboxes to add or remove the selected user from the corresponding roles.

Note

사용자 계정을 나열 하기 위해 드롭다운 목록을 사용 하는 것은 수백 명의 사용자 계정이 있는 웹 사이트에 적합 한 선택이 아닙니다.Using a drop-down list to list the user accounts is not an ideal choice for websites where there may be hundreds of user accounts. 드롭다운 목록은 사용자가 비교적 짧은 옵션 목록에서 한 항목을 선택할 수 있도록 디자인 되었습니다.A drop-down list is designed to allow a user to pick one item from a relatively short list of options. 목록 항목 수가 늘어남에 따라 신속 하 게 복잡해 집니다.It quickly becomes unwieldy as the number of list items grows. 잠재적으로 많은 수의 사용자 계정을 포함 하는 웹 사이트를 작성 하는 경우 다른 사용자 인터페이스를 사용 하는 것이 좋습니다. 예를 들어, 방문자에 게 문자를 선택 하 고 해당 문자를 선택 하 라는 메시지를 표시 하는 필터링 가능한 인터페이스 또는 선택한 문자로 시작 하는 사용자 이름이 있는 사용자를 표시 합니다.If you are building a website that will have potentially large numbers of user accounts, you may want to consider using an alternative user interface, such as a pageable GridView or a filterable interface that lists prompts the visitor to choose a letter and then only shows those users whose username starts with the selected letter.

1 단계: "사용자" 사용자 인터페이스 빌드Step 1: Building the "By User" User Interface

UsersAndRoles.aspx 페이지를 엽니다.Open the UsersAndRoles.aspx page. 페이지 맨 위에서 ActionStatus 이라는 레이블 웹 컨트롤을 추가 하 고 해당 Text 속성을 지웁니다.At the top of the page, add a Label Web control named ActionStatus and clear out its Text property. Microsoft는이 레이블을 사용 하 여 수행 된 작업에 대 한 피드백을 제공 하 고, "사용자 Tito를 관리자 역할에 추가 했습니다." 또는 "사용자 Jisun이 감독자 역할에서 제거 되었습니다."와 같은 메시지를 표시 합니다.We will use this Label to provide feedback on the actions performed, displaying messages like, "User Tito has been added to the Administrators role," or "User Jisun has been removed from the Supervisors role." 이러한 메시지를 출력 하기 위해 레이블의 CssClass 속성을 "Important"로 설정 합니다.In order to make these messages stand out, set the Label's CssClass property to "Important".

<p align="center"> 

     <asp:Label ID="ActionStatus" runat="server" CssClass="Important"></asp:Label> 
</p>

그런 다음 Styles.css 스타일 시트에 다음 CSS 클래스 정의를 추가 합니다.Next, add the following CSS class definition to the Styles.css stylesheet:

.Important 
{ 
     font-size: large; 
     color: Red; 
}

이 CSS 정의는 긴 빨강 글꼴을 사용 하 여 레이블을 표시 하도록 브라우저에 지시 합니다.This CSS definition instructs the browser to display the Label using a large, red font. 그림 1에서는 Visual Studio 디자이너를 통해 이러한 효과를 보여 줍니다.Figure 1 shows this effect through the Visual Studio Designer.

레이블의 CssClass 속성을 하면 빨간색 글꼴이 크게 생성 됩니다.The Label's CssClass Property Results in a Large, Red Font

그림 1: 레이블의 CssClass 속성으로 인해 큰 빨간색 글꼴이 표시 됩니다 (전체 크기 이미지를 보려면 클릭).Figure 1: The Label's CssClass Property Results in a Large, Red Font (Click to view full-size image)

그런 다음 페이지에 DropDownList을 추가 하 고, 해당 ID 속성을 UserList로 설정 하 고, AutoPostBack 속성을 True로 설정 합니다.Next, add a DropDownList to the page, set its ID property to UserList, and set its AutoPostBack property to True. 이 DropDownList을 사용 하 여 시스템의 모든 사용자를 나열 합니다.We will use this DropDownList to list all of the users in the system. 이 DropDownList은 MembershipUser 개체의 컬렉션에 바인딩됩니다.This DropDownList will be bound to a collection of MembershipUser objects. DropDownList에서 MembershipUser 개체의 UserName 속성을 표시 하 고이를 목록 항목의 값으로 사용 하려고 하므로 DropDownList의 DataTextFieldDataValueField 속성을 "UserName"으로 설정 합니다.Because we want the DropDownList to display the UserName property of the MembershipUser object (and use it as the value of the list items), set the DropDownList's DataTextField and DataValueField properties to "UserName".

DropDownList 아래에 UsersRoleList이라는 리피터를 추가 합니다.Underneath the DropDownList, add a Repeater named UsersRoleList. 이 리피터는 시스템의 모든 역할을 일련의 확인란으로 나열 합니다.This Repeater will list all of the roles in the system as a series of checkboxes. 다음 선언 태그를 사용 하 여 Repeater의 ItemTemplate를 정의 합니다.Define the Repeater's ItemTemplate using the following declarative markup:

<asp:Repeater ID="UsersRoleList" runat="server"> 
     <ItemTemplate> 
          <asp:CheckBox runat="server" ID="RoleCheckBox" AutoPostBack="true" 

               Text='<%# Container.DataItem %>' /> 
          <br /> 
     </ItemTemplate> 
</asp:Repeater>

ItemTemplate 태그는 RoleCheckBox라는 단일 CheckBox 웹 컨트롤을 포함 합니다.The ItemTemplate markup includes a single CheckBox Web control named RoleCheckBox. CheckBox의 AutoPostBack 속성은 True로 설정 되 고 Text 속성은 Container.DataItem에 바인딩됩니다.The CheckBox's AutoPostBack property is set to True and the Text property is bound to Container.DataItem. 데이터 바인딩 구문이 Container.DataItem 된 이유는 역할 프레임 워크가 역할 이름 목록을 문자열 배열로 반환 하 고,이 문자열 배열이 Repeater에 바인딩할 수 있기 때문입니다.The reason the databinding syntax is simply Container.DataItem is because the Roles framework returns the list of role names as a string array, and it is this string array that we will be binding to the Repeater. 이 구문을 사용 하 여 데이터 웹 컨트롤에 바인딩된 배열의 내용을 표시 하는 이유에 대 한 자세한 설명은이 자습서의 범위를 벗어나는 것입니다.A thorough description of why this syntax is used to display the contents of an array bound to a data Web control is beyond the scope of this tutorial. 이러한 문제에 대 한 자세한 내용은 스칼라 배열을 데이터 웹 컨트롤에 바인딩을 참조 하세요.For more information on this matter, refer to Binding a Scalar Array to a Data Web Control.

이 시점에서 "사용자의" 인터페이스의 선언 태그는 다음과 유사 합니다.At this point your "by user" interface's declarative markup should look similar to the following:

<h3>Manage Roles By User</h3> 

<p> 
     <b>Select a User:</b> 
     <asp:DropDownList ID="UserList" runat="server" AutoPostBack="True" 
          DataTextField="UserName" DataValueField="UserName"> 

     </asp:DropDownList> 
</p> 
<p> 
     <asp:Repeater ID="UsersRoleList" runat="server"> 
          <ItemTemplate> 
               <asp:CheckBox runat="server" ID="RoleCheckBox" AutoPostBack="true" 

                    Text='<%# Container.DataItem %>' /> 
               <br /> 
          </ItemTemplate> 
     </asp:Repeater> 
</p>

이제 사용자 계정 집합을 DropDownList에 바인딩하는 코드를 작성 하 고 역할 집합을 리피터에 게 바인딩할 수 있습니다.We are now ready to write the code to bind the set of user accounts to the DropDownList and the set of roles to the Repeater. 페이지의 코드 숨김이 클래스에서 다음 코드를 사용 하 여 BindUsersToUserList 라는 메서드와 BindRolesList라는 다른를 추가 합니다.In the page's code-behind class, add a method named BindUsersToUserList and another named BindRolesList, using the following code:

private void BindUsersToUserList() 
{ 
     // Get all of the user accounts 
     MembershipUserCollection users = Membership.GetAllUsers(); 
     UserList.DataSource = users; 
     UserList.DataBind(); 
}
 
private void BindRolesToList() 
{ 
     // Get all of the roles 
     string[] roles = Roles.GetAllRoles(); 
     UsersRoleList.DataSource = roles; 
     UsersRoleList.DataBind(); 
}

BindUsersToUserList 메서드는 Membership.GetAllUsers 메서드를 통해 시스템의 모든 사용자 계정을 검색 합니다.The BindUsersToUserList method retrieves all of the user accounts in the system via the Membership.GetAllUsers method. 그러면 MembershipUser 인스턴스의컬렉션인 MembershipUserCollection 개체가반환 됩니다.This returns a MembershipUserCollection object, which is a collection of MembershipUser instances. 그런 다음이 컬렉션은 UserList DropDownList에 바인딩됩니다.This collection is then bound to the UserList DropDownList. 컬렉션을 구성을 MembershipUser 인스턴스에는 UserName, Email, CreationDate, IsOnline등의 다양 한 속성이 포함 되어 있습니다.The MembershipUser instances that makeup the collection contain a variety of properties, like UserName, Email, CreationDate, and IsOnline. DropDownList에 UserName 속성 값을 표시 하도록 지시 하려면 UserList DropDownList의 DataTextFieldDataValueField 속성이 "UserName"으로 설정 되어 있는지 확인 합니다.In order to instruct the DropDownList to display the value of the UserName property, ensure that the UserList DropDownList's DataTextField and DataValueField properties have been set to "UserName".

Note

Membership.GetAllUsers 메서드에는 두 개의 오버 로드가 있습니다. 하나는 입력 매개 변수를 허용 하지 않고 모든 사용자를 반환 하 고, 다른 하나는 페이지 인덱스와 페이지 크기에 대 한 정수 값을 사용 하 고 사용자의 지정 된 하위 집합만 반환 합니다.The Membership.GetAllUsers method has two overloads: one that accepts no input parameters and returns all of the users, and one that takes in integer values for the page index and page size, and returns only the specified subset of the users. 페이징할 수 있는 사용자 인터페이스 요소에 많은 양의 사용자 계정이 표시 되는 경우 두 번째 오버 로드를 사용 하 여 모든 것이 아니라 사용자 계정의 정확한 하위 집합만 반환 하기 때문에 사용자를 보다 효율적으로 페이징할 수 있습니다.When there are large amounts of user accounts being displayed in a pageable user interface element, the second overload can be used to more efficiently page through the users since it returns just the precise subset of user accounts rather than all of them.

BindRolesToList 메서드는 시스템의 역할을 포함 하는 문자열 배열을 반환 하는 Roles 클래스의 GetAllRoles 메서드를 호출 하 여 시작 합니다.The BindRolesToList method starts by calling the Roles class's GetAllRoles method, which returns a string array containing the roles in the system. 그런 다음이 문자열 배열을 Repeater에 바인딩합니다.This string array is then bound to the Repeater.

마지막으로 페이지가 처음 로드 될 때 이러한 두 메서드를 호출 해야 합니다.Finally, we need to call these two methods when the page is first loaded. 다음 코드를 Page_Load 이벤트 처리기에 추가합니다.Add the following code to the Page_Load event handler:

protected void Page_Load(object sender, EventArgs e) 
{ 
     if (!Page.IsPostBack) 
     { 
          // Bind the users and roles 
          BindUsersToUserList(); 
          BindRolesToList(); 
     } 
}

이 코드를 적용 하면 잠시 브라우저를 통해 페이지를 방문 하세요. 화면은 그림 2와 유사 하 게 표시 됩니다.With this code in place, take a moment to visit the page through a browser; your screen should look similar to Figure 2. 모든 사용자 계정이 드롭다운 목록에 채워지며, 그 아래에서 각 역할이 확인란으로 나타납니다.All of the user accounts are populated in the drop-down list and, underneath that, each role appears as a checkbox. DropDownList 및 확인란의 AutoPostBack 속성을 True로 설정 하 여 선택한 사용자를 변경 하거나 역할을 선택 하거나 선택 취소 하면 포스트백이 발생 합니다.Because we set the AutoPostBack properties of the DropDownList and CheckBoxes to True, changing the selected user or checking or unchecking a role causes a postback. 그러나 이러한 작업을 처리 하는 코드를 아직 작성 하지 않았으므로 아무 작업도 수행 되지 않습니다.No action is performed, however, because we have yet to write code to handle these actions. 다음 두 섹션에서 이러한 작업을 다룰 것입니다.We'll tackle these tasks in the next two sections.

페이지 사용자 및 역할 표시The Page Displays the Users and Roles

그림 2: 사용자 및 역할을 표시 하는 페이지 (전체 크기 이미지를 보려면 클릭)Figure 2: The Page Displays the Users and Roles (Click to view full-size image)

선택한 사용자가 속한 역할을 확인 하는 중Checking the Roles the Selected User Belongs To

페이지가 처음 로드 될 때 또는 방문자가 드롭다운 목록에서 새 사용자를 선택할 때마다 선택한 사용자가 해당 역할에 속하는 경우에만 지정 된 역할 확인란이 선택 되도록 UsersRoleList의 확인란을 업데이트 해야 합니다.When the page is first loaded, or whenever the visitor selects a new user from the drop-down list, we need to update the UsersRoleList's checkboxes so that a given role checkbox is checked only if the selected user belongs to that role. 이 작업을 수행 하려면 다음 코드를 사용 하 여 CheckRolesForSelectedUser 라는 메서드를 만듭니다.To accomplish this, create a method named CheckRolesForSelectedUser with the following code:

private void CheckRolesForSelectedUser() 
{ 
     // Determine what roles the selected user belongs to 
     string selectedUserName = UserList.SelectedValue; 
     string[] selectedUsersRoles = Roles.GetRolesForUser(selectedUserName); 

     // Loop through the Repeater's Items and check or uncheck the checkbox as needed 

     foreach (RepeaterItem ri in UsersRoleList.Items) 
     { 
          // Programmatically reference the CheckBox 
          CheckBox RoleCheckBox = ri.FindControl("RoleCheckBox") as CheckBox; 
          // See if RoleCheckBox.Text is in selectedUsersRoles 
          if (selectedUsersRoles.Contains<string>(RoleCheckBox.Text)) 
               RoleCheckBox.Checked = true; 
          else 
               RoleCheckBox.Checked = false; 
     } 
}

위의 코드는 선택한 사용자의 사용자를 확인 하 여 시작 합니다.The above code starts by determining who the selected user is. 그런 다음 Roles 클래스의 GetRolesForUser(userName) 메서드 를 사용 하 여 지정 된 사용자의 역할 집합을 문자열 배열로 반환 합니다.It then uses the Roles class's GetRolesForUser(userName) method to return the specified user's set of roles as a string array. 다음으로는 Repeater의 항목이 열거 되 고 각 항목의 RoleCheckBox CheckBox는 프로그래밍 방식으로 참조 됩니다.Next, the Repeater's items are enumerated and each item's RoleCheckBox CheckBox is programmatically referenced. 이 확인란은 해당 역할이 해당 하는 역할이 selectedUsersRoles 문자열 배열에 포함 되어 있는 경우에만 확인 됩니다.The CheckBox is checked only if the role it corresponds to is contained within the selectedUsersRoles string array.

Note

ASP.NET 버전 2.0을 사용 하는 경우에는 selectedUserRoles.Contains<string>(...) 구문이 컴파일되지 않습니다.The selectedUserRoles.Contains<string>(...) syntax will not compile if you are using ASP.NET version 2.0. Contains<string> 메서드는 ASP.NET 3.5에 새로 포함 된 LINQ 라이브러리의 일부입니다.The Contains<string> method is part of the LINQ library, which is new to ASP.NET 3.5. 여전히 ASP.NET 버전 2.0을 사용 하는 경우 Array.IndexOf<string> 메서드 를 대신 사용 합니다.If you are still using ASP.NET version 2.0, use the Array.IndexOf<string> method instead.

CheckRolesForSelectedUser 메서드는 페이지가 처음 로드 될 때와 UserList DropDownList의 선택 된 인덱스가 변경 될 때마다 호출 해야 합니다.The CheckRolesForSelectedUser method needs to be called in two cases: when the page is first loaded and whenever the UserList DropDownList's selected index is changed. 따라서 BindUsersToUserListBindRolesToList를 호출한 후 Page_Load 이벤트 처리기에서이 메서드를 호출 합니다.Therefore, call this method from the Page_Load event handler (after the calls to BindUsersToUserList and BindRolesToList). 또한 DropDownList의 SelectedIndexChanged 이벤트에 대 한 이벤트 처리기를 만들고 여기에서이 메서드를 호출 합니다.Also, create an event handler for the DropDownList's SelectedIndexChanged event and call this method from there.

protected void Page_Load(object sender, EventArgs e) 
{ 
     if (!Page.IsPostBack) 
     { 

          // Bind the users and roles 
          BindUsersToUserList(); 
          BindRolesToList(); 
          // Check the selected user's roles 
          CheckRolesForSelectedUser(); 
     } 
} 

... 

protected void UserList_SelectedIndexChanged(object sender, EventArgs e) 
{ 
     CheckRolesForSelectedUser(); 
}

이 코드가 준비 되 면 브라우저를 통해 페이지를 테스트할 수 있습니다.With this code in place, you can test the page through the browser. 그러나 UsersAndRoles.aspx 페이지에는 현재 역할에 사용자를 할당할 수 있는 권한이 없으므로 사용자에 게 역할이 없습니다.However, since the UsersAndRoles.aspx page currently lacks the ability to assign users to roles, no users have roles. 잠시 후에 역할에 사용자를 할당 하는 인터페이스를 만듭니다. 따라서이 코드가 작동 하는 단어를 사용 하 여 나중에 수행 하는지 확인 하거나, 지금이 기능을 테스트 하기 위해 레코드를 aspnet_UsersInRoles 테이블에 삽입 하 여 사용자를 역할에 수동으로 추가할 수 있습니다.We will create the interface for assigning users to roles in a moment, so you can either take my word that this code works and verify that it does so later, or you can manually add users to roles by inserting records into the aspnet_UsersInRoles table in order to test this functionality now.

역할에서 사용자 할당 및 제거Assigning and Removing Users from Roles

방문자가 UsersRoleList Repeater의 확인란을 선택 하거나 선택 취소 하는 경우 해당 역할에서 선택한 사용자를 추가 하거나 제거 해야 합니다.When the visitor checks or unchecks a CheckBox in the UsersRoleList Repeater we need to add or remove the selected user from the corresponding role. CheckBox의 AutoPostBack 속성은 현재 True로 설정 되어 있으므로 Repeater의 확인란을 선택 하거나 선택 하지 않을 때마다 포스트백이 발생 합니다.The CheckBox's AutoPostBack property is currently set to True, which causes a postback anytime a CheckBox in the Repeater is checked or unchecked. 간단히 말해서 CheckBox의 CheckChanged 이벤트에 대 한 이벤트 처리기를 만들어야 합니다.In short, we need to create an event handler for the CheckBox's CheckChanged event. 이 확인란은 Repeater 컨트롤 이므로 이벤트 처리기를 수동으로 추가 해야 합니다.Since the CheckBox is in a Repeater control, we need to manually add the event handler plumbing. 다음과 같이 이벤트 처리기를 protected 메서드로 코드 숨김으로 추가 하 여 시작 합니다.Start by adding the event handler to the code-behind class as a protected method, like so:

protected void RoleCheckBox_CheckChanged(object sender, EventArgs e) 
{ 

}

잠시 후이 이벤트 처리기에 대 한 코드를 작성 하기 위해를 반환 합니다.We will return to write the code for this event handler in a moment. 하지만 먼저 이벤트 처리를 완료 해 보겠습니다.But first let's complete the event handling plumbing. Repeater의 ItemTemplate에 있는 확인란에서 OnCheckedChanged="RoleCheckBox_CheckChanged"를 추가 합니다.From the CheckBox within the Repeater's ItemTemplate, add OnCheckedChanged="RoleCheckBox_CheckChanged". 이 구문은 RoleCheckBoxCheckedChanged 이벤트에 RoleCheckBox_CheckChanged 이벤트 처리기를 배선 합니다.This syntax wires the RoleCheckBox_CheckChanged event handler to the RoleCheckBox's CheckedChanged event.

<asp:CheckBox runat="server" ID="RoleCheckBox" 
     AutoPostBack="true" 
     Text='<%# Container.DataItem %>' 
     OnCheckedChanged="RoleCheckBox_CheckChanged" />

최종 작업은 RoleCheckBox_CheckChanged 이벤트 처리기를 완료 하는 것입니다.Our final task is to complete the RoleCheckBox_CheckChanged event handler. 이벤트를 발생 시킨 CheckBox 컨트롤을 참조 하 여 시작 해야 합니다 .이 확인란 인스턴스는 TextChecked 속성을 통해 확인 되거나 선택 취소 된 역할을 알려 줍니다.We need to start by referencing the CheckBox control that raised the event because this CheckBox instance tells us what role was checked or unchecked via its Text and Checked properties. 선택한 사용자의 사용자 이름과 함께이 정보를 사용 하 여 Roles 클래스의 AddUserToRole 또는 RemoveUserFromRole 메서드를 통해 역할에서 사용자를 추가 하거나 제거 합니다.Using this information along with the UserName of the selected user, we add or remove the user from the role via the Roles class's AddUserToRole or RemoveUserFromRole method.

protected void RoleCheckBox_CheckChanged(object sender, EventArgs e) 
{ 
     // Reference the CheckBox that raised this event 
     CheckBox RoleCheckBox = sender as CheckBox; 

     // Get the currently selected user and role 
     string selectedUserName = UserList.SelectedValue; 

     string roleName = RoleCheckBox.Text; 

     // Determine if we need to add or remove the user from this role 
     if (RoleCheckBox.Checked) 
     { 
          // Add the user to the role 
          Roles.AddUserToRole(selectedUserName, roleName); 
          // Display a status message 
          ActionStatus.Text = string.Format("User {0} was added to role {1}.", selectedUserName, roleName); 
     } 
     else 
     { 
          // Remove the user from the role 
          Roles.RemoveUserFromRole(selectedUserName, roleName); 
          // Display a status message 
          ActionStatus.Text = string.Format("User {0} was removed from role {1}.", selectedUserName, roleName); 

     } 
}

위의 코드는 sender 입력 매개 변수를 통해 사용할 수 있는 이벤트를 발생 시킨 CheckBox를 프로그래밍 방식으로 참조 하 여 시작 합니다.The above code starts by programmatically referencing the CheckBox that raised the event, which is available via the sender input parameter. 확인란을 선택 하면 선택한 사용자가 지정 된 역할에 추가 되 고, 그렇지 않으면 역할에서 제거 됩니다.If the CheckBox is checked, the selected user is added to the specified role, otherwise they are removed from the role. 두 경우 모두 ActionStatus 레이블은 단지 수행한 동작을 요약 하는 메시지를 표시 합니다.In either case, the ActionStatus Label displays a message summarizing the action just performed.

잠시 시간을 사용 하 여 브라우저를 통해이 페이지를 테스트 합니다.Take a moment to test out this page through a browser. 사용자 Tito를 선택 하 고 관리자 및 감독자 역할 모두에 Tito를 추가 합니다.Select user Tito and then add Tito to both the Administrators and Supervisors roles.

Tito가 Administrators 및 감독자 역할에 추가 되었습니다.Tito Has Been Added to the Administrators and Supervisors Roles

그림 3: 관리자 및 감독자 역할에 Tito를 추가 했습니다 (전체 크기 이미지를 보려면 클릭).Figure 3: Tito Has Been Added to the Administrators and Supervisors Roles (Click to view full-size image)

다음으로, 드롭다운 목록에서 사용자 Bruce를 선택 합니다.Next, select user Bruce from the drop-down list. 포스트백이 발생 하 고 CheckRolesForSelectedUser를 통해 Repeater의 확인란이 업데이트 됩니다.There is a postback and the Repeater's CheckBoxes are updated via the CheckRolesForSelectedUser. Bruce는 아직 어떠한 역할에도 속하지 않으므로 두 확인란을 선택 취소 합니다.Since Bruce does not yet belong to any roles, the two checkboxes are unchecked. 다음으로, 감독자 역할에 Bruce를 추가 합니다.Next, add Bruce to the Supervisors role.

Bruce가 감독자 역할에 추가 되었습니다.Bruce Has Been Added to the Supervisors Role

그림 4: Bruce가 감독자 역할에 추가 됨 (전체 크기 이미지를 보려면 클릭)Figure 4: Bruce Has Been Added to the Supervisors Role (Click to view full-size image)

CheckRolesForSelectedUser 메서드의 기능을 자세히 확인 하려면 Tito 또는 Bruce 이외의 사용자를 선택 합니다.To further verify the functionality of the CheckRolesForSelectedUser method, select a user other than Tito or Bruce. 확인란을 선택 취소 하 여 어떤 역할에도 속하지 않는 것을 확인 합니다.Note how the checkboxes are automatically unchecked, denoting that they do not belong to any roles. Tito로 돌아갑니다.Return to Tito. 관리자와 감독자 확인란을 모두 선택 해야 합니다.Both the Administrators and Supervisors checkboxes should be checked.

2 단계: "역할 별" 사용자 인터페이스 빌드Step 2: Building the "By Roles" User Interface

이 시점에서 "사용자" 인터페이스를 완료 하 고 "주요 당면" 인터페이스를 시작할 준비가 되었습니다.At this point we have completed the "by users" interface and are ready to start tackling the "by roles" interface. "역할별" 인터페이스는 드롭다운 목록에서 역할을 선택 하 라는 메시지를 표시 한 다음 GridView에서 해당 역할에 속하는 사용자 집합을 표시 합니다.The "by roles" interface prompts the user to select a role from a drop-down list and then displays the set of users that belong to that role in a GridView.

UsersAndRoles.aspx 페이지에 다른 DropDownList 컨트롤을 추가 합니다.Add another DropDownList control to the UsersAndRoles.aspx page. Repeater 컨트롤 아래에이를 놓고 RoleList이름을로 지정 하 고 AutoPostBack 속성을 True로 설정 합니다.Place this one beneath the Repeater control, name it RoleList, and set its AutoPostBack property to True. 그 아래에서 GridView를 추가 하 고 이름을 RolesUserList로 합니다.Underneath that, add a GridView and name it RolesUserList. 이 GridView에는 선택한 역할에 속하는 사용자가 나열 됩니다.This GridView will list the users that belong to the selected role. GridView의 AutoGenerateColumns 속성을 False로 설정 하 고, 표의 Columns 컬렉션에 Templatefield로 변환를 추가 하 고, HeaderText 속성을 "사용자"로 설정 합니다.Set the GridView's AutoGenerateColumns property to False, add a TemplateField to the grid's Columns collection, and set its HeaderText property to "Users". Templatefield로 변환의 ItemTemplate를 정의 하 여 UserNameLabel이라는 레이블의 Text 속성에 Container.DataItem 데이터 바인딩 식의 값을 표시 합니다.Define the TemplateField's ItemTemplate so that it displays the value of the databinding expression Container.DataItem in the Text property of a Label named UserNameLabel.

GridView를 추가 하 고 구성한 후에는 "역할별" 인터페이스의 선언적 태그가 다음과 같이 표시 됩니다.After adding and configuring the GridView, your "by role" interface's declarative markup should look similar to the following:

<h3>Manage Users By Role</h3> 
<p> 
     <b>Select a Role:</b> 

     <asp:DropDownList ID="RoleList" runat="server" AutoPostBack="true"></asp:DropDownList> 
</p> 
<p>      <asp:GridView ID="RolesUserList" runat="server" AutoGenerateColumns="false" 

          EmptyDataText="No users belong to this role."> 
          <Columns> 
               <asp:TemplateField HeaderText="Users"> 
                    <ItemTemplate> 
                         <asp:Label runat="server" id="UserNameLabel" 
                              Text='<%# Container.DataItem %>'></asp:Label> 

                    </ItemTemplate> 
               </asp:TemplateField> 
          </Columns> 
     </asp:GridView> </p>

RoleList DropDownList을 시스템의 역할 집합과 채워야 합니다.We need to populate the RoleList DropDownList with the set of roles in the system. 이를 수행 하려면가 Roles.GetAllRoles 메서드에서 반환 하는 문자열 배열을 RolesList DropDownList (및 UsersRoleList Repeater)에 바인딩되도록 BindRolesToList 메서드를 업데이트 합니다.To accomplish this, update the BindRolesToList method so that is binds the string array returned by the Roles.GetAllRoles method to the RolesList DropDownList (as well as the UsersRoleList Repeater).

private void BindRolesToList() 
{ 
     // Get all of the roles 

     string[] roles = Roles.GetAllRoles(); 
     UsersRoleList.DataSource = roles; 
     UsersRoleList.DataBind(); 

     RoleList.DataSource = roles; 
     RoleList.DataBind(); 
}

RoleList DropDownList 컨트롤에 역할 집합을 바인딩하기 위해 BindRolesToList 메서드의 마지막 두 줄이 추가 되었습니다.The last two lines in the BindRolesToList method have been added to bind the set of roles to the RoleList DropDownList control. 그림 5는 브라우저를 통해 볼 때 최종 결과를 보여 줍니다 .이는 시스템 역할로 채워진 드롭다운 목록입니다.Figure 5 shows the end result when viewed through a browser – a drop-down list populated with the system's roles.

역할이 RoleList DropDownList에 표시 The Roles are Displayed in the RoleList DropDownList

그림 5: RoleList DropDownList에 표시 되는 역할 (전체 크기 이미지를 보려면 클릭)Figure 5: The Roles are Displayed in the RoleList DropDownList (Click to view full-size image)

선택한 역할에 속한 사용자 표시Displaying the Users That Belong To the Selected Role

페이지를 처음 로드 하거나 RoleList DropDownList에서 새 역할을 선택 하는 경우 GridView에서 해당 역할에 속하는 사용자 목록을 표시 해야 합니다.When the page is first loaded, or when a new role is selected from the RoleList DropDownList, we need to display the list of users that belong to that role in the GridView. 다음 코드를 사용 하 여 DisplayUsersBelongingToRole 라는 메서드를 만듭니다.Create a method named DisplayUsersBelongingToRole using the following code:

private void DisplayUsersBelongingToRole() 
{ 
     // Get the selected role 
     string selectedRoleName = RoleList.SelectedValue; 

     // Get the list of usernames that belong to the role 
     string[] usersBelongingToRole = Roles.GetUsersInRole(selectedRoleName); 

     // Bind the list of users to the GridView 
     RolesUserList.DataSource = usersBelongingToRole; 
     RolesUserList.DataBind(); 
}

이 메서드는 RoleList DropDownList에서 선택한 역할을 가져와 시작 합니다.This method starts by getting the selected role from the RoleList DropDownList. 그런 다음 Roles.GetUsersInRole(roleName) 메서드 를 사용 하 여 해당 역할에 속한 사용자 이름의 문자열 배열을 검색 합니다.It then uses the Roles.GetUsersInRole(roleName) method to retrieve a string array of the UserNames of the users that belong to that role. 그런 다음이 배열은 RolesUserList GridView에 바인딩됩니다.This array is then bound to the RolesUserList GridView.

이 메서드는 페이지가 처음 로드 될 때와 RoleList DropDownList에서 선택 된 역할이 변경 될 때 두 가지 상황에서 호출 해야 합니다.This method needs to be called in two circumstances: when the page is initially loaded and when the selected role in the RoleList DropDownList changes. 따라서 CheckRolesForSelectedUser를 호출한 후이 메서드가 호출 되도록 Page_Load 이벤트 처리기를 업데이트 합니다.Therefore, update the Page_Load event handler so that this method is invoked after the call to CheckRolesForSelectedUser. 그런 다음 RoleListSelectedIndexChanged 이벤트에 대 한 이벤트 처리기를 만들고 여기에서이 메서드를 호출 합니다.Next, create an event handler for the RoleList's SelectedIndexChanged event, and call this method from there, too.

protected void Page_Load(object sender, EventArgs e) 
{ 
     if (!Page.IsPostBack) 
     { 
          // Bind the users and roles 
          BindUsersToUserList(); 
          BindRolesToList(); 

          // Check the selected user's roles 
          CheckRolesForSelectedUser(); 

          // Display those users belonging to the currently selected role 
          DisplayUsersBelongingToRole(); 
     } 
} 

... 

protected void RoleList_SelectedIndexChanged(object sender, EventArgs e) 
{ 
     DisplayUsersBelongingToRole(); 
}

이 코드를 사용 하면 RolesUserList GridView에서 선택한 역할에 속하는 사용자를 표시 해야 합니다.With this code in place, the RolesUserList GridView should display those users that belong to the selected role. 그림 6에서 볼 수 있듯이, 감독자 역할은 Bruce와 Tito의 두 멤버로 구성 됩니다.As Figure 6 shows, the Supervisors role consists of two members: Bruce and Tito.

GridView 선택한 역할에 속하는 사용자를 나열 합니다.The GridView Lists Those Users That Belong to the Selected Role

그림 6: GridView에 선택한 역할에 속하는 사용자 나열 (전체 크기 이미지를 보려면 클릭)Figure 6: The GridView Lists Those Users That Belong to the Selected Role (Click to view full-size image)

선택한 역할에서 사용자 제거Removing Users from the Selected Role

"제거" 단추 열을 포함 하도록 RolesUserList GridView를 늘려 보겠습니다.Let's augment the RolesUserList GridView so that it includes a column of "Remove" buttons. 특정 사용자에 대 한 "제거" 단추를 클릭 하면 해당 역할에서 해당 사용자가 제거 됩니다.Clicking the "Remove" button for a particular user will remove them from that role.

먼저 GridView에 삭제 단추 필드를 추가 합니다.Start by adding a Delete button field to the GridView. 이 필드가 가장 왼쪽에 표시 되도록 하 고 해당 DeleteText 속성을 "Delete" (기본값)에서 "Remove"로 변경 합니다.Make this field appear as the left most filed and change its DeleteText property from "Delete" (the default) to "Remove".

추가 합니다.Add the

그림 7: "제거" 단추를 GridView에 추가 (전체 크기 이미지를 보려면 클릭)Figure 7: Add the "Remove" Button to the GridView (Click to view full-size image)

"제거" 단추를 클릭 하면 ensues이 다시 게시 되 고 GridView의 RowDeleting 이벤트가 발생 합니다.When the "Remove" button is clicked a postback ensues and the GridView's RowDeleting event is raised. 이 이벤트에 대 한 이벤트 처리기를 만들고 선택한 역할에서 사용자를 제거 하는 코드를 작성 해야 합니다.We need to create an event handler for this event and write code that removes the user from the selected role. 이벤트 처리기를 만들고 다음 코드를 추가 합니다.Create the event handler and then add the following code:

protected void RolesUserList_RowDeleting(object sender, GridViewDeleteEventArgs e) 
{ 
     // Get the selected role 
     string selectedRoleName = RoleList.SelectedValue; 

     // Reference the UserNameLabel 
     Label UserNameLabel = RolesUserList.Rows[e.RowIndex].FindControl("UserNameLabel") as Label; 

     // Remove the user from the role 
     Roles.RemoveUserFromRole(UserNameLabel.Text, selectedRoleName); 

     // Refresh the GridView 
     DisplayUsersBelongingToRole(); 

     // Display a status message 
     ActionStatus.Text = string.Format("User {0} was removed from role {1}.", UserNameLabel.Text, selectedRoleName); 
}

선택한 역할 이름을 확인 하 여 코드를 시작 합니다.The code starts by determining the selected role name. 그런 다음 제거할 사용자의 사용자 이름을 결정 하기 위해 "제거" 단추를 클릭 한 행의 UserNameLabel 컨트롤을 프로그래밍 방식으로 참조 합니다.It then programmatically references the UserNameLabel control from the row whose "Remove" button was clicked in order to determine the UserName of the user to remove. 그런 다음 Roles.RemoveUserFromRole 메서드에 대 한 호출을 통해 사용자를 역할에서 제거 합니다.The user is then removed from the role via a call to the Roles.RemoveUserFromRole method. 그러면 RolesUserList GridView가 새로 고쳐지고 ActionStatus 레이블 컨트롤을 통해 메시지가 표시 됩니다.The RolesUserList GridView is then refreshed and a message is displayed via the ActionStatus Label control.

Note

"제거" 단추는 역할에서 사용자를 제거 하기 전에 사용자가 어떤 종류의 확인도 필요 하지 않습니다.The "Remove" button does not require any sort of confirmation from the user before removing the user from the role. 사용자를 초대 하 여 일정 수준의 사용자 확인을 추가 합니다.I invite you to add some level of user confirmation. 동작을 확인 하는 가장 쉬운 방법 중 하나는 클라이언트 쪽 확인 대화 상자를 통하는 것입니다.One of the easiest ways to confirm an action is through a client-side confirm dialog box. 이 기술에 대 한 자세한 내용은 삭제할 때 클라이언트 쪽 확인 추가를 참조 하세요.For more information on this technique, see Adding Client-Side Confirmation When Deleting.

그림 8에서는 사용자 Tito가 감독자 그룹에서 제거 된 후의 페이지를 보여 줍니다.Figure 8 shows the page after user Tito has been removed from the Supervisors group.

하는 경우 Tito는 더 이상 감독자가 아닙니다.Alas, Tito is No Longer a Supervisor

그림 8: Tito는 더 이상 감독자가 아닙니다 (전체 크기 이미지를 보려면 클릭).Figure 8: Alas, Tito is No Longer a Supervisor (Click to view full-size image)

선택한 역할에 새 사용자 추가Adding New Users to the Selected Role

선택한 역할에서 사용자를 제거 하는 것과 함께이 페이지의 방문자는 선택한 역할에 사용자를 추가할 수도 있습니다.Along with removing users from the selected role, the visitor to this page should also be able to add a user to the selected role. 선택한 역할에 사용자를 추가 하는 가장 좋은 인터페이스는 필요한 사용자 계정 수에 따라 달라 집니다.The best interface for adding a user to the selected role depends on the number of user accounts you expect to have. 웹 사이트가 수십 개의 사용자 계정에만 있는 경우 여기에서 DropDownList를 사용할 수 있습니다.If your website will house just a few dozen user accounts or less, you could use a DropDownList here. 수천 개의 사용자 계정이 있을 수 있는 경우 방문자가 계정을 통해 페이지를 이동 하거나 특정 계정을 검색 하거나 다른 방식으로 사용자 계정을 필터링 할 수 있도록 하는 사용자 인터페이스를 포함 하는 것이 좋습니다.If there might be thousands of user accounts, you would want to include a user interface that permits the visitor to page through the accounts, search for a particular account, or filter the user accounts in some other fashion.

이 페이지에서는 시스템의 사용자 계정 수에 관계 없이 작동 하는 매우 간단한 인터페이스를 사용 하겠습니다.For this page let's use a very simple interface that works regardless of the number of user accounts in the system. 즉, 텍스트 상자를 사용 하 여 방문자에 게 선택한 역할에 추가 하려는 사용자의 사용자 이름을 입력 하 라는 메시지를 표시 합니다.Namely, we will use a TextBox, prompting the visitor to type in the username of the user she wants to add to the selected role. 해당 이름을 가진 사용자가 없거나 사용자가 이미 역할의 구성원 인 경우 ActionStatus 레이블에 메시지를 표시 합니다.If no user with that name exists, or if the user is already a member of the role, we'll display a message in ActionStatus Label. 그러나 사용자가 존재 하 고 역할의 멤버가 아닌 경우 해당 사용자를 역할에 추가 하 고 그리드를 새로 고칩니다.But if the user exists and is not a member of the role, we'll add them to the role and refresh the grid.

텍스트 상자와 단추를 GridView 아래에 추가 합니다.Add a TextBox and Button beneath the GridView. 텍스트 상자의 IDUserNameToAddToRole 설정 하 고 단추의 IDText 속성을 각각 AddUserToRoleButton 및 "역할에 사용자 추가"로 설정 합니다.Set the TextBox's ID to UserNameToAddToRole and set the Button's ID and Text properties to AddUserToRoleButton and "Add User to Role", respectively.

<p> 
     <b>UserName:</b> 
     <asp:TextBox ID="UserNameToAddToRole" runat="server"></asp:TextBox> 
     <br /> 
     <asp:Button ID="AddUserToRoleButton" runat="server" Text="Add User to Role" /> 

</p>

다음으로 AddUserToRoleButton에 대 한 Click 이벤트 처리기를 만들고 다음 코드를 추가 합니다.Next, create a Click event handler for the AddUserToRoleButton and add the following code:

protected void AddUserToRoleButton_Click(object sender, EventArgs e) 
{ 
     // Get the selected role and username 

     string selectedRoleName = RoleList.SelectedValue; 
     string userNameToAddToRole = UserNameToAddToRole.Text; 

     // Make sure that a value was entered 
     if (userNameToAddToRole.Trim().Length == 0) 
     { 
          ActionStatus.Text = "You must enter a username in the textbox."; 
          return; 
     } 

     // Make sure that the user exists in the system 
     MembershipUser userInfo = Membership.GetUser(userNameToAddToRole); 
     if (userInfo == null) 
     { 
          ActionStatus.Text = string.Format("The user {0} does not exist in the system.", userNameToAddToRole); 

          return; 
     } 

     // Make sure that the user doesn't already belong to this role 
     if (Roles.IsUserInRole(userNameToAddToRole, selectedRoleName)) 
     { 
          ActionStatus.Text = string.Format("User {0} already is a member of role {1}.", userNameToAddToRole, selectedRoleName); 
          return; 
     } 

     // If we reach here, we need to add the user to the role 
     Roles.AddUserToRole(userNameToAddToRole, selectedRoleName); 

     // Clear out the TextBox 
     UserNameToAddToRole.Text = string.Empty; 

     // Refresh the GridView 
     DisplayUsersBelongingToRole(); 

     // Display a status message 

     ActionStatus.Text = string.Format("User {0} was added to role {1}.", userNameToAddToRole, selectedRoleName); }

Click 이벤트 처리기에서 대부분의 코드는 다양 한 유효성 검사를 수행 합니다.The majority of the code in the Click event handler performs various validation checks. 이를 통해 방문자는 UserNameToAddToRole 텍스트 상자에 사용자 이름을 제공 하 고, 사용자가 시스템에 존재 하며, 선택 된 역할에 속해 있지 않은지 확인할 수 있습니다.It ensures that the visitor supplied a username in the UserNameToAddToRole TextBox, that the user exists in the system, and that they don't already belong to the selected role. 이러한 검사 중 하나라도 실패 하면 ActionStatus에 적절 한 메시지가 표시 되 고 이벤트 처리기가 종료 됩니다.If any of these checks fails, an appropriate message is displayed in ActionStatus and the event handler is exited. 모든 검사가 통과 되 면 사용자는 Roles.AddUserToRole 메서드를 통해 역할에 추가 됩니다.If all of the checks pass, the user is added to the role via the Roles.AddUserToRole method. 그러면 텍스트 상자의 Text 속성이 지워지고 GridView가 새로 고쳐지고 ActionStatus 레이블에 지정 된 사용자가 선택한 역할에 성공적으로 추가 되었음을 나타내는 메시지가 표시 됩니다.Following that, the TextBox's Text property is cleared out, the GridView is refreshed, and the ActionStatus Label displays a message indicating that the specified user was successfully added to the selected role.

Note

지정 된 사용자가 선택 된 역할에 아직 속해 있지 않은지 확인 하려면 Roles.IsUserInRole(userName, roleName) 메서드를 사용 합니다 .이 메서드는 사용자 이름이 roleName의 멤버 인지 여부를 나타내는 부울 값을 반환 합니다.To ensure that the specified user does not already belong to the selected role, we use the Roles.IsUserInRole(userName, roleName) method, which returns a Boolean value indicating whether userName is a member of roleName. 역할 기반 권한 부여를 살펴볼 때 다음 자습서 에서이 방법을 다시 사용 합니다.We will use this method again in the next tutorial when we look at role-based authorization.

브라우저를 통해 페이지를 방문 하 고 RoleList DropDownList에서 감독자 역할을 선택 합니다.Visit the page through a browser and select the Supervisors role from the RoleList DropDownList. 잘못 된 사용자 이름을 입력 해 보세요. 사용자가 시스템에 존재 하지 않는다는 메시지가 표시 됩니다.Try entering an invalid username – you should see a message explaining that the user does not exist in the system.

존재 하지 않는 사용자를 역할에 추가할 수 없습니다.You Cannot Add a Non-Existent User to a Role

그림 9: 존재 하지 않는 사용자를 역할에 추가할 수 없음 (전체 크기 이미지를 보려면 클릭)Figure 9: You Cannot Add a Non-Existent User to a Role (Click to view full-size image)

이제 유효한 사용자를 추가 해 보세요.Now try adding a valid user. 계속 해 서 Tito를 감독자 역할에 다시 추가 합니다.Go ahead and re-add Tito to the Supervisors role.

Tito가 감독자에 게 한 번입니다.Tito Is Once Again a Supervisor!

그림 10: 감독자에 게 한 번Figure 10: Tito Is Once Again a Supervisor! (전체 크기 이미지를 보려면 클릭)(Click to view full-size image)

3 단계: "사용자" 및 "역할 기준" 인터페이스를 교차 업데이트Step 3: Cross-Updating the "By User" and "By Role" Interfaces

UsersAndRoles.aspx 페이지는 사용자 및 역할을 관리 하기 위한 두 가지 고유한 인터페이스를 제공 합니다.The UsersAndRoles.aspx page offers two distinct interfaces for managing users and roles. 현재이 두 인터페이스는 서로 독립적으로 작동 하므로 한 인터페이스에서 변경한 내용이 다른 인터페이스에 즉시 반영 되지 않을 수 있습니다.Currently, these two interfaces act independently of one another so it is possible that a change made in one interface will not be reflected immediately in the other. 예를 들어 페이지 방문자가 Bruce 및 Tito를 멤버로 나열 하는 RoleList DropDownList에서 감독자 역할을 선택 한다고 가정 합니다.For example, imagine that the visitor to the page selects the Supervisors role from the RoleList DropDownList, which lists Bruce and Tito as its members. 그런 다음 방문자는 UserList DropDownList에서 Tito를 선택 하 여 UsersRoleList Repeater의 관리자 및 감독자 확인란을 확인 합니다.Next, the visitor selects Tito from the UserList DropDownList, which checks the Administrators and Supervisors checkboxes in the UsersRoleList Repeater. 그러면 방문자가 Repeater에서 감독자 역할을 편집 하는 경우 Tito가 감독자 역할에서 제거 되지만이 수정 사항은 "역할" 인터페이스에 반영 되지 않습니다.If the visitor then unchecks the Supervisor role from the Repeater, Tito is removed from the Supervisors role, but this modification is not reflected in the "by role" interface. GridView는 여전히 감독자 역할의 멤버가 되는 것으로 표시 합니다.The GridView will still show Tito as being a member of the Supervisors role.

이 문제를 해결 하려면 UsersRoleList 리피터에서 역할을 선택 하거나 선택 취소할 때마다 GridView를 새로 고쳐야 합니다.To fix this we need to refresh the GridView whenever a role is checked or unchecked from the UsersRoleList Repeater. 마찬가지로 사용자가 "role" 인터페이스에서 역할에 추가 되거나 제거 될 때마다 Repeater를 새로 고쳐야 합니다.Likewise, we need to refresh the Repeater whenever a user is removed or added to a role from the "by role" interface.

"사용자" 인터페이스의 Repeater는 CheckRolesForSelectedUser 메서드를 호출 하 여 새로 고쳐집니다.The Repeater in the "by user" interface is refreshed by calling the CheckRolesForSelectedUser method. "Role" 인터페이스는 RolesUserList GridView의 RowDeleting 이벤트 처리기 및 AddUserToRoleButton 단추의 Click 이벤트 처리기에서 수정할 수 있습니다.The "by role" interface can be modified in the RolesUserList GridView's RowDeleting event handler and the AddUserToRoleButton Button's Click event handler. 따라서 이러한 각 메서드에서 CheckRolesForSelectedUser 메서드를 호출 해야 합니다.Therefore, we need to call the CheckRolesForSelectedUser method from each of these methods.

protected void RolesUserList_RowDeleting(object sender, GridViewDeleteEventArgs e) 
{ 
     ... Code removed for brevity ... 

     // Refresh the "by user" interface 
     CheckRolesForSelectedUser(); 
} 

protected void AddUserToRoleButton_Click(object sender, EventArgs e) 
{ 
     ... Code removed for brevity ... 


     // Refresh the "by user" interface 
     CheckRolesForSelectedUser(); 
}

마찬가지로, "role" 인터페이스의 GridView는 DisplayUsersBelongingToRole 메서드를 호출 하 여 새로 고쳐지고 "사용자" 인터페이스는 RoleCheckBox_CheckChanged 이벤트 처리기를 통해 수정 됩니다.Similarly, the GridView in the "by role" interface is refreshed by calling the DisplayUsersBelongingToRole method and the "by user" interface is modified through the RoleCheckBox_CheckChanged event handler. 따라서이 이벤트 처리기에서 DisplayUsersBelongingToRole 메서드를 호출 해야 합니다.Therefore, we need to call the DisplayUsersBelongingToRole method from this event handler.

protected void RoleCheckBox_CheckChanged(object sender, EventArgs e) 
{ 
     ... Code removed for brevity... 

     // Refresh the "by role" interface 
     DisplayUsersBelongingToRole(); 
}

이러한 사소한 코드를 변경 하면 "사용자 기준" 및 "역할 기준" 인터페이스가 이제 올바르게 교차 업데이트 됩니다.With these minor code changes, the "by user" and "by role" interfaces now correctly cross-update. 이를 확인 하려면 브라우저를 통해 페이지를 방문 하 고 UserList에서 Tito 및 감독자를 선택 하 고 RoleList Dropdownlist를 각각 선택 합니다.To verify this, visit the page through a browser and select Tito and Supervisors from the UserList and RoleList DropDownLists, respectively. "사용자" 인터페이스의 Repeater에서 Tito에 대 한 감독자 역할을 선택 취소 하면 Tito는 "role" 인터페이스의 GridView에서 자동으로 제거 됩니다.Note that as you uncheck the Supervisors role for Tito from the Repeater in the "by user" interface, Tito is automatically removed from the GridView in the "by role" interface. "Role" 인터페이스에서 감독자 역할에 Tito를 추가 하면 "사용자" 인터페이스에서 감독자 확인란을 자동으로 다시 검사 합니다.Adding Tito back to the Supervisors role from the "by role" interface automatically re-checks the Supervisors checkbox in the "by user" interface.

4 단계: "역할 지정" 단계를 포함 하도록 CreateUserWizard 사용자 지정Step 4: Customizing the CreateUserWizard to Include a "Specify Roles" Step

사용자 계정 만들기 자습서에서 CreateUserWizard 웹 컨트롤을 사용 하 여 새 사용자 계정을 만들기 위한 인터페이스를 제공 하는 방법을 살펴보았습니다.In the Creating User Accounts tutorial we saw how to use the CreateUserWizard Web control to provide an interface for creating a new user account. CreateUserWizard 컨트롤은 다음 두 가지 방법 중 하나로 사용할 수 있습니다.The CreateUserWizard control can be used in one of two ways:

  • 방문자가 사이트에서 자신의 고유한 사용자 계정을 만드는 방법으로As a means for visitors to create their own user account on the site, and
  • 관리자가 새 계정을 만들 수 있도록 하는 방법As a means for administrators to create new accounts

첫 번째 사용 사례에서 방문자가 사이트에 제공 하 고 CreateUserWizard를 입력 하 여 사이트에 등록 하기 위해 정보를 입력 합니다.In the first use case, a visitor comes to the site and fills out the CreateUserWizard, entering their information in order to register on the site. 두 번째 경우 관리자가 다른 사용자에 대 한 새 계정을 만듭니다.In the second case, an administrator creates a new account for another person.

관리자가 다른 사용자를 위해 계정을 만들 경우 관리자가 새 사용자 계정이 속한 역할을 지정할 수 있도록 하는 것이 유용할 수 있습니다.When an account is being created by an administrator for some other person, it might be helpful to allow the administrator to specify what roles the new user account belongs to. 추가 사용자 정보 저장 자습서에서 추가 WizardSteps를 추가 하 여 CreateUserWizard를 사용자 지정 하는 방법을 살펴보았습니다.In the Storing Additional User Information tutorial we saw how to customize the CreateUserWizard by adding additional WizardSteps. 새 사용자의 역할을 지정 하기 위해 CreateUserWizard에 추가 단계를 추가 하는 방법을 살펴보겠습니다.Let's look at how to add an additional step to the CreateUserWizard in order to specify the new user's roles.

CreateUserWizardWithRoles.aspx 페이지를 열고 이름이 RegisterUserWithRoles인 CreateUserWizard 컨트롤을 추가 합니다.Open the CreateUserWizardWithRoles.aspx page and add a CreateUserWizard control named RegisterUserWithRoles. 컨트롤의 ContinueDestinationPageUrl 속성을 "~/Default.aspx"로 설정 합니다.Set the control's ContinueDestinationPageUrl property to "~/Default.aspx". 여기서는 관리자가이 CreateUserWizard 컨트롤을 사용 하 여 새 사용자 계정을 만드는 것 이므로 컨트롤의 LoginCreatedUser 속성을 False로 설정 합니다.Because the idea here is that an administrator will be using this CreateUserWizard control to create new user accounts, set the control's LoginCreatedUser property to False. LoginCreatedUser 속성은 방문자가 자신에 게 생성 된 사용자로 자동으로 로그온 하는지 여부를 지정 하며 기본값은 True입니다.This LoginCreatedUser property specifies whether the visitor is automatically logged on as the just-created user, and it defaults to True. 관리자가 새 계정을 만들 때 자기 자신에 게 로그인 된 상태를 유지 하려는 경우에는이 설정을 False로 설정 합니다.We set it to False because when an administrator creates a new account we want to keep him signed in as himself.

다음으로 "WizardSteps추가/제거 ..."를 선택 합니다. CreateUserWizard의 스마트 태그에서 옵션을 선택 하 고 새 WizardStep을 추가 하 여 IDSpecifyRolesStep로 설정 합니다.Next, select the "Add/Remove WizardSteps…" option from the CreateUserWizard's Smart Tag and add a new WizardStep, setting its ID to SpecifyRolesStep. "새 계정에 등록" 단계를 수행 하 고 "완료" 단계 전에 SpecifyRolesStep WizardStep 이동 합니다.Move the SpecifyRolesStep WizardStep so that it comes after the "Sign Up for Your New Account" step, but before the "Complete" step. WizardStepTitle 속성을 "역할 지정"으로 설정 하 고 StepType 속성을 Step로 설정 하 고 해당 AllowReturn 속성을 False로 설정 합니다.Set the WizardStep's Title property to "Specify Roles", its StepType property to Step, and its AllowReturn property to False.

추가 합니다.Add the

그림 11: CreateUserWizard에 "역할 지정" WizardStep 추가 (전체 크기 이미지를 보려면 클릭)Figure 11: Add the "Specify Roles" WizardStep to the CreateUserWizard (Click to view full-size image)

이렇게 변경 하면 CreateUserWizard의 선언적 태그가 다음과 같이 표시 됩니다.After this change your CreateUserWizard's declarative markup should look like the following:

<asp:CreateUserWizard ID="RegisterUserWithRoles" runat="server" 
     ContinueDestinationPageUrl="~/Default.aspx" LoginCreatedUser="False"> 

     <WizardSteps> 
          <asp:CreateUserWizardStep ID="CreateUserWizardStep1" runat="server"> 
          </asp:CreateUserWizardStep> 
          <asp:WizardStep ID="SpecifyRolesStep" runat="server" StepType="Step" 

               Title="Specify Roles" AllowReturn="False"> 
          </asp:WizardStep> 
          <asp:CompleteWizardStep ID="CompleteWizardStep1" runat="server"> 
          </asp:CompleteWizardStep> 
     </WizardSteps> 

</asp:CreateUserWizard>

"역할 지정" WizardStep에서 이름이 RoleList인 CheckBoxList를 추가 합니다.In the "Specify Roles" WizardStep, add a CheckBoxList named RoleList. 이 CheckBoxList는 사용 가능한 역할을 나열 하 여 페이지를 방문 하는 사용자가 새로 만든 사용자가 속한 역할을 확인할 수 있도록 합니다.This CheckBoxList will list the available roles, enabling the person visiting the page to check what roles the newly created user belongs to.

두 가지 코딩 작업이 있습니다. 먼저 RoleList CheckBoxList를 시스템의 역할로 채워야 합니다. 두 번째로, 사용자가 "역할 지정" 단계에서 "완료" 단계로 이동할 때 만든 사용자를 선택한 역할에 추가 해야 합니다.We are left with two coding tasks: first we must populate the RoleList CheckBoxList with the roles in the system; second, we need to add the created user to the selected roles when the user moves from the "Specify Roles" step to the "Complete" step. Page_Load 이벤트 처리기에서 첫 번째 작업을 수행할 수 있습니다.We can accomplish the first task in the Page_Load event handler. 다음 코드에서는 페이지에 대 한 첫 번째 방문에서 RoleList CheckBox를 프로그래밍 방식으로 참조 하 고 시스템의 역할을 해당 페이지에 바인딩합니다.The following code programmatically references the RoleList CheckBox on the first visit to the page and binds the roles in the system to it.

protected void Page_Load(object sender, EventArgs e) 
{ 
     if (!Page.IsPostBack) 
     { 
          // Reference the SpecifyRolesStep WizardStep 
          WizardStep SpecifyRolesStep = RegisterUserWithRoles.FindControl("SpecifyRolesStep") as WizardStep; 

          // Reference the RoleList CheckBoxList 
          CheckBoxList RoleList = SpecifyRolesStep.FindControl("RoleList") as CheckBoxList; 

          // Bind the set of roles to RoleList 
          RoleList.DataSource = Roles.GetAllRoles(); 
          RoleList.DataBind(); 
     } 
}

위의 코드는 잘 알고 있어야 합니다.The above code should look familiar. 추가 사용자 정보 저장 자습서에서는 사용자 지정 WizardStep에서 웹 컨트롤을 참조 하는 두 개의 FindControl 문을 사용 했습니다.In the Storing Additional User Information tutorial we used two FindControl statements to reference a Web control from within a custom WizardStep. 그리고 CheckBoxList에 역할을 바인딩하는 코드는이 자습서의 앞부분에서 가져온 것입니다.And the code that binds the roles to the CheckBoxList was taken from earlier in this tutorial.

두 번째 프로그래밍 작업을 수행 하기 위해 "역할 지정" 단계가 완료 된 시기를 알아야 합니다.In order to perform the second programming task we need to know when the "Specify Roles" step has been completed. CreateUserWizard에는 방문자가 한 단계에서 다른 단계로 이동할 때마다 발생 하는 ActiveStepChanged 이벤트가 있습니다.Recall that the CreateUserWizard has an ActiveStepChanged event, which fires each time the visitor navigates from one step to another. 여기서는 사용자가 "완료" 단계에 도달 했는지 여부를 확인할 수 있습니다. 그렇다면 선택한 역할에 사용자를 추가 해야 합니다.Here we can determine if the user has reached the "Complete" step; if so, we need to add the user to the selected roles.

ActiveStepChanged 이벤트에 대 한 이벤트 처리기를 만들고 다음 코드를 추가 합니다.Create an event handler for the ActiveStepChanged event and add the following code:

protected void RegisterUserWithRoles_ActiveStepChanged(object sender, EventArgs e) 
{ 
     // Have we JUST reached the Complete step? 
     if (RegisterUserWithRoles.ActiveStep.Title == "Complete") 
     { 
          // Reference the SpecifyRolesStep WizardStep 
          WizardStep SpecifyRolesStep = RegisterUserWithRoles.FindControl("SpecifyRolesStep") as WizardStep; 

          // Reference the RoleList CheckBoxList 
          CheckBoxList RoleList = SpecifyRolesStep.FindControl("RoleList") as CheckBoxList; 

          // Add the checked roles to the just-added user 
          foreach (ListItem li in RoleList.Items) 

          { 
               if (li.Selected) 
                    Roles.AddUserToRole(RegisterUserWithRoles.UserName, li.Text); 
          } 
     } 
}

사용자가 "완료" 단계에 도달한 경우 이벤트 처리기는 RoleList CheckBoxList의 항목을 열거 하 고, 사용자가 만든 사용자가 선택한 역할에 할당 됩니다.If the user has just reached the "Completed" step, the event handler enumerates the items of the RoleList CheckBoxList and the just-created user is assigned to the selected roles.

브라우저를 통해이 페이지를 방문 하세요.Visit this page through a browser. CreateUserWizard의 첫 번째 단계는 새로운 사용자의 사용자 이름, 암호, 전자 메일 및 기타 키 정보를 요청 하는 표준 "새 계정에 등록" 단계입니다.The first step in the CreateUserWizard is the standard "Sign Up for Your New Account" step, which prompts for the new user's username, password, email, and other key information. 정보를 입력 하 여 Wanda 라는 새 사용자를 만듭니다.Enter the information to create a new user named Wanda.

Wanda 이라는 새 사용자를 만듭니다.Create a New User Named Wanda

그림 12: Wanda 이라는 새 사용자 만들기 (전체 크기 이미지를 보려면 클릭)Figure 12: Create a New User Named Wanda (Click to view full-size image)

"사용자 만들기" 단추를 클릭 합니다.Click the "Create User" button. CreateUserWizard은 내부적으로 Membership.CreateUser 메서드를 호출 하 여 새 사용자 계정을 만든 후 다음 단계인 "역할 지정"으로 진행 합니다.The CreateUserWizard internally calls the Membership.CreateUser method, creating the new user account, and then progresses to the next step, "Specify Roles." 여기에 시스템 역할이 나열 됩니다.Here the system roles are listed. 감독자 확인란을 선택 하 고 다음을 클릭 합니다.Check the Supervisors checkbox and click Next.

Wanda을 감독자 역할의 구성원으로 설정 Make Wanda a Member of the Supervisors Role

그림 13: Wanda을 감독자 역할의 멤버로 만들기 (전체 크기 이미지를 보려면 클릭)Figure 13: Make Wanda a Member of the Supervisors Role (Click to view full-size image)

[다음]을 클릭 하면 포스트백이 발생 하 고 ActiveStep "Complete" 단계로 업데이트 됩니다.Clicking Next causes a postback and updates the ActiveStep to the "Complete" step. ActiveStepChanged 이벤트 처리기에서 최근에 만든 사용자 계정이 감독자 역할에 할당 됩니다.In the ActiveStepChanged event handler, the recently-created user account is assigned to the Supervisors role. 이를 확인 하려면 UsersAndRoles.aspx 페이지로 돌아가 RoleList DropDownList에서 감독자를 선택 합니다.To verify this, return to the UsersAndRoles.aspx page and select Supervisors from the RoleList DropDownList. 그림 14와 같이 감독자는 이제 Bruce, Tito 및 Wanda의 세 가지 사용자로 구성 됩니다.As Figure 14 shows, the Supervisors are now made up of three users: Bruce, Tito, and Wanda.

Bruce, Tito 및 Wanda는 모두 감독자입니다.Bruce, Tito, and Wanda are All Supervisors

그림 14: Bruce, Tito 및 Wanda는 모두 감독자입니다 (전체 크기 이미지를 보려면 클릭).Figure 14: Bruce, Tito, and Wanda are All Supervisors (Click to view full-size image)

요약Summary

역할 프레임 워크는 특정 사용자의 역할에 대 한 정보를 검색 하는 메서드와 지정 된 역할에 속한 사용자를 결정 하는 메서드를 제공 합니다.The Roles framework offers methods for retrieving information about a particular user's roles and methods for determining what users belong to a specified role. 또한 하나 이상의 역할에 하나 이상의 사용자를 추가 하 고 제거 하는 방법에는 여러 가지가 있습니다.Furthermore, there are a number of methods for adding and removing one or more users to one or more roles. 이 자습서에서는 AddUserToRoleRemoveUserFromRole의 두 가지 방법에 대해 집중적으로 설명 했습니다.In this tutorial we focused on just two of these methods: AddUserToRole and RemoveUserFromRole. 단일 역할에 여러 사용자를 추가 하 고 단일 사용자에 게 여러 역할을 할당 하도록 디자인 된 추가 변형이 있습니다.There are additional variants designed to add multiple users to a single role and to assign multiple roles to a single user.

이 자습서에는 새로 만든 사용자의 역할을 지정 하 WizardStep를 포함 하도록 CreateUserWizard 컨트롤을 확장 하는 방법도 포함 되어 있습니다.This tutorial also included a look at extending the CreateUserWizard control to include a WizardStep to specify the newly-created user's roles. 이러한 단계는 관리자가 새 사용자를 위한 사용자 계정을 만드는 프로세스를 간소화 하는 데 도움이 될 수 있습니다.Such a step could help an administrator streamline the process of creating user accounts for new users.

이 시점에서 역할을 만들고 삭제 하는 방법 및 역할에서 사용자를 추가 및 제거 하는 방법을 살펴보았습니다.At this point we have seen how to create and delete roles and how to add and remove users from roles. 하지만 역할 기반 권한 부여를 적용 하는 것은 아직 확인 하지 않았습니다.But we have yet to look at applying role-based authorization. 다음 자습서 에서는 역할 별로 URL 권한 부여 규칙을 정의 하는 방법과 현재 로그인 한 사용자의 역할에 따라 페이지 수준 기능을 제한 하는 방법을 살펴보겠습니다.In the following tutorial we will look at defining URL authorization rules on a role-by-role basis, as well as how to limit page-level functionality based on the currently logged in user's roles.

행복 한 프로그래밍Happy Programming!

추가 참고 자료Further Reading

이 자습서에서 설명 하는 항목에 대 한 자세한 내용은 다음 리소스를 참조 하세요.For more information on the topics discussed in this tutorial, refer to the following resources:

저자 정보About the Author

Scott Mitchell는 여러 ASP/ASP. NET books의 작성자와 4GuysFromRolla.com의 창립자가 1998부터 Microsoft 웹 기술을 사용 하 여 작업 했습니다.Scott Mitchell, author of multiple ASP/ASP.NET books and founder of 4GuysFromRolla.com, has been working with Microsoft Web technologies since 1998. Scott은 독립 컨설턴트, 강사 및 기록기로 작동 합니다.Scott works as an independent consultant, trainer, and writer. 최신 책은 24 시간 이내에 ASP.NET 2.0을 sams teach yourself 것입니다.His latest book is Sams Teach Yourself ASP.NET 2.0 in 24 Hours. Scott은 mitchell@4guysfromrolla.com 또는 http://ScottOnWriting.NET의 블로그를 통해 연결할 수 있습니다.Scott can be reached at mitchell@4guysfromrolla.com or via his blog at http://ScottOnWriting.NET.

특별 해 주셔서 감사 합니다.Special Thanks To…

이 자습서 시리즈는 많은 유용한 검토자가 검토 했습니다.This tutorial series was reviewed by many helpful reviewers. 이 자습서의 리드 검토자는 Teresa Murphy입니다.Lead reviewer for this tutorial was Teresa Murphy. 예정 된 MSDN 문서를 검토 하는 데 관심이 있나요?Interested in reviewing my upcoming MSDN articles? 그렇다면 mitchell@4GuysFromRolla.com 에 줄을 놓습니다.If so, drop me a line at mitchell@4GuysFromRolla.com