mirror of
https://github.com/etcd-io/etcd.git
synced 2024-09-27 06:25:44 +00:00
auth, etcdserver: authenticate clients based on certificate CommonName
This commit lets v3 auth mechanism authenticate clients based on CommonName of certificate like v2 auth.
This commit is contained in:
parent
7d6280fa82
commit
0191509637
@ -30,7 +30,9 @@ import (
|
||||
"github.com/coreos/pkg/capnslog"
|
||||
"golang.org/x/crypto/bcrypt"
|
||||
"golang.org/x/net/context"
|
||||
"google.golang.org/grpc/credentials"
|
||||
"google.golang.org/grpc/metadata"
|
||||
"google.golang.org/grpc/peer"
|
||||
)
|
||||
|
||||
var (
|
||||
@ -159,6 +161,9 @@ type AuthStore interface {
|
||||
|
||||
// AuthInfoFromCtx gets AuthInfo from gRPC's context
|
||||
AuthInfoFromCtx(ctx context.Context) (*AuthInfo, error)
|
||||
|
||||
// AuthInfoFromTLS gets AuthInfo from TLS info of gRPC's context
|
||||
AuthInfoFromTLS(ctx context.Context) *AuthInfo
|
||||
}
|
||||
|
||||
type authStore struct {
|
||||
@ -950,6 +955,28 @@ func (as *authStore) isValidSimpleToken(token string, ctx context.Context) bool
|
||||
return false
|
||||
}
|
||||
|
||||
func (as *authStore) AuthInfoFromTLS(ctx context.Context) *AuthInfo {
|
||||
peer, ok := peer.FromContext(ctx)
|
||||
if !ok || peer == nil || peer.AuthInfo == nil {
|
||||
return nil
|
||||
}
|
||||
|
||||
tlsInfo := peer.AuthInfo.(credentials.TLSInfo)
|
||||
for _, chains := range tlsInfo.State.VerifiedChains {
|
||||
for _, chain := range chains {
|
||||
cn := chain.Subject.CommonName
|
||||
plog.Debugf("found common name %s", cn)
|
||||
|
||||
return &AuthInfo{
|
||||
Username: cn,
|
||||
Revision: as.Revision(),
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
return nil
|
||||
}
|
||||
|
||||
func (as *authStore) AuthInfoFromCtx(ctx context.Context) (*AuthInfo, error) {
|
||||
md, ok := metadata.FromContext(ctx)
|
||||
if !ok {
|
||||
|
@ -47,6 +47,7 @@ type RaftStatusGetter interface {
|
||||
}
|
||||
|
||||
type AuthGetter interface {
|
||||
AuthInfoFromCtx(ctx context.Context) (*auth.AuthInfo, error)
|
||||
AuthStore() auth.AuthStore
|
||||
}
|
||||
|
||||
@ -152,7 +153,7 @@ type authMaintenanceServer struct {
|
||||
}
|
||||
|
||||
func (ams *authMaintenanceServer) isAuthenticated(ctx context.Context) error {
|
||||
authInfo, err := ams.ag.AuthStore().AuthInfoFromCtx(ctx)
|
||||
authInfo, err := ams.ag.AuthInfoFromCtx(ctx)
|
||||
if err != nil {
|
||||
return err
|
||||
}
|
||||
|
@ -1022,7 +1022,7 @@ func (s *EtcdServer) checkMembershipOperationPermission(ctx context.Context) err
|
||||
// in the state machine layer
|
||||
// However, both of membership change and role management requires the root privilege.
|
||||
// So careful operation by admins can prevent the problem.
|
||||
authInfo, err := s.AuthStore().AuthInfoFromCtx(ctx)
|
||||
authInfo, err := s.AuthInfoFromCtx(ctx)
|
||||
if err != nil {
|
||||
return err
|
||||
}
|
||||
|
@ -617,7 +617,7 @@ func (s *EtcdServer) RoleDelete(ctx context.Context, r *pb.AuthRoleDeleteRequest
|
||||
// doSerialize handles the auth logic, with permissions checked by "chk", for a serialized request "get". Returns a non-nil error on authentication failure.
|
||||
func (s *EtcdServer) doSerialize(ctx context.Context, chk func(*auth.AuthInfo) error, get func()) error {
|
||||
for {
|
||||
ai, err := s.AuthStore().AuthInfoFromCtx(ctx)
|
||||
ai, err := s.AuthInfoFromCtx(ctx)
|
||||
if err != nil {
|
||||
return err
|
||||
}
|
||||
@ -652,7 +652,7 @@ func (s *EtcdServer) processInternalRaftRequestOnce(ctx context.Context, r pb.In
|
||||
ID: s.reqIDGen.Next(),
|
||||
}
|
||||
|
||||
authInfo, err := s.AuthStore().AuthInfoFromCtx(ctx)
|
||||
authInfo, err := s.AuthInfoFromCtx(ctx)
|
||||
if err != nil {
|
||||
return nil, err
|
||||
}
|
||||
@ -802,3 +802,14 @@ func (s *EtcdServer) linearizableReadNotify(ctx context.Context) error {
|
||||
return ErrStopped
|
||||
}
|
||||
}
|
||||
|
||||
func (s *EtcdServer) AuthInfoFromCtx(ctx context.Context) (*auth.AuthInfo, error) {
|
||||
if s.Cfg.ClientCertAuthEnabled {
|
||||
authInfo := s.AuthStore().AuthInfoFromTLS(ctx)
|
||||
if authInfo != nil {
|
||||
return authInfo, nil
|
||||
}
|
||||
}
|
||||
|
||||
return s.AuthStore().AuthInfoFromCtx(ctx)
|
||||
}
|
||||
|
Loading…
x
Reference in New Issue
Block a user