Browse Source

*: support getting all users and roles in auth v3

This commit expands RPCs for getting user and role and support list up
all users and roles. etcdctl v3 is now support getting all users and
roles with the newly added option --all e.g. etcdctl user get --all
Hitoshi Mitake 9 years ago
parent
commit
18253e2723

+ 34 - 2
Documentation/dev-guide/api_reference_v3.md

@@ -12,13 +12,15 @@ This is a generated documentation. Please read the proto files for more.
 | AuthDisable | AuthDisableRequest | AuthDisableResponse | AuthDisable disables authentication. |
 | Authenticate | AuthenticateRequest | AuthenticateResponse | Authenticate processes an authenticate request. |
 | UserAdd | AuthUserAddRequest | AuthUserAddResponse | UserAdd adds a new user. |
-| UserGet | AuthUserGetRequest | AuthUserGetResponse | UserGet gets detailed user information or lists all users. |
+| UserGet | AuthUserGetRequest | AuthUserGetResponse | UserGet gets detailed user information. |
+| UserList | AuthUserListRequest | AuthUserListResponse | UserList gets a list of all users. |
 | UserDelete | AuthUserDeleteRequest | AuthUserDeleteResponse | UserDelete deletes a specified user. |
 | UserChangePassword | AuthUserChangePasswordRequest | AuthUserChangePasswordResponse | UserChangePassword changes the password of a specified user. |
 | UserGrantRole | AuthUserGrantRoleRequest | AuthUserGrantRoleResponse | UserGrant grants a role to a specified user. |
 | UserRevokeRole | AuthUserRevokeRoleRequest | AuthUserRevokeRoleResponse | UserRevokeRole revokes a role of specified user. |
 | RoleAdd | AuthRoleAddRequest | AuthRoleAddResponse | RoleAdd adds a new role. |
-| RoleGet | AuthRoleGetRequest | AuthRoleGetResponse | RoleGet gets detailed role information or lists all roles. |
+| RoleGet | AuthRoleGetRequest | AuthRoleGetResponse | RoleGet gets detailed role information. |
+| RoleList | AuthRoleListRequest | AuthRoleListResponse | RoleList gets lists of all roles. |
 | RoleDelete | AuthRoleDeleteRequest | AuthRoleDeleteResponse | RoleDelete deletes a specified role. |
 | RoleGrantPermission | AuthRoleGrantPermissionRequest | AuthRoleGrantPermissionResponse | RoleGrantPermission grants a permission of a specified key or range to a specified role. |
 | RoleRevokePermission | AuthRoleRevokePermissionRequest | AuthRoleRevokePermissionResponse | RoleRevokePermission revokes a key or range permission of a specified role. |
@@ -204,6 +206,21 @@ Empty field.
 
 
 
+##### message `AuthRoleListRequest` (etcdserver/etcdserverpb/rpc.proto)
+
+Empty field.
+
+
+
+##### message `AuthRoleListResponse` (etcdserver/etcdserverpb/rpc.proto)
+
+| Field | Description | Type |
+| ----- | ----------- | ---- |
+| header |  | ResponseHeader |
+| roles |  | (slice of) string |
+
+
+
 ##### message `AuthRoleRevokePermissionRequest` (etcdserver/etcdserverpb/rpc.proto)
 
 | Field | Description | Type |
@@ -306,6 +323,21 @@ Empty field.
 
 
 
+##### message `AuthUserListRequest` (etcdserver/etcdserverpb/rpc.proto)
+
+Empty field.
+
+
+
+##### message `AuthUserListResponse` (etcdserver/etcdserverpb/rpc.proto)
+
+| Field | Description | Type |
+| ----- | ----------- | ---- |
+| header |  | ResponseHeader |
+| users |  | (slice of) string |
+
+
+
 ##### message `AuthUserRevokeRoleRequest` (etcdserver/etcdserverpb/rpc.proto)
 
 | Field | Description | Type |

+ 85 - 3
auth/store.go

@@ -83,7 +83,7 @@ type AuthStore interface {
 	// UserGrantRole grants a role to the user
 	UserGrantRole(r *pb.AuthUserGrantRoleRequest) (*pb.AuthUserGrantRoleResponse, error)
 
-	// UserGet gets the detailed information of a user
+	// UserGet gets the detailed information of a users
 	UserGet(r *pb.AuthUserGetRequest) (*pb.AuthUserGetResponse, error)
 
 	// UserRevokeRole revokes a role of a user
@@ -104,6 +104,12 @@ type AuthStore interface {
 	// RoleDelete gets the detailed information of a role
 	RoleDelete(r *pb.AuthRoleDeleteRequest) (*pb.AuthRoleDeleteResponse, error)
 
+	// UserList gets a list of all users
+	UserList(r *pb.AuthUserListRequest) (*pb.AuthUserListResponse, error)
+
+	// RoleList gets a list of all roles
+	RoleList(r *pb.AuthRoleListRequest) (*pb.AuthRoleListResponse, error)
+
 	// UsernameFromToken gets a username from the given Token
 	UsernameFromToken(token string) (string, bool)
 
@@ -339,12 +345,13 @@ func (as *authStore) UserGet(r *pb.AuthUserGetRequest) (*pb.AuthUserGetResponse,
 	tx.Lock()
 	defer tx.Unlock()
 
+	var resp pb.AuthUserGetResponse
+
 	user := getUser(tx, r.Name)
 	if user == nil {
 		return nil, ErrUserNotFound
 	}
 
-	var resp pb.AuthUserGetResponse
 	for _, role := range user.Roles {
 		resp.Roles = append(resp.Roles, role)
 	}
@@ -352,6 +359,22 @@ func (as *authStore) UserGet(r *pb.AuthUserGetRequest) (*pb.AuthUserGetResponse,
 	return &resp, nil
 }
 
+func (as *authStore) UserList(r *pb.AuthUserListRequest) (*pb.AuthUserListResponse, error) {
+	tx := as.be.BatchTx()
+	tx.Lock()
+	defer tx.Unlock()
+
+	var resp pb.AuthUserListResponse
+
+	users := getAllUsers(tx)
+
+	for _, u := range users {
+		resp.Users = append(resp.Users, string(u.Name))
+	}
+
+	return &resp, nil
+}
+
 func (as *authStore) UserRevokeRole(r *pb.AuthUserRevokeRoleRequest) (*pb.AuthUserRevokeRoleResponse, error) {
 	tx := as.be.BatchTx()
 	tx.Lock()
@@ -390,12 +413,13 @@ func (as *authStore) RoleGet(r *pb.AuthRoleGetRequest) (*pb.AuthRoleGetResponse,
 	tx.Lock()
 	defer tx.Unlock()
 
+	var resp pb.AuthRoleGetResponse
+
 	role := getRole(tx, r.Role)
 	if role == nil {
 		return nil, ErrRoleNotFound
 	}
 
-	var resp pb.AuthRoleGetResponse
 	for _, perm := range role.KeyPermission {
 		resp.Perm = append(resp.Perm, perm)
 	}
@@ -403,6 +427,22 @@ func (as *authStore) RoleGet(r *pb.AuthRoleGetRequest) (*pb.AuthRoleGetResponse,
 	return &resp, nil
 }
 
+func (as *authStore) RoleList(r *pb.AuthRoleListRequest) (*pb.AuthRoleListResponse, error) {
+	tx := as.be.BatchTx()
+	tx.Lock()
+	defer tx.Unlock()
+
+	var resp pb.AuthRoleListResponse
+
+	roles := getAllRoles(tx)
+
+	for _, r := range roles {
+		resp.Roles = append(resp.Roles, string(r.Name))
+	}
+
+	return &resp, nil
+}
+
 func (as *authStore) RoleRevokePermission(r *pb.AuthRoleRevokePermissionRequest) (*pb.AuthRoleRevokePermissionResponse, error) {
 	tx := as.be.BatchTx()
 	tx.Lock()
@@ -613,6 +653,27 @@ func getUser(tx backend.BatchTx, username string) *authpb.User {
 	return user
 }
 
+func getAllUsers(tx backend.BatchTx) []*authpb.User {
+	_, vs := tx.UnsafeRange(authUsersBucketName, []byte{0}, []byte{0xff}, -1)
+	if len(vs) == 0 {
+		return nil
+	}
+
+	var users []*authpb.User
+
+	for _, v := range vs {
+		user := &authpb.User{}
+		err := user.Unmarshal(v)
+		if err != nil {
+			plog.Panicf("failed to unmarshal user struct: %s", err)
+		}
+
+		users = append(users, user)
+	}
+
+	return users
+}
+
 func putUser(tx backend.BatchTx, user *authpb.User) {
 	b, err := user.Marshal()
 	if err != nil {
@@ -639,6 +700,27 @@ func getRole(tx backend.BatchTx, rolename string) *authpb.Role {
 	return role
 }
 
+func getAllRoles(tx backend.BatchTx) []*authpb.Role {
+	_, vs := tx.UnsafeRange(authRolesBucketName, []byte{0}, []byte{0xff}, -1)
+	if len(vs) == 0 {
+		return nil
+	}
+
+	var roles []*authpb.Role
+
+	for _, v := range vs {
+		role := &authpb.Role{}
+		err := role.Unmarshal(v)
+		if err != nil {
+			plog.Panicf("failed to unmarshal role struct: %s", err)
+		}
+
+		roles = append(roles, role)
+	}
+
+	return roles
+}
+
 func putRole(tx backend.BatchTx, role *authpb.Role) {
 	b, err := role.Marshal()
 	if err != nil {

+ 18 - 0
clientv3/auth.go

@@ -39,6 +39,8 @@ type (
 	AuthRoleGetResponse              pb.AuthRoleGetResponse
 	AuthRoleRevokePermissionResponse pb.AuthRoleRevokePermissionResponse
 	AuthRoleDeleteResponse           pb.AuthRoleDeleteResponse
+	AuthUserListResponse             pb.AuthUserListResponse
+	AuthRoleListResponse             pb.AuthRoleListResponse
 
 	PermissionType authpb.Permission_Type
 )
@@ -71,6 +73,9 @@ type Auth interface {
 	// UserGet gets a detailed information of a user.
 	UserGet(ctx context.Context, name string) (*AuthUserGetResponse, error)
 
+	// UserList gets a list of all users.
+	UserList(ctx context.Context) (*AuthUserListResponse, error)
+
 	// UserRevokeRole revokes a role of a user.
 	UserRevokeRole(ctx context.Context, name string, role string) (*AuthUserRevokeRoleResponse, error)
 
@@ -83,6 +88,9 @@ type Auth interface {
 	// RoleGet gets a detailed information of a role.
 	RoleGet(ctx context.Context, role string) (*AuthRoleGetResponse, error)
 
+	// RoleList gets a list of all roles.
+	RoleList(ctx context.Context) (*AuthRoleListResponse, error)
+
 	// RoleRevokePermission revokes a permission from a role.
 	RoleRevokePermission(ctx context.Context, role string, key, rangeEnd string) (*AuthRoleRevokePermissionResponse, error)
 
@@ -141,6 +149,11 @@ func (auth *auth) UserGet(ctx context.Context, name string) (*AuthUserGetRespons
 	return (*AuthUserGetResponse)(resp), toErr(ctx, err)
 }
 
+func (auth *auth) UserList(ctx context.Context) (*AuthUserListResponse, error) {
+	resp, err := auth.remote.UserList(ctx, &pb.AuthUserListRequest{})
+	return (*AuthUserListResponse)(resp), toErr(ctx, err)
+}
+
 func (auth *auth) UserRevokeRole(ctx context.Context, name string, role string) (*AuthUserRevokeRoleResponse, error) {
 	resp, err := auth.remote.UserRevokeRole(ctx, &pb.AuthUserRevokeRoleRequest{Name: name, Role: role})
 	return (*AuthUserRevokeRoleResponse)(resp), toErr(ctx, err)
@@ -166,6 +179,11 @@ func (auth *auth) RoleGet(ctx context.Context, role string) (*AuthRoleGetRespons
 	return (*AuthRoleGetResponse)(resp), toErr(ctx, err)
 }
 
+func (auth *auth) RoleList(ctx context.Context) (*AuthRoleListResponse, error) {
+	resp, err := auth.remote.RoleList(ctx, &pb.AuthRoleListRequest{})
+	return (*AuthRoleListResponse)(resp), toErr(ctx, err)
+}
+
 func (auth *auth) RoleRevokePermission(ctx context.Context, role string, key, rangeEnd string) (*AuthRoleRevokePermissionResponse, error) {
 	resp, err := auth.remote.RoleRevokePermission(ctx, &pb.AuthRoleRevokePermissionRequest{Role: role, Key: key, RangeEnd: rangeEnd})
 	return (*AuthRoleRevokePermissionResponse)(resp), toErr(ctx, err)

+ 28 - 2
etcdctl/ctlv3/command/role_command.go

@@ -32,6 +32,7 @@ func NewRoleCommand() *cobra.Command {
 	ac.AddCommand(newRoleAddCommand())
 	ac.AddCommand(newRoleDeleteCommand())
 	ac.AddCommand(newRoleGetCommand())
+	ac.AddCommand(newRoleListCommand())
 	ac.AddCommand(newRoleRevokePermissionCommand())
 	ac.AddCommand(newRoleGrantPermissionCommand())
 
@@ -62,6 +63,14 @@ func newRoleGetCommand() *cobra.Command {
 	}
 }
 
+func newRoleListCommand() *cobra.Command {
+	return &cobra.Command{
+		Use:   "list",
+		Short: "list up all roles",
+		Run:   roleListCommandFunc,
+	}
+}
+
 func newRoleGrantPermissionCommand() *cobra.Command {
 	return &cobra.Command{
 		Use:   "grant-permission <role name> <permission type> <key> [endkey]",
@@ -112,12 +121,13 @@ func roleGetCommandFunc(cmd *cobra.Command, args []string) {
 		ExitWithError(ExitBadArgs, fmt.Errorf("role get command requires role name as its argument."))
 	}
 
-	resp, err := mustClientFromCmd(cmd).Auth.RoleGet(context.TODO(), args[0])
+	name := args[0]
+	resp, err := mustClientFromCmd(cmd).Auth.RoleGet(context.TODO(), name)
 	if err != nil {
 		ExitWithError(ExitError, err)
 	}
 
-	fmt.Printf("Role %s\n", args[0])
+	fmt.Printf("Role %s\n", name)
 	fmt.Println("KV Read:")
 	for _, perm := range resp.Perm {
 		if perm.PermType == clientv3.PermRead || perm.PermType == clientv3.PermReadWrite {
@@ -140,6 +150,22 @@ func roleGetCommandFunc(cmd *cobra.Command, args []string) {
 	}
 }
 
+// roleListCommandFunc executes the "role list" command.
+func roleListCommandFunc(cmd *cobra.Command, args []string) {
+	if len(args) != 0 {
+		ExitWithError(ExitBadArgs, fmt.Errorf("role list command requires no arguments."))
+	}
+
+	resp, err := mustClientFromCmd(cmd).Auth.RoleList(context.TODO())
+	if err != nil {
+		ExitWithError(ExitError, err)
+	}
+
+	for _, role := range resp.Roles {
+		fmt.Printf("%s\n", role)
+	}
+}
+
 // roleGrantPermissionCommandFunc executes the "role grant-permission" command.
 func roleGrantPermissionCommandFunc(cmd *cobra.Command, args []string) {
 	if len(args) < 3 {

+ 28 - 2
etcdctl/ctlv3/command/user_command.go

@@ -33,6 +33,7 @@ func NewUserCommand() *cobra.Command {
 	ac.AddCommand(newUserAddCommand())
 	ac.AddCommand(newUserDeleteCommand())
 	ac.AddCommand(newUserGetCommand())
+	ac.AddCommand(newUserListCommand())
 	ac.AddCommand(newUserChangePasswordCommand())
 	ac.AddCommand(newUserGrantRoleCommand())
 	ac.AddCommand(newUserRevokeRoleCommand())
@@ -73,6 +74,14 @@ func newUserGetCommand() *cobra.Command {
 	}
 }
 
+func newUserListCommand() *cobra.Command {
+	return &cobra.Command{
+		Use:   "list",
+		Short: "list up all users",
+		Run:   userListCommandFunc,
+	}
+}
+
 func newUserChangePasswordCommand() *cobra.Command {
 	cmd := cobra.Command{
 		Use:   "passwd <user name>",
@@ -143,12 +152,13 @@ func userGetCommandFunc(cmd *cobra.Command, args []string) {
 		ExitWithError(ExitBadArgs, fmt.Errorf("user get command requires user name as its argument."))
 	}
 
-	resp, err := mustClientFromCmd(cmd).Auth.UserGet(context.TODO(), args[0])
+	name := args[0]
+	resp, err := mustClientFromCmd(cmd).Auth.UserGet(context.TODO(), name)
 	if err != nil {
 		ExitWithError(ExitError, err)
 	}
 
-	fmt.Printf("User: %s\n", args[0])
+	fmt.Printf("User: %s\n", name)
 	fmt.Printf("Roles:")
 	for _, role := range resp.Roles {
 		fmt.Printf(" %s", role)
@@ -156,6 +166,22 @@ func userGetCommandFunc(cmd *cobra.Command, args []string) {
 	fmt.Printf("\n")
 }
 
+// userListCommandFunc executes the "user list" command.
+func userListCommandFunc(cmd *cobra.Command, args []string) {
+	if len(args) != 0 {
+		ExitWithError(ExitBadArgs, fmt.Errorf("user list command requires no arguments."))
+	}
+
+	resp, err := mustClientFromCmd(cmd).Auth.UserList(context.TODO())
+	if err != nil {
+		ExitWithError(ExitError, err)
+	}
+
+	for _, user := range resp.Users {
+		fmt.Printf("%s\n", user)
+	}
+}
+
 // userChangePasswordCommandFunc executes the "user passwd" command.
 func userChangePasswordCommandFunc(cmd *cobra.Command, args []string) {
 	if len(args) != 1 {

+ 16 - 0
etcdserver/api/v3rpc/auth.go

@@ -76,6 +76,14 @@ func (as *AuthServer) RoleGet(ctx context.Context, r *pb.AuthRoleGetRequest) (*p
 	return resp, nil
 }
 
+func (as *AuthServer) RoleList(ctx context.Context, r *pb.AuthRoleListRequest) (*pb.AuthRoleListResponse, error) {
+	resp, err := as.authenticator.RoleList(ctx, r)
+	if err != nil {
+		return nil, togRPCError(err)
+	}
+	return resp, nil
+}
+
 func (as *AuthServer) RoleRevokePermission(ctx context.Context, r *pb.AuthRoleRevokePermissionRequest) (*pb.AuthRoleRevokePermissionResponse, error) {
 	resp, err := as.authenticator.RoleRevokePermission(ctx, r)
 	if err != nil {
@@ -116,6 +124,14 @@ func (as *AuthServer) UserGet(ctx context.Context, r *pb.AuthUserGetRequest) (*p
 	return resp, nil
 }
 
+func (as *AuthServer) UserList(ctx context.Context, r *pb.AuthUserListRequest) (*pb.AuthUserListResponse, error) {
+	resp, err := as.authenticator.UserList(ctx, r)
+	if err != nil {
+		return nil, togRPCError(err)
+	}
+	return resp, nil
+}
+
 func (as *AuthServer) UserGrantRole(ctx context.Context, r *pb.AuthUserGrantRoleRequest) (*pb.AuthUserGrantRoleResponse, error) {
 	resp, err := as.authenticator.UserGrantRole(ctx, r)
 	if err != nil {

+ 14 - 0
etcdserver/apply.go

@@ -78,6 +78,8 @@ type applierV3 interface {
 	RoleGet(ua *pb.AuthRoleGetRequest) (*pb.AuthRoleGetResponse, error)
 	RoleRevokePermission(ua *pb.AuthRoleRevokePermissionRequest) (*pb.AuthRoleRevokePermissionResponse, error)
 	RoleDelete(ua *pb.AuthRoleDeleteRequest) (*pb.AuthRoleDeleteResponse, error)
+	UserList(ua *pb.AuthUserListRequest) (*pb.AuthUserListResponse, error)
+	RoleList(ua *pb.AuthRoleListRequest) (*pb.AuthRoleListResponse, error)
 }
 
 type applierV3backend struct {
@@ -140,6 +142,10 @@ func (a *applierV3backend) Apply(r *pb.InternalRaftRequest) *applyResult {
 		ar.resp, ar.err = a.s.applyV3.RoleRevokePermission(r.AuthRoleRevokePermission)
 	case r.AuthRoleDelete != nil:
 		ar.resp, ar.err = a.s.applyV3.RoleDelete(r.AuthRoleDelete)
+	case r.AuthUserList != nil:
+		ar.resp, ar.err = a.s.applyV3.UserList(r.AuthUserList)
+	case r.AuthRoleList != nil:
+		ar.resp, ar.err = a.s.applyV3.RoleList(r.AuthRoleList)
 	default:
 		panic("not implemented")
 	}
@@ -590,6 +596,14 @@ func (a *applierV3backend) RoleDelete(r *pb.AuthRoleDeleteRequest) (*pb.AuthRole
 	return a.s.AuthStore().RoleDelete(r)
 }
 
+func (a *applierV3backend) UserList(r *pb.AuthUserListRequest) (*pb.AuthUserListResponse, error) {
+	return a.s.AuthStore().UserList(r)
+}
+
+func (a *applierV3backend) RoleList(r *pb.AuthRoleListRequest) (*pb.AuthRoleListResponse, error) {
+	return a.s.AuthStore().RoleList(r)
+}
+
 type quotaApplierV3 struct {
 	applierV3
 	q Quota

+ 4 - 0
etcdserver/apply_auth.go

@@ -146,6 +146,10 @@ func needAdminPermission(r *pb.InternalRaftRequest) bool {
 		return true
 	case r.AuthRoleDelete != nil:
 		return true
+	case r.AuthUserList != nil:
+		return true
+	case r.AuthRoleList != nil:
+		return true
 	default:
 		return false
 	}

+ 4 - 0
etcdserver/etcdserverpb/etcdserver.pb.go

@@ -72,6 +72,8 @@
 		AuthUserRevokeRoleRequest
 		AuthRoleAddRequest
 		AuthRoleGetRequest
+		AuthUserListRequest
+		AuthRoleListRequest
 		AuthRoleDeleteRequest
 		AuthRoleGrantPermissionRequest
 		AuthRoleRevokePermissionRequest
@@ -86,6 +88,8 @@
 		AuthUserRevokeRoleResponse
 		AuthRoleAddResponse
 		AuthRoleGetResponse
+		AuthRoleListResponse
+		AuthUserListResponse
 		AuthRoleDeleteResponse
 		AuthRoleGrantPermissionResponse
 		AuthRoleRevokePermissionResponse

+ 162 - 60
etcdserver/etcdserverpb/raft_internal.pb.go

@@ -53,6 +53,8 @@ type InternalRaftRequest struct {
 	AuthUserChangePassword   *AuthUserChangePasswordRequest   `protobuf:"bytes,1103,opt,name=auth_user_change_password,json=authUserChangePassword" json:"auth_user_change_password,omitempty"`
 	AuthUserGrantRole        *AuthUserGrantRoleRequest        `protobuf:"bytes,1104,opt,name=auth_user_grant_role,json=authUserGrantRole" json:"auth_user_grant_role,omitempty"`
 	AuthUserRevokeRole       *AuthUserRevokeRoleRequest       `protobuf:"bytes,1105,opt,name=auth_user_revoke_role,json=authUserRevokeRole" json:"auth_user_revoke_role,omitempty"`
+	AuthUserList             *AuthUserListRequest             `protobuf:"bytes,1106,opt,name=auth_user_list,json=authUserList" json:"auth_user_list,omitempty"`
+	AuthRoleList             *AuthRoleListRequest             `protobuf:"bytes,1107,opt,name=auth_role_list,json=authRoleList" json:"auth_role_list,omitempty"`
 	AuthRoleAdd              *AuthRoleAddRequest              `protobuf:"bytes,1200,opt,name=auth_role_add,json=authRoleAdd" json:"auth_role_add,omitempty"`
 	AuthRoleDelete           *AuthRoleDeleteRequest           `protobuf:"bytes,1201,opt,name=auth_role_delete,json=authRoleDelete" json:"auth_role_delete,omitempty"`
 	AuthRoleGet              *AuthRoleGetRequest              `protobuf:"bytes,1202,opt,name=auth_role_get,json=authRoleGet" json:"auth_role_get,omitempty"`
@@ -355,17 +357,41 @@ func (m *InternalRaftRequest) MarshalTo(data []byte) (int, error) {
 		}
 		i += n19
 	}
+	if m.AuthUserList != nil {
+		data[i] = 0x92
+		i++
+		data[i] = 0x45
+		i++
+		i = encodeVarintRaftInternal(data, i, uint64(m.AuthUserList.Size()))
+		n20, err := m.AuthUserList.MarshalTo(data[i:])
+		if err != nil {
+			return 0, err
+		}
+		i += n20
+	}
+	if m.AuthRoleList != nil {
+		data[i] = 0x9a
+		i++
+		data[i] = 0x45
+		i++
+		i = encodeVarintRaftInternal(data, i, uint64(m.AuthRoleList.Size()))
+		n21, err := m.AuthRoleList.MarshalTo(data[i:])
+		if err != nil {
+			return 0, err
+		}
+		i += n21
+	}
 	if m.AuthRoleAdd != nil {
 		data[i] = 0x82
 		i++
 		data[i] = 0x4b
 		i++
 		i = encodeVarintRaftInternal(data, i, uint64(m.AuthRoleAdd.Size()))
-		n20, err := m.AuthRoleAdd.MarshalTo(data[i:])
+		n22, err := m.AuthRoleAdd.MarshalTo(data[i:])
 		if err != nil {
 			return 0, err
 		}
-		i += n20
+		i += n22
 	}
 	if m.AuthRoleDelete != nil {
 		data[i] = 0x8a
@@ -373,11 +399,11 @@ func (m *InternalRaftRequest) MarshalTo(data []byte) (int, error) {
 		data[i] = 0x4b
 		i++
 		i = encodeVarintRaftInternal(data, i, uint64(m.AuthRoleDelete.Size()))
-		n21, err := m.AuthRoleDelete.MarshalTo(data[i:])
+		n23, err := m.AuthRoleDelete.MarshalTo(data[i:])
 		if err != nil {
 			return 0, err
 		}
-		i += n21
+		i += n23
 	}
 	if m.AuthRoleGet != nil {
 		data[i] = 0x92
@@ -385,11 +411,11 @@ func (m *InternalRaftRequest) MarshalTo(data []byte) (int, error) {
 		data[i] = 0x4b
 		i++
 		i = encodeVarintRaftInternal(data, i, uint64(m.AuthRoleGet.Size()))
-		n22, err := m.AuthRoleGet.MarshalTo(data[i:])
+		n24, err := m.AuthRoleGet.MarshalTo(data[i:])
 		if err != nil {
 			return 0, err
 		}
-		i += n22
+		i += n24
 	}
 	if m.AuthRoleGrantPermission != nil {
 		data[i] = 0x9a
@@ -397,11 +423,11 @@ func (m *InternalRaftRequest) MarshalTo(data []byte) (int, error) {
 		data[i] = 0x4b
 		i++
 		i = encodeVarintRaftInternal(data, i, uint64(m.AuthRoleGrantPermission.Size()))
-		n23, err := m.AuthRoleGrantPermission.MarshalTo(data[i:])
+		n25, err := m.AuthRoleGrantPermission.MarshalTo(data[i:])
 		if err != nil {
 			return 0, err
 		}
-		i += n23
+		i += n25
 	}
 	if m.AuthRoleRevokePermission != nil {
 		data[i] = 0xa2
@@ -409,11 +435,11 @@ func (m *InternalRaftRequest) MarshalTo(data []byte) (int, error) {
 		data[i] = 0x4b
 		i++
 		i = encodeVarintRaftInternal(data, i, uint64(m.AuthRoleRevokePermission.Size()))
-		n24, err := m.AuthRoleRevokePermission.MarshalTo(data[i:])
+		n26, err := m.AuthRoleRevokePermission.MarshalTo(data[i:])
 		if err != nil {
 			return 0, err
 		}
-		i += n24
+		i += n26
 	}
 	return i, nil
 }
@@ -594,6 +620,14 @@ func (m *InternalRaftRequest) Size() (n int) {
 		l = m.AuthUserRevokeRole.Size()
 		n += 2 + l + sovRaftInternal(uint64(l))
 	}
+	if m.AuthUserList != nil {
+		l = m.AuthUserList.Size()
+		n += 2 + l + sovRaftInternal(uint64(l))
+	}
+	if m.AuthRoleList != nil {
+		l = m.AuthRoleList.Size()
+		n += 2 + l + sovRaftInternal(uint64(l))
+	}
 	if m.AuthRoleAdd != nil {
 		l = m.AuthRoleAdd.Size()
 		n += 2 + l + sovRaftInternal(uint64(l))
@@ -1427,6 +1461,72 @@ func (m *InternalRaftRequest) Unmarshal(data []byte) error {
 				return err
 			}
 			iNdEx = postIndex
+		case 1106:
+			if wireType != 2 {
+				return fmt.Errorf("proto: wrong wireType = %d for field AuthUserList", wireType)
+			}
+			var msglen int
+			for shift := uint(0); ; shift += 7 {
+				if shift >= 64 {
+					return ErrIntOverflowRaftInternal
+				}
+				if iNdEx >= l {
+					return io.ErrUnexpectedEOF
+				}
+				b := data[iNdEx]
+				iNdEx++
+				msglen |= (int(b) & 0x7F) << shift
+				if b < 0x80 {
+					break
+				}
+			}
+			if msglen < 0 {
+				return ErrInvalidLengthRaftInternal
+			}
+			postIndex := iNdEx + msglen
+			if postIndex > l {
+				return io.ErrUnexpectedEOF
+			}
+			if m.AuthUserList == nil {
+				m.AuthUserList = &AuthUserListRequest{}
+			}
+			if err := m.AuthUserList.Unmarshal(data[iNdEx:postIndex]); err != nil {
+				return err
+			}
+			iNdEx = postIndex
+		case 1107:
+			if wireType != 2 {
+				return fmt.Errorf("proto: wrong wireType = %d for field AuthRoleList", wireType)
+			}
+			var msglen int
+			for shift := uint(0); ; shift += 7 {
+				if shift >= 64 {
+					return ErrIntOverflowRaftInternal
+				}
+				if iNdEx >= l {
+					return io.ErrUnexpectedEOF
+				}
+				b := data[iNdEx]
+				iNdEx++
+				msglen |= (int(b) & 0x7F) << shift
+				if b < 0x80 {
+					break
+				}
+			}
+			if msglen < 0 {
+				return ErrInvalidLengthRaftInternal
+			}
+			postIndex := iNdEx + msglen
+			if postIndex > l {
+				return io.ErrUnexpectedEOF
+			}
+			if m.AuthRoleList == nil {
+				m.AuthRoleList = &AuthRoleListRequest{}
+			}
+			if err := m.AuthRoleList.Unmarshal(data[iNdEx:postIndex]); err != nil {
+				return err
+			}
+			iNdEx = postIndex
 		case 1200:
 			if wireType != 2 {
 				return fmt.Errorf("proto: wrong wireType = %d for field AuthRoleAdd", wireType)
@@ -1906,54 +2006,56 @@ var (
 )
 
 var fileDescriptorRaftInternal = []byte{
-	// 770 bytes of a gzipped FileDescriptorProto
-	0x1f, 0x8b, 0x08, 0x00, 0x00, 0x09, 0x6e, 0x88, 0x02, 0xff, 0x7c, 0x95, 0x4b, 0x6f, 0x13, 0x3b,
-	0x14, 0xc7, 0x6f, 0xd2, 0x67, 0x9c, 0xa4, 0xb7, 0xd7, 0x6d, 0x2f, 0x26, 0x95, 0x4a, 0x09, 0xe2,
-	0x0d, 0x05, 0xb5, 0x4b, 0x16, 0x10, 0x9a, 0xaa, 0x54, 0x42, 0xa8, 0x1a, 0x15, 0x09, 0x89, 0xc5,
-	0xc8, 0xcd, 0x98, 0x74, 0x60, 0x5e, 0x78, 0x9c, 0x52, 0xbe, 0x15, 0xaf, 0x0f, 0xd1, 0x05, 0x8f,
-	0xb2, 0x65, 0x05, 0xac, 0xd8, 0xc3, 0x07, 0xc0, 0xaf, 0xf1, 0xcc, 0x24, 0x4e, 0x17, 0x91, 0x66,
-	0xce, 0xf9, 0x9f, 0xdf, 0x39, 0x9e, 0xbf, 0x1d, 0x83, 0x05, 0x8a, 0x9f, 0x31, 0xd7, 0x8f, 0x18,
-	0xa1, 0x11, 0x0e, 0xd6, 0x12, 0x1a, 0xb3, 0x18, 0x36, 0x08, 0xeb, 0x79, 0x29, 0xa1, 0x87, 0x84,
-	0x26, 0xfb, 0xad, 0xc5, 0x7e, 0xdc, 0x8f, 0x65, 0xe2, 0x96, 0x78, 0x52, 0x9a, 0xd6, 0x7c, 0xae,
-	0xd1, 0x91, 0x1a, 0x4d, 0x7a, 0xea, 0xb1, 0x7d, 0x07, 0x34, 0x1d, 0xf2, 0x72, 0x40, 0x52, 0xf6,
-	0x80, 0x60, 0x8f, 0x50, 0x38, 0x07, 0xaa, 0x3b, 0x5d, 0x54, 0x59, 0xad, 0x5c, 0x99, 0x74, 0xaa,
-	0x7e, 0x17, 0xb6, 0xc0, 0xec, 0x20, 0x15, 0x2d, 0x43, 0x82, 0xaa, 0x3c, 0x5a, 0x73, 0xcc, 0x7b,
-	0xfb, 0x5b, 0x13, 0x2c, 0xec, 0xe8, 0x81, 0x1c, 0x3e, 0x9d, 0x26, 0x8d, 0x30, 0x2e, 0x82, 0xea,
-	0xe1, 0xba, 0xac, 0xae, 0xaf, 0x2f, 0xad, 0x15, 0x47, 0x5e, 0xd3, 0x25, 0x0e, 0x17, 0xc0, 0xdb,
-	0x60, 0x8a, 0xe2, 0xa8, 0x4f, 0xd0, 0x84, 0x54, 0xb6, 0x86, 0x94, 0x22, 0x95, 0xc9, 0x95, 0x10,
-	0x5e, 0x03, 0x13, 0xc9, 0x80, 0xa1, 0x49, 0xa9, 0x47, 0x65, 0xfd, 0xee, 0x20, 0x9b, 0xc7, 0x11,
-	0x22, 0xb8, 0x09, 0x1a, 0x1e, 0x09, 0x08, 0x23, 0xae, 0x6a, 0x32, 0x25, 0x8b, 0x56, 0xcb, 0x45,
-	0x5d, 0xa9, 0x28, 0xb5, 0xaa, 0x7b, 0x79, 0x4c, 0x34, 0x64, 0x47, 0x11, 0x9a, 0xb6, 0x35, 0xdc,
-	0x3b, 0x8a, 0x4c, 0x43, 0x2e, 0x82, 0x77, 0x01, 0xe8, 0xc5, 0x61, 0x82, 0x7b, 0xcc, 0x8f, 0x23,
-	0x34, 0x23, 0x4b, 0xce, 0x95, 0x4b, 0x36, 0x4d, 0x3e, 0xab, 0x2c, 0x94, 0xc0, 0x7b, 0xa0, 0x1e,
-	0x10, 0x9c, 0x12, 0xb7, 0xcf, 0x27, 0x66, 0x68, 0xd6, 0x46, 0x78, 0x28, 0x04, 0xdb, 0x22, 0x6f,
-	0x08, 0x81, 0x09, 0x89, 0x35, 0x2b, 0x02, 0x25, 0x87, 0xf1, 0x0b, 0x82, 0x6a, 0xb6, 0x35, 0x4b,
-	0x84, 0x23, 0x05, 0x66, 0xcd, 0x41, 0x1e, 0x13, 0xb6, 0xe0, 0x00, 0xd3, 0x10, 0x01, 0x9b, 0x2d,
-	0x1d, 0x91, 0x32, 0xb6, 0x48, 0x21, 0xdc, 0x00, 0xd3, 0x07, 0x72, 0x37, 0x21, 0x4f, 0x96, 0x2c,
-	0x5b, 0x3d, 0x57, 0x1b, 0xce, 0xd1, 0x52, 0xd8, 0x01, 0x75, 0x3c, 0x60, 0x07, 0x2e, 0x89, 0xf0,
-	0x7e, 0x40, 0xd0, 0x2f, 0xeb, 0x07, 0xeb, 0x70, 0xc5, 0x96, 0x14, 0x98, 0xe5, 0x62, 0x13, 0x82,
-	0x5d, 0xd0, 0x90, 0x08, 0xcf, 0x4f, 0x25, 0xe3, 0xf7, 0x8c, 0x6d, 0xbd, 0x82, 0xd1, 0x55, 0x0a,
-	0xb3, 0x5e, 0x9c, 0xc7, 0xe0, 0x23, 0x45, 0x21, 0x11, 0xf3, 0x7b, 0x98, 0x11, 0xf4, 0x47, 0x51,
-	0xae, 0x96, 0x29, 0xd9, 0xbe, 0xef, 0x14, 0xa4, 0x19, 0xae, 0x54, 0x0f, 0xb7, 0x40, 0x53, 0x4e,
-	0x25, 0x8e, 0x8d, 0x8b, 0x3d, 0x0f, 0x7d, 0x9c, 0x1d, 0x37, 0xd6, 0x63, 0xfe, 0xd6, 0xf1, 0xbc,
-	0xd2, 0x58, 0x3a, 0xc6, 0xc7, 0x9a, 0xcf, 0x31, 0x6a, 0x4f, 0xa2, 0x4f, 0x8a, 0x74, 0xc1, 0x4e,
-	0xd2, 0x9b, 0x59, 0xc3, 0xe6, 0x70, 0x29, 0x5c, 0x1e, 0xab, 0x4f, 0x18, 0xfa, 0x7c, 0xea, 0x58,
-	0xdb, 0x84, 0x8d, 0x8c, 0xc5, 0x63, 0xb0, 0x0f, 0xce, 0xe6, 0x98, 0xde, 0x81, 0x38, 0x25, 0x6e,
-	0x82, 0xd3, 0xf4, 0x55, 0x4c, 0x3d, 0xf4, 0x45, 0x21, 0xaf, 0xdb, 0x91, 0x9b, 0x52, 0xbd, 0xab,
-	0xc5, 0x19, 0xfd, 0x7f, 0x6c, 0x4d, 0xc3, 0x27, 0x60, 0xb1, 0x30, 0xaf, 0xd8, 0xde, 0x2e, 0x8d,
-	0xb9, 0xc9, 0x27, 0xaa, 0xc7, 0xa5, 0x31, 0x63, 0xcb, 0xa3, 0x11, 0xe7, 0x56, 0xff, 0x87, 0x87,
-	0x33, 0xf0, 0x29, 0x58, 0xca, 0xc9, 0xea, 0xa4, 0x28, 0xf4, 0x57, 0x85, 0xbe, 0x6c, 0x47, 0xeb,
-	0x23, 0x53, 0x60, 0x43, 0x3c, 0x92, 0x32, 0x9f, 0x59, 0x00, 0xa5, 0xfb, 0x6f, 0x6a, 0xe3, 0x3e,
-	0xb3, 0xd0, 0x0f, 0xbb, 0xaf, 0x63, 0xc6, 0x7d, 0x89, 0xd1, 0xee, 0xbf, 0xad, 0x8d, 0x73, 0x5f,
-	0x54, 0x59, 0xdc, 0xcf, 0xc3, 0xe5, 0xb1, 0x84, 0xfb, 0xef, 0x4e, 0x1d, 0x6b, 0xd8, 0x7d, 0x1d,
-	0x83, 0xcf, 0x41, 0xab, 0x80, 0x91, 0xa6, 0x24, 0x84, 0x86, 0x7e, 0x9a, 0x8a, 0xff, 0xbc, 0xf7,
-	0x8a, 0x79, 0x63, 0x0c, 0x53, 0xc8, 0x77, 0x8d, 0x3a, 0xe3, 0x9f, 0xc1, 0xf6, 0x3c, 0x0c, 0xc1,
-	0x72, 0xde, 0x4b, 0xdb, 0x54, 0x68, 0xf6, 0x41, 0x35, 0xbb, 0x69, 0x6f, 0xa6, 0x1c, 0x19, 0xed,
-	0x86, 0xf0, 0x18, 0x41, 0xfb, 0x5f, 0xd0, 0xdc, 0x0a, 0x13, 0xf6, 0xda, 0x21, 0x69, 0x12, 0x47,
-	0x29, 0x69, 0x27, 0x60, 0xf9, 0x94, 0x43, 0x0f, 0x21, 0x98, 0x94, 0x97, 0x64, 0x45, 0x5e, 0x92,
-	0xf2, 0x59, 0x5c, 0x9e, 0xe6, 0x2c, 0xe8, 0xcb, 0x33, 0x7b, 0x87, 0xe7, 0x41, 0x23, 0xf5, 0xc3,
-	0x84, 0xaf, 0x85, 0xf1, 0xc6, 0x91, 0xbc, 0xf4, 0x6a, 0x4e, 0x5d, 0xc5, 0xf6, 0x44, 0xe8, 0xfe,
-	0xfc, 0xf1, 0x8f, 0x95, 0x7f, 0x8e, 0x7f, 0xae, 0x54, 0x4e, 0xf8, 0xef, 0x3b, 0xff, 0xed, 0x4f,
-	0xcb, 0x5b, 0x7b, 0xe3, 0x6f, 0x00, 0x00, 0x00, 0xff, 0xff, 0xa6, 0x96, 0x31, 0x96, 0x0d, 0x08,
-	0x00, 0x00,
+	// 808 bytes of a gzipped FileDescriptorProto
+	0x1f, 0x8b, 0x08, 0x00, 0x00, 0x09, 0x6e, 0x88, 0x02, 0xff, 0x7c, 0x96, 0x4b, 0x6f, 0xd3, 0x4a,
+	0x14, 0xc7, 0x6f, 0xd2, 0x67, 0x26, 0x69, 0x6e, 0xef, 0xb4, 0xbd, 0x77, 0x6e, 0x2a, 0x95, 0x36,
+	0x88, 0x37, 0x14, 0xd4, 0x2e, 0x59, 0x40, 0x68, 0xaa, 0xb6, 0x52, 0x85, 0x2a, 0xab, 0x48, 0x48,
+	0x2c, 0xac, 0x69, 0x3c, 0xa4, 0x06, 0xbf, 0xb0, 0x27, 0xa5, 0x7c, 0x2b, 0x5e, 0x1f, 0xa2, 0x0b,
+	0x1e, 0x05, 0xbe, 0x00, 0xb0, 0x62, 0xc5, 0x06, 0x3e, 0x00, 0xf3, 0xf2, 0xd8, 0x4e, 0xc6, 0x5d,
+	0x44, 0xb2, 0xcf, 0xf9, 0x9f, 0xdf, 0x39, 0xd3, 0xf9, 0x8f, 0xa7, 0x60, 0x2e, 0xc6, 0x8f, 0xa9,
+	0xed, 0x06, 0x94, 0xc4, 0x01, 0xf6, 0x56, 0xa3, 0x38, 0xa4, 0x21, 0x6c, 0x10, 0xda, 0x73, 0x12,
+	0x12, 0x1f, 0x91, 0x38, 0x3a, 0x68, 0xcd, 0xf7, 0xc3, 0x7e, 0x28, 0x12, 0x37, 0xf9, 0x93, 0xd4,
+	0xb4, 0x66, 0x33, 0x8d, 0x8a, 0xd4, 0xe2, 0xa8, 0x27, 0x1f, 0xdb, 0xb7, 0xc1, 0x8c, 0x45, 0x9e,
+	0x0d, 0x48, 0x42, 0xb7, 0x09, 0x76, 0x48, 0x0c, 0x9b, 0xa0, 0xba, 0xd3, 0x45, 0x95, 0xe5, 0xca,
+	0xe5, 0x71, 0xab, 0xea, 0x76, 0x61, 0x0b, 0x4c, 0x0f, 0x12, 0xde, 0xd2, 0x27, 0xa8, 0xca, 0xa2,
+	0x35, 0x4b, 0xbf, 0xb7, 0x7f, 0x36, 0xc1, 0xdc, 0x8e, 0x1a, 0xc8, 0x62, 0xd3, 0x29, 0xd2, 0x08,
+	0xe3, 0x02, 0xa8, 0x1e, 0xad, 0x89, 0xea, 0xfa, 0xda, 0xc2, 0x6a, 0x7e, 0xe4, 0x55, 0x55, 0x62,
+	0x31, 0x01, 0xbc, 0x05, 0x26, 0x62, 0x1c, 0xf4, 0x09, 0x1a, 0x13, 0xca, 0xd6, 0x90, 0x92, 0xa7,
+	0x52, 0xb9, 0x14, 0xc2, 0xab, 0x60, 0x2c, 0x1a, 0x50, 0x34, 0x2e, 0xf4, 0xa8, 0xa8, 0xdf, 0x1b,
+	0xa4, 0xf3, 0x58, 0x5c, 0x04, 0x37, 0x40, 0xc3, 0x21, 0x1e, 0xa1, 0xc4, 0x96, 0x4d, 0x26, 0x44,
+	0xd1, 0x72, 0xb1, 0xa8, 0x2b, 0x14, 0x85, 0x56, 0x75, 0x27, 0x8b, 0xf1, 0x86, 0xf4, 0x38, 0x40,
+	0x93, 0xa6, 0x86, 0xfb, 0xc7, 0x81, 0x6e, 0xc8, 0x44, 0xf0, 0x0e, 0x00, 0xbd, 0xd0, 0x8f, 0x70,
+	0x8f, 0xba, 0x61, 0x80, 0xa6, 0x44, 0xc9, 0xb9, 0x62, 0xc9, 0x86, 0xce, 0xa7, 0x95, 0xb9, 0x12,
+	0x78, 0x17, 0xd4, 0x3d, 0x82, 0x13, 0x62, 0xf7, 0xd9, 0xc4, 0x14, 0x4d, 0x9b, 0x08, 0xbb, 0x5c,
+	0xb0, 0xc5, 0xf3, 0x9a, 0xe0, 0xe9, 0x10, 0x5f, 0xb3, 0x24, 0xc4, 0xe4, 0x28, 0x7c, 0x4a, 0x50,
+	0xcd, 0xb4, 0x66, 0x81, 0xb0, 0x84, 0x40, 0xaf, 0xd9, 0xcb, 0x62, 0x7c, 0x5b, 0xb0, 0x87, 0x63,
+	0x1f, 0x01, 0xd3, 0xb6, 0x74, 0x78, 0x4a, 0x6f, 0x8b, 0x10, 0xc2, 0x75, 0x30, 0x79, 0x28, 0xdc,
+	0x84, 0x1c, 0x51, 0xb2, 0x68, 0xdc, 0x73, 0x69, 0x38, 0x4b, 0x49, 0x61, 0x07, 0xd4, 0xf1, 0x80,
+	0x1e, 0xda, 0x24, 0xc0, 0x07, 0x1e, 0x41, 0x3f, 0x8c, 0x7f, 0xb0, 0x0e, 0x53, 0x6c, 0x0a, 0x81,
+	0x5e, 0x2e, 0xd6, 0x21, 0xd8, 0x05, 0x0d, 0x81, 0x70, 0xdc, 0x44, 0x30, 0x7e, 0x4d, 0x99, 0xd6,
+	0xcb, 0x19, 0x5d, 0xa9, 0xd0, 0xeb, 0xc5, 0x59, 0x0c, 0xde, 0x97, 0x14, 0x12, 0x50, 0xb7, 0x87,
+	0x29, 0x41, 0xbf, 0x25, 0xe5, 0x4a, 0x91, 0x92, 0xfa, 0xbe, 0x93, 0x93, 0xa6, 0xb8, 0x42, 0x3d,
+	0xdc, 0x04, 0x33, 0x62, 0x2a, 0x7e, 0x6c, 0x6c, 0xec, 0x38, 0xe8, 0xdd, 0x74, 0xd9, 0x58, 0x0f,
+	0xd8, 0x5b, 0xc7, 0x71, 0x0a, 0x63, 0xa9, 0x18, 0x1b, 0x6b, 0x36, 0xc3, 0x48, 0x4f, 0xa2, 0xf7,
+	0x92, 0x74, 0xde, 0x4c, 0x52, 0x66, 0x56, 0xb0, 0x26, 0x2e, 0x84, 0x8b, 0x63, 0xf5, 0x09, 0x45,
+	0x1f, 0xce, 0x1c, 0x6b, 0x8b, 0xd0, 0x91, 0xb1, 0x58, 0x0c, 0xf6, 0xc1, 0xff, 0x19, 0xa6, 0x77,
+	0xc8, 0x4f, 0x89, 0x1d, 0xe1, 0x24, 0x79, 0x1e, 0xc6, 0x0e, 0xfa, 0x28, 0x91, 0xd7, 0xcc, 0xc8,
+	0x0d, 0xa1, 0xde, 0x53, 0xe2, 0x94, 0xfe, 0x2f, 0x36, 0xa6, 0xe1, 0x43, 0x30, 0x9f, 0x9b, 0x97,
+	0xdb, 0xdb, 0x8e, 0x43, 0xb6, 0xc9, 0xa7, 0xb2, 0xc7, 0xc5, 0x92, 0xb1, 0xc5, 0xd1, 0x08, 0xb3,
+	0xad, 0xfe, 0x07, 0x0f, 0x67, 0xe0, 0x23, 0xb0, 0x90, 0x91, 0xe5, 0x49, 0x91, 0xe8, 0x4f, 0x12,
+	0x7d, 0xc9, 0x8c, 0x56, 0x47, 0x26, 0xc7, 0x86, 0x78, 0x24, 0x05, 0xb7, 0x41, 0x33, 0x83, 0x7b,
+	0x6e, 0x42, 0xd1, 0x67, 0x49, 0x5d, 0x31, 0x53, 0x77, 0x99, 0xa4, 0xe0, 0xa3, 0x34, 0xa8, 0x49,
+	0x7c, 0x34, 0x49, 0xfa, 0x52, 0x4a, 0xe2, 0xad, 0x47, 0x48, 0x69, 0x50, 0x6f, 0xbd, 0x20, 0x71,
+	0x47, 0xbe, 0xac, 0x95, 0x6d, 0x3d, 0xaf, 0x19, 0x76, 0xa4, 0x8a, 0x69, 0x47, 0x0a, 0x8c, 0x72,
+	0xe4, 0xab, 0x5a, 0x99, 0x23, 0x79, 0x95, 0xc1, 0x91, 0x59, 0xb8, 0x38, 0x16, 0x77, 0xe4, 0xeb,
+	0x33, 0xc7, 0x1a, 0x76, 0xa4, 0x8a, 0xc1, 0x27, 0xa0, 0x95, 0xc3, 0x08, 0xa3, 0x44, 0x24, 0xf6,
+	0xdd, 0x24, 0xe1, 0xdf, 0xe1, 0x37, 0x92, 0x79, 0xbd, 0x84, 0xc9, 0xe5, 0x7b, 0x5a, 0x9d, 0xf2,
+	0xff, 0xc3, 0xe6, 0x3c, 0xf4, 0xc1, 0x62, 0xd6, 0x4b, 0x59, 0x27, 0xd7, 0xec, 0xad, 0x6c, 0x76,
+	0xc3, 0xdc, 0x4c, 0xba, 0x64, 0xb4, 0x1b, 0xc2, 0x25, 0x82, 0xf6, 0xdf, 0x60, 0x66, 0xd3, 0x8f,
+	0xe8, 0x0b, 0x8b, 0x24, 0x51, 0x18, 0x24, 0xa4, 0x1d, 0x81, 0xc5, 0x33, 0x3e, 0x44, 0x10, 0x82,
+	0x71, 0x71, 0x71, 0x57, 0xc4, 0xc5, 0x2d, 0x9e, 0xf9, 0x85, 0xae, 0xcf, 0xa7, 0xba, 0xd0, 0xd3,
+	0x77, 0xb8, 0x02, 0x1a, 0x89, 0xeb, 0x47, 0x6c, 0x2d, 0x94, 0x35, 0x0e, 0xc4, 0x45, 0x5c, 0xb3,
+	0xea, 0x32, 0xb6, 0xcf, 0x43, 0xf7, 0x66, 0x4f, 0xbe, 0x2d, 0xfd, 0x75, 0xf2, 0x7d, 0xa9, 0x72,
+	0xca, 0x7e, 0x5f, 0xd9, 0xef, 0x60, 0x52, 0xfc, 0x27, 0xb1, 0xfe, 0x27, 0x00, 0x00, 0xff, 0xff,
+	0xdc, 0xb1, 0xbb, 0xb7, 0xa1, 0x08, 0x00, 0x00,
 }

+ 2 - 0
etcdserver/etcdserverpb/raft_internal.proto

@@ -46,6 +46,8 @@ message InternalRaftRequest {
   AuthUserChangePasswordRequest auth_user_change_password = 1103;
   AuthUserGrantRoleRequest auth_user_grant_role = 1104;
   AuthUserRevokeRoleRequest auth_user_revoke_role = 1105;
+  AuthUserListRequest auth_user_list = 1106;
+  AuthRoleListRequest auth_role_list = 1107;
 
   AuthRoleAddRequest auth_role_add = 1200;
   AuthRoleDeleteRequest auth_role_delete = 1201;

File diff suppressed because it is too large
+ 664 - 50
etcdserver/etcdserverpb/rpc.pb.go


+ 90 - 0
etcdserver/etcdserverpb/rpc.pb.gw.go

@@ -387,6 +387,19 @@ func request_Auth_UserGet_0(ctx context.Context, marshaler runtime.Marshaler, cl
 
 }
 
+func request_Auth_UserList_0(ctx context.Context, marshaler runtime.Marshaler, client AuthClient, req *http.Request, pathParams map[string]string) (proto.Message, runtime.ServerMetadata, error) {
+	var protoReq AuthUserListRequest
+	var metadata runtime.ServerMetadata
+
+	if err := marshaler.NewDecoder(req.Body).Decode(&protoReq); err != nil {
+		return nil, metadata, grpc.Errorf(codes.InvalidArgument, "%v", err)
+	}
+
+	msg, err := client.UserList(ctx, &protoReq, grpc.Header(&metadata.HeaderMD), grpc.Trailer(&metadata.TrailerMD))
+	return msg, metadata, err
+
+}
+
 func request_Auth_UserDelete_0(ctx context.Context, marshaler runtime.Marshaler, client AuthClient, req *http.Request, pathParams map[string]string) (proto.Message, runtime.ServerMetadata, error) {
 	var protoReq AuthUserDeleteRequest
 	var metadata runtime.ServerMetadata
@@ -465,6 +478,19 @@ func request_Auth_RoleGet_0(ctx context.Context, marshaler runtime.Marshaler, cl
 
 }
 
+func request_Auth_RoleList_0(ctx context.Context, marshaler runtime.Marshaler, client AuthClient, req *http.Request, pathParams map[string]string) (proto.Message, runtime.ServerMetadata, error) {
+	var protoReq AuthRoleListRequest
+	var metadata runtime.ServerMetadata
+
+	if err := marshaler.NewDecoder(req.Body).Decode(&protoReq); err != nil {
+		return nil, metadata, grpc.Errorf(codes.InvalidArgument, "%v", err)
+	}
+
+	msg, err := client.RoleList(ctx, &protoReq, grpc.Header(&metadata.HeaderMD), grpc.Trailer(&metadata.TrailerMD))
+	return msg, metadata, err
+
+}
+
 func request_Auth_RoleDelete_0(ctx context.Context, marshaler runtime.Marshaler, client AuthClient, req *http.Request, pathParams map[string]string) (proto.Message, runtime.ServerMetadata, error) {
 	var protoReq AuthRoleDeleteRequest
 	var metadata runtime.ServerMetadata
@@ -1403,6 +1429,34 @@ func RegisterAuthHandler(ctx context.Context, mux *runtime.ServeMux, conn *grpc.
 
 	})
 
+	mux.Handle("POST", pattern_Auth_UserList_0, func(w http.ResponseWriter, req *http.Request, pathParams map[string]string) {
+		ctx, cancel := context.WithCancel(ctx)
+		defer cancel()
+		if cn, ok := w.(http.CloseNotifier); ok {
+			go func(done <-chan struct{}, closed <-chan bool) {
+				select {
+				case <-done:
+				case <-closed:
+					cancel()
+				}
+			}(ctx.Done(), cn.CloseNotify())
+		}
+		inboundMarshaler, outboundMarshaler := runtime.MarshalerForRequest(mux, req)
+		rctx, err := runtime.AnnotateContext(ctx, req)
+		if err != nil {
+			runtime.HTTPError(ctx, outboundMarshaler, w, req, err)
+		}
+		resp, md, err := request_Auth_UserList_0(rctx, inboundMarshaler, client, req, pathParams)
+		ctx = runtime.NewServerMetadataContext(ctx, md)
+		if err != nil {
+			runtime.HTTPError(ctx, outboundMarshaler, w, req, err)
+			return
+		}
+
+		forward_Auth_UserList_0(ctx, outboundMarshaler, w, req, resp, mux.GetForwardResponseOptions()...)
+
+	})
+
 	mux.Handle("POST", pattern_Auth_UserDelete_0, func(w http.ResponseWriter, req *http.Request, pathParams map[string]string) {
 		ctx, cancel := context.WithCancel(ctx)
 		defer cancel()
@@ -1571,6 +1625,34 @@ func RegisterAuthHandler(ctx context.Context, mux *runtime.ServeMux, conn *grpc.
 
 	})
 
+	mux.Handle("POST", pattern_Auth_RoleList_0, func(w http.ResponseWriter, req *http.Request, pathParams map[string]string) {
+		ctx, cancel := context.WithCancel(ctx)
+		defer cancel()
+		if cn, ok := w.(http.CloseNotifier); ok {
+			go func(done <-chan struct{}, closed <-chan bool) {
+				select {
+				case <-done:
+				case <-closed:
+					cancel()
+				}
+			}(ctx.Done(), cn.CloseNotify())
+		}
+		inboundMarshaler, outboundMarshaler := runtime.MarshalerForRequest(mux, req)
+		rctx, err := runtime.AnnotateContext(ctx, req)
+		if err != nil {
+			runtime.HTTPError(ctx, outboundMarshaler, w, req, err)
+		}
+		resp, md, err := request_Auth_RoleList_0(rctx, inboundMarshaler, client, req, pathParams)
+		ctx = runtime.NewServerMetadataContext(ctx, md)
+		if err != nil {
+			runtime.HTTPError(ctx, outboundMarshaler, w, req, err)
+			return
+		}
+
+		forward_Auth_RoleList_0(ctx, outboundMarshaler, w, req, resp, mux.GetForwardResponseOptions()...)
+
+	})
+
 	mux.Handle("POST", pattern_Auth_RoleDelete_0, func(w http.ResponseWriter, req *http.Request, pathParams map[string]string) {
 		ctx, cancel := context.WithCancel(ctx)
 		defer cancel()
@@ -1669,6 +1751,8 @@ var (
 
 	pattern_Auth_UserGet_0 = runtime.MustPattern(runtime.NewPattern(1, []int{2, 0, 2, 1, 2, 2, 2, 3}, []string{"v3alpha", "auth", "user", "get"}, ""))
 
+	pattern_Auth_UserList_0 = runtime.MustPattern(runtime.NewPattern(1, []int{2, 0, 2, 1, 2, 2, 2, 3}, []string{"v3alpha", "auth", "user", "list"}, ""))
+
 	pattern_Auth_UserDelete_0 = runtime.MustPattern(runtime.NewPattern(1, []int{2, 0, 2, 1, 2, 2, 2, 3}, []string{"v3alpha", "auth", "user", "delete"}, ""))
 
 	pattern_Auth_UserChangePassword_0 = runtime.MustPattern(runtime.NewPattern(1, []int{2, 0, 2, 1, 2, 2, 2, 3}, []string{"v3alpha", "auth", "user", "changepw"}, ""))
@@ -1681,6 +1765,8 @@ var (
 
 	pattern_Auth_RoleGet_0 = runtime.MustPattern(runtime.NewPattern(1, []int{2, 0, 2, 1, 2, 2, 2, 3}, []string{"v3alpha", "auth", "role", "get"}, ""))
 
+	pattern_Auth_RoleList_0 = runtime.MustPattern(runtime.NewPattern(1, []int{2, 0, 2, 1, 2, 2, 2, 3}, []string{"v3alpha", "auth", "role", "list"}, ""))
+
 	pattern_Auth_RoleDelete_0 = runtime.MustPattern(runtime.NewPattern(1, []int{2, 0, 2, 1, 2, 2, 2, 3}, []string{"v3alpha", "auth", "role", "delete"}, ""))
 
 	pattern_Auth_RoleGrantPermission_0 = runtime.MustPattern(runtime.NewPattern(1, []int{2, 0, 2, 1, 2, 2, 2, 3}, []string{"v3alpha", "auth", "role", "grant"}, ""))
@@ -1699,6 +1785,8 @@ var (
 
 	forward_Auth_UserGet_0 = runtime.ForwardResponseMessage
 
+	forward_Auth_UserList_0 = runtime.ForwardResponseMessage
+
 	forward_Auth_UserDelete_0 = runtime.ForwardResponseMessage
 
 	forward_Auth_UserChangePassword_0 = runtime.ForwardResponseMessage
@@ -1711,6 +1799,8 @@ var (
 
 	forward_Auth_RoleGet_0 = runtime.ForwardResponseMessage
 
+	forward_Auth_RoleList_0 = runtime.ForwardResponseMessage
+
 	forward_Auth_RoleDelete_0 = runtime.ForwardResponseMessage
 
 	forward_Auth_RoleGrantPermission_0 = runtime.ForwardResponseMessage

+ 36 - 2
etcdserver/etcdserverpb/rpc.proto

@@ -214,7 +214,7 @@ service Auth {
     };
   }
 
-  // UserGet gets detailed user information or lists all users.
+  // UserGet gets detailed user information.
   rpc UserGet(AuthUserGetRequest) returns (AuthUserGetResponse) {
       option (google.api.http) = {
         post: "/v3alpha/auth/user/get"
@@ -222,6 +222,14 @@ service Auth {
     };
   }
 
+  // UserList gets a list of all users.
+  rpc UserList(AuthUserListRequest) returns (AuthUserListResponse) {
+      option (google.api.http) = {
+        post: "/v3alpha/auth/user/list"
+        body: "*"
+    };
+  }
+
   // UserDelete deletes a specified user.
   rpc UserDelete(AuthUserDeleteRequest) returns (AuthUserDeleteResponse) {
       option (google.api.http) = {
@@ -262,7 +270,7 @@ service Auth {
     };
   }
 
-  // RoleGet gets detailed role information or lists all roles.
+  // RoleGet gets detailed role information.
   rpc RoleGet(AuthRoleGetRequest) returns (AuthRoleGetResponse) {
       option (google.api.http) = {
         post: "/v3alpha/auth/role/get"
@@ -270,6 +278,14 @@ service Auth {
     };
   }
 
+  // RoleList gets lists of all roles.
+  rpc RoleList(AuthRoleListRequest) returns (AuthRoleListResponse) {
+      option (google.api.http) = {
+        post: "/v3alpha/auth/role/list"
+        body: "*"
+    };
+  }
+
   // RoleDelete deletes a specified role.
   rpc RoleDelete(AuthRoleDeleteRequest) returns (AuthRoleDeleteResponse) {
       option (google.api.http) = {
@@ -766,6 +782,12 @@ message AuthRoleGetRequest {
   string role = 1;
 }
 
+message AuthUserListRequest {
+}
+
+message AuthRoleListRequest {
+}
+
 message AuthRoleDeleteRequest {
   string role = 1;
 }
@@ -833,6 +855,18 @@ message AuthRoleGetResponse {
   repeated authpb.Permission perm = 2;
 }
 
+message AuthRoleListResponse {
+  ResponseHeader header = 1;
+
+  repeated string roles = 2;
+}
+
+message AuthUserListResponse {
+  ResponseHeader header = 1;
+
+  repeated string users = 2;
+}
+
 message AuthRoleDeleteResponse {
   ResponseHeader header = 1;
 }

+ 24 - 0
etcdserver/v3_server.go

@@ -72,6 +72,8 @@ type Authenticator interface {
 	RoleGet(ctx context.Context, r *pb.AuthRoleGetRequest) (*pb.AuthRoleGetResponse, error)
 	RoleRevokePermission(ctx context.Context, r *pb.AuthRoleRevokePermissionRequest) (*pb.AuthRoleRevokePermissionResponse, error)
 	RoleDelete(ctx context.Context, r *pb.AuthRoleDeleteRequest) (*pb.AuthRoleDeleteResponse, error)
+	UserList(ctx context.Context, r *pb.AuthUserListRequest) (*pb.AuthUserListResponse, error)
+	RoleList(ctx context.Context, r *pb.AuthRoleListRequest) (*pb.AuthRoleListResponse, error)
 }
 
 func (s *EtcdServer) Range(ctx context.Context, r *pb.RangeRequest) (*pb.RangeResponse, error) {
@@ -350,6 +352,17 @@ func (s *EtcdServer) UserGet(ctx context.Context, r *pb.AuthUserGetRequest) (*pb
 	return result.resp.(*pb.AuthUserGetResponse), nil
 }
 
+func (s *EtcdServer) UserList(ctx context.Context, r *pb.AuthUserListRequest) (*pb.AuthUserListResponse, error) {
+	result, err := s.processInternalRaftRequest(ctx, pb.InternalRaftRequest{AuthUserList: r})
+	if err != nil {
+		return nil, err
+	}
+	if result.err != nil {
+		return nil, result.err
+	}
+	return result.resp.(*pb.AuthUserListResponse), nil
+}
+
 func (s *EtcdServer) UserRevokeRole(ctx context.Context, r *pb.AuthUserRevokeRoleRequest) (*pb.AuthUserRevokeRoleResponse, error) {
 	result, err := s.processInternalRaftRequest(ctx, pb.InternalRaftRequest{AuthUserRevokeRole: r})
 	if err != nil {
@@ -394,6 +407,17 @@ func (s *EtcdServer) RoleGet(ctx context.Context, r *pb.AuthRoleGetRequest) (*pb
 	return result.resp.(*pb.AuthRoleGetResponse), nil
 }
 
+func (s *EtcdServer) RoleList(ctx context.Context, r *pb.AuthRoleListRequest) (*pb.AuthRoleListResponse, error) {
+	result, err := s.processInternalRaftRequest(ctx, pb.InternalRaftRequest{AuthRoleList: r})
+	if err != nil {
+		return nil, err
+	}
+	if result.err != nil {
+		return nil, result.err
+	}
+	return result.resp.(*pb.AuthRoleListResponse), nil
+}
+
 func (s *EtcdServer) RoleRevokePermission(ctx context.Context, r *pb.AuthRoleRevokePermissionRequest) (*pb.AuthRoleRevokePermissionResponse, error) {
 	result, err := s.processInternalRaftRequest(ctx, pb.InternalRaftRequest{AuthRoleRevokePermission: r})
 	if err != nil {

Some files were not shown because too many files changed in this diff