mirror of
https://github.com/gravitational/teleport.git
synced 2026-09-24 16:17:11 +08:00
Metrics: add IsSSO to Discover Events (#23791)
* Metrics: add IsSSO to Discover Events * review pt1 * use services.UserGetter interface * godocs, renamings * add isSSO to user identity * remove ctx from convert * add godocs to usermetadata fields * add UserType enum
This commit is contained in:
@@ -26,6 +26,16 @@ import (
|
||||
"github.com/gravitational/teleport/api/utils"
|
||||
)
|
||||
|
||||
// UserType is the user's types that indicates where it was created.
|
||||
type UserType string
|
||||
|
||||
const (
|
||||
// UserTypeSSO identifies a user that was created from an SSO provider.
|
||||
UserTypeSSO UserType = "sso"
|
||||
// UserTypeLocal identifies a user that was created in Teleport itself and has no connection to an external identity.
|
||||
UserTypeLocal UserType = "local"
|
||||
)
|
||||
|
||||
// User represents teleport embedded user or external user.
|
||||
type User interface {
|
||||
// ResourceWithSecrets provides common resource properties
|
||||
@@ -99,6 +109,8 @@ type User interface {
|
||||
GetCreatedBy() CreatedBy
|
||||
// SetCreatedBy sets created by information
|
||||
SetCreatedBy(CreatedBy)
|
||||
// GetUserType indicates if the User was created by an SSO Provider or locally.
|
||||
GetUserType() UserType
|
||||
// GetTraits gets the trait map for this user used to populate role variables.
|
||||
GetTraits() map[string][]string
|
||||
// SetTraits sets the trait map for this user used to populate role variables.
|
||||
@@ -404,6 +416,15 @@ func (u UserV2) GetGCPServiceAccounts() []string {
|
||||
return u.getTrait(constants.TraitGCPServiceAccounts)
|
||||
}
|
||||
|
||||
// GetUserType indicates if the User was created by an SSO Provider or locally.
|
||||
func (u UserV2) GetUserType() UserType {
|
||||
if u.GetCreatedBy().Connector == nil {
|
||||
return UserTypeLocal
|
||||
}
|
||||
|
||||
return UserTypeSSO
|
||||
}
|
||||
|
||||
func (u *UserV2) String() string {
|
||||
return fmt.Sprintf("User(name=%v, roles=%v, identities=%v)", u.Metadata.Name, u.Spec.Roles, u.Spec.OIDCIdentities)
|
||||
}
|
||||
|
||||
File diff suppressed because it is too large
Load Diff
+4
@@ -391,6 +391,9 @@ export class DiscoverMetadata extends jspb.Message {
|
||||
getUserName(): string;
|
||||
setUserName(value: string): DiscoverMetadata;
|
||||
|
||||
getSso(): boolean;
|
||||
setSso(value: boolean): DiscoverMetadata;
|
||||
|
||||
|
||||
serializeBinary(): Uint8Array;
|
||||
toObject(includeInstance?: boolean): DiscoverMetadata.AsObject;
|
||||
@@ -406,6 +409,7 @@ export namespace DiscoverMetadata {
|
||||
export type AsObject = {
|
||||
id: string,
|
||||
userName: string,
|
||||
sso: boolean,
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
+31
-1
@@ -3439,7 +3439,8 @@ proto.prehog.v1alpha.DiscoverMetadata.prototype.toObject = function(opt_includeI
|
||||
proto.prehog.v1alpha.DiscoverMetadata.toObject = function(includeInstance, msg) {
|
||||
var f, obj = {
|
||||
id: jspb.Message.getFieldWithDefault(msg, 1, ""),
|
||||
userName: jspb.Message.getFieldWithDefault(msg, 2, "")
|
||||
userName: jspb.Message.getFieldWithDefault(msg, 2, ""),
|
||||
sso: jspb.Message.getBooleanFieldWithDefault(msg, 3, false)
|
||||
};
|
||||
|
||||
if (includeInstance) {
|
||||
@@ -3484,6 +3485,10 @@ proto.prehog.v1alpha.DiscoverMetadata.deserializeBinaryFromReader = function(msg
|
||||
var value = /** @type {string} */ (reader.readString());
|
||||
msg.setUserName(value);
|
||||
break;
|
||||
case 3:
|
||||
var value = /** @type {boolean} */ (reader.readBool());
|
||||
msg.setSso(value);
|
||||
break;
|
||||
default:
|
||||
reader.skipField();
|
||||
break;
|
||||
@@ -3527,6 +3532,13 @@ proto.prehog.v1alpha.DiscoverMetadata.serializeBinaryToWriter = function(message
|
||||
f
|
||||
);
|
||||
}
|
||||
f = message.getSso();
|
||||
if (f) {
|
||||
writer.writeBool(
|
||||
3,
|
||||
f
|
||||
);
|
||||
}
|
||||
};
|
||||
|
||||
|
||||
@@ -3566,6 +3578,24 @@ proto.prehog.v1alpha.DiscoverMetadata.prototype.setUserName = function(value) {
|
||||
};
|
||||
|
||||
|
||||
/**
|
||||
* optional bool sso = 3;
|
||||
* @return {boolean}
|
||||
*/
|
||||
proto.prehog.v1alpha.DiscoverMetadata.prototype.getSso = function() {
|
||||
return /** @type {boolean} */ (jspb.Message.getBooleanFieldWithDefault(this, 3, false));
|
||||
};
|
||||
|
||||
|
||||
/**
|
||||
* @param {boolean} value
|
||||
* @return {!proto.prehog.v1alpha.DiscoverMetadata} returns this
|
||||
*/
|
||||
proto.prehog.v1alpha.DiscoverMetadata.prototype.setSso = function(value) {
|
||||
return jspb.Message.setProto3BooleanField(this, 3, value);
|
||||
};
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
+12
-1
@@ -2073,6 +2073,7 @@ func generateCert(a *Server, req certRequest, caType types.CertAuthType) (*proto
|
||||
AssetTag: req.deviceExtensions.AssetTag,
|
||||
CredentialID: req.deviceExtensions.CredentialID,
|
||||
},
|
||||
UserType: req.user.GetUserType(),
|
||||
}
|
||||
|
||||
var signedTLSCert []byte
|
||||
@@ -4314,7 +4315,17 @@ func (a *Server) SubmitUsageEvent(ctx context.Context, req *proto.SubmitUsageEve
|
||||
return trace.Wrap(err)
|
||||
}
|
||||
|
||||
event, err := usagereporter.ConvertUsageEvent(req.GetEvent(), username)
|
||||
userIsSSO, err := authz.GetClientUserIsSSO(ctx)
|
||||
if err != nil {
|
||||
return trace.Wrap(err)
|
||||
}
|
||||
|
||||
userMetadata := usagereporter.UserMetadata{
|
||||
Username: username,
|
||||
IsSSO: userIsSSO,
|
||||
}
|
||||
|
||||
event, err := usagereporter.ConvertUsageEvent(req.GetEvent(), userMetadata)
|
||||
if err != nil {
|
||||
return trace.Wrap(err)
|
||||
}
|
||||
|
||||
@@ -2607,7 +2607,7 @@ func (a *ServerWithRoles) generateUserCerts(ctx context.Context, req proto.UserC
|
||||
}
|
||||
|
||||
// Do not allow SSO users to be impersonated.
|
||||
if req.Username != a.context.User.GetName() && user.GetCreatedBy().Connector != nil {
|
||||
if req.Username != a.context.User.GetName() && user.GetUserType() == types.UserTypeSSO {
|
||||
log.Warningf("User %v tried to issue a cert for externally managed user %v, this is not supported.", a.context.User.GetName(), req.Username)
|
||||
return nil, trace.AccessDenied("access denied")
|
||||
}
|
||||
|
||||
+1
-1
@@ -485,7 +485,7 @@ func (s *Server) generateInitialBotCerts(ctx context.Context, username string, p
|
||||
}
|
||||
|
||||
// Do not allow SSO users to be impersonated.
|
||||
if user.GetCreatedBy().Connector != nil {
|
||||
if user.GetUserType() == types.UserTypeSSO {
|
||||
log.Warningf("Tried to issue a renewable cert for externally managed user %v, this is not supported.", username)
|
||||
return nil, trace.AccessDenied("access denied")
|
||||
}
|
||||
|
||||
@@ -369,6 +369,7 @@ func (a *authorizer) authorizeRemoteUser(ctx context.Context, u RemoteUser) (*Co
|
||||
LoginIP: u.Identity.LoginIP,
|
||||
PinnedIP: u.Identity.PinnedIP,
|
||||
PrivateKeyPolicy: u.Identity.PrivateKeyPolicy,
|
||||
UserType: u.Identity.UserType,
|
||||
}
|
||||
if checker.PinSourceIP() && identity.PinnedIP == "" {
|
||||
return nil, trace.AccessDenied("pinned IP is required for the user, but is not present on identity")
|
||||
@@ -931,21 +932,42 @@ func ClientUsername(ctx context.Context) string {
|
||||
return identity.Username
|
||||
}
|
||||
|
||||
func userIdentityFromContext(ctx context.Context) (*tlsca.Identity, error) {
|
||||
userWithIdentity, err := UserFromContext(ctx)
|
||||
if err != nil {
|
||||
return nil, trace.AccessDenied("missing identity")
|
||||
}
|
||||
|
||||
identity := userWithIdentity.GetIdentity()
|
||||
if identity.Username == "" {
|
||||
return nil, trace.AccessDenied("missing identity username")
|
||||
}
|
||||
|
||||
return &identity, nil
|
||||
}
|
||||
|
||||
// GetClientUsername returns the username of a remote HTTP client making the call.
|
||||
// If ctx didn't pass through auth middleware or did not come from an HTTP
|
||||
// request, returns an error.
|
||||
func GetClientUsername(ctx context.Context) (string, error) {
|
||||
userWithIdentity, err := UserFromContext(ctx)
|
||||
identity, err := userIdentityFromContext(ctx)
|
||||
if err != nil {
|
||||
return "", trace.AccessDenied("missing identity")
|
||||
}
|
||||
identity := userWithIdentity.GetIdentity()
|
||||
if identity.Username == "" {
|
||||
return "", trace.AccessDenied("missing identity username")
|
||||
return "", trace.Wrap(err)
|
||||
}
|
||||
return identity.Username, nil
|
||||
}
|
||||
|
||||
// GetClientUserIsSSO extracts the identity of a remote HTTP client and indicates whether that is an SSO user.
|
||||
// If ctx didn't pass through auth middleware or did not come from an HTTP
|
||||
// request, returns an error.
|
||||
func GetClientUserIsSSO(ctx context.Context) (bool, error) {
|
||||
identity, err := userIdentityFromContext(ctx)
|
||||
if err != nil {
|
||||
return false, trace.Wrap(err)
|
||||
}
|
||||
return identity.UserType == types.UserTypeSSO, nil
|
||||
}
|
||||
|
||||
// ClientImpersonator returns the impersonator username of a remote client
|
||||
// making the call. If not present, returns an empty string
|
||||
func ClientImpersonator(ctx context.Context) string {
|
||||
|
||||
@@ -182,6 +182,32 @@ func upsertLockWithPutEvent(ctx context.Context, t *testing.T, client *testClien
|
||||
}
|
||||
}
|
||||
|
||||
func TestGetClientUserIsSSO(t *testing.T) {
|
||||
ctx := context.Background()
|
||||
|
||||
u := LocalUser{
|
||||
Username: "someuser",
|
||||
Identity: tlsca.Identity{
|
||||
Username: "someuser",
|
||||
Groups: []string{"somerole"},
|
||||
},
|
||||
}
|
||||
|
||||
// Non SSO user must return false
|
||||
nonSSOUserCtx := context.WithValue(ctx, contextUser, u)
|
||||
|
||||
isSSO, err := GetClientUserIsSSO(nonSSOUserCtx)
|
||||
require.NoError(t, err)
|
||||
require.False(t, isSSO, "expected a non-SSO user")
|
||||
|
||||
// An SSO user must return true
|
||||
u.Identity.UserType = types.UserTypeSSO
|
||||
ssoUserCtx := context.WithValue(ctx, contextUser, u)
|
||||
localUserIsSSO, err := GetClientUserIsSSO(ssoUserCtx)
|
||||
require.NoError(t, err)
|
||||
require.True(t, localUserIsSSO, "expected an SSO user")
|
||||
}
|
||||
|
||||
func TestAuthorizer_Authorize_deviceTrust(t *testing.T) {
|
||||
t.Parallel()
|
||||
|
||||
|
||||
@@ -190,6 +190,9 @@ type Identity struct {
|
||||
|
||||
// DeviceExtensions holds device-aware extensions for the identity.
|
||||
DeviceExtensions DeviceExtensions
|
||||
|
||||
// UserType indicates if the User was created by an SSO Provider or locally.
|
||||
UserType types.UserType
|
||||
}
|
||||
|
||||
// RouteToApp holds routing information for applications.
|
||||
|
||||
@@ -407,10 +407,18 @@ func (u *ResourceHeartbeatEvent) Anonymize(a utils.Anonymizer) prehogv1.SubmitEv
|
||||
}
|
||||
}
|
||||
|
||||
// UserMetadata contains user metadata information which is used to contextualize events with user information.
|
||||
type UserMetadata struct {
|
||||
// Username contains the user's name.
|
||||
Username string
|
||||
// IsSSO indicates if the user was created by an SSO provider.
|
||||
IsSSO bool
|
||||
}
|
||||
|
||||
// ConvertUsageEvent converts a usage event from an API object into an
|
||||
// anonymizable event. All events that can be submitted externally via the Auth
|
||||
// API need to be defined here.
|
||||
func ConvertUsageEvent(event *usageeventsv1.UsageEventOneOf, identityUsername string) (Anonymizable, error) {
|
||||
func ConvertUsageEvent(event *usageeventsv1.UsageEventOneOf, userMD UserMetadata) (Anonymizable, error) {
|
||||
// Note: events (especially pre-registration) that embed a username of their
|
||||
// own should generally pass that through rather than using the identity
|
||||
// username provided to the function. It may be the username of a Teleport
|
||||
@@ -419,16 +427,16 @@ func ConvertUsageEvent(event *usageeventsv1.UsageEventOneOf, identityUsername st
|
||||
switch e := event.GetEvent().(type) {
|
||||
case *usageeventsv1.UsageEventOneOf_UiBannerClick:
|
||||
return &UIBannerClickEvent{
|
||||
UserName: identityUsername,
|
||||
UserName: userMD.Username,
|
||||
Alert: e.UiBannerClick.Alert,
|
||||
}, nil
|
||||
case *usageeventsv1.UsageEventOneOf_UiOnboardAddFirstResourceClick:
|
||||
return &UIOnboardAddFirstResourceClickEvent{
|
||||
UserName: identityUsername,
|
||||
UserName: userMD.Username,
|
||||
}, nil
|
||||
case *usageeventsv1.UsageEventOneOf_UiOnboardAddFirstResourceLaterClick:
|
||||
return &UIOnboardAddFirstResourceLaterClickEvent{
|
||||
UserName: identityUsername,
|
||||
UserName: userMD.Username,
|
||||
}, nil
|
||||
case *usageeventsv1.UsageEventOneOf_UiOnboardCompleteGoToDashboardClick:
|
||||
return &UIOnboardCompleteGoToDashboardClickEvent{
|
||||
@@ -458,23 +466,23 @@ func ConvertUsageEvent(event *usageeventsv1.UsageEventOneOf, identityUsername st
|
||||
}, nil
|
||||
case *usageeventsv1.UsageEventOneOf_UiCreateNewRoleClick:
|
||||
return &UICreateNewRoleClickEvent{
|
||||
UserName: identityUsername,
|
||||
UserName: userMD.Username,
|
||||
}, nil
|
||||
case *usageeventsv1.UsageEventOneOf_UiCreateNewRoleSaveClick:
|
||||
return &UICreateNewRoleSaveClickEvent{
|
||||
UserName: identityUsername,
|
||||
UserName: userMD.Username,
|
||||
}, nil
|
||||
case *usageeventsv1.UsageEventOneOf_UiCreateNewRoleCancelClick:
|
||||
return &UICreateNewRoleCancelClickEvent{
|
||||
UserName: identityUsername,
|
||||
UserName: userMD.Username,
|
||||
}, nil
|
||||
case *usageeventsv1.UsageEventOneOf_UiCreateNewRoleViewDocumentationClick:
|
||||
return &UICreateNewRoleViewDocumentationClickEvent{
|
||||
UserName: identityUsername,
|
||||
UserName: userMD.Username,
|
||||
}, nil
|
||||
case *usageeventsv1.UsageEventOneOf_UiDiscoverStartedEvent:
|
||||
ret := &UIDiscoverStartedEvent{
|
||||
Metadata: discoverMetadataToPrehog(e.UiDiscoverStartedEvent.Metadata, identityUsername),
|
||||
Metadata: discoverMetadataToPrehog(e.UiDiscoverStartedEvent.Metadata, userMD),
|
||||
Status: discoverStatusToPrehog(e.UiDiscoverStartedEvent.Status),
|
||||
}
|
||||
if err := ret.CheckAndSetDefaults(); err != nil {
|
||||
@@ -484,7 +492,7 @@ func ConvertUsageEvent(event *usageeventsv1.UsageEventOneOf, identityUsername st
|
||||
return ret, nil
|
||||
case *usageeventsv1.UsageEventOneOf_UiDiscoverResourceSelectionEvent:
|
||||
ret := &UIDiscoverResourceSelectionEvent{
|
||||
Metadata: discoverMetadataToPrehog(e.UiDiscoverResourceSelectionEvent.Metadata, identityUsername),
|
||||
Metadata: discoverMetadataToPrehog(e.UiDiscoverResourceSelectionEvent.Metadata, userMD),
|
||||
Resource: discoverResourceToPrehog(e.UiDiscoverResourceSelectionEvent.Resource),
|
||||
Status: discoverStatusToPrehog(e.UiDiscoverResourceSelectionEvent.Status),
|
||||
}
|
||||
@@ -495,7 +503,7 @@ func ConvertUsageEvent(event *usageeventsv1.UsageEventOneOf, identityUsername st
|
||||
return ret, nil
|
||||
case *usageeventsv1.UsageEventOneOf_UiDiscoverDeployServiceEvent:
|
||||
ret := &UIDiscoverDeployServiceEvent{
|
||||
Metadata: discoverMetadataToPrehog(e.UiDiscoverDeployServiceEvent.Metadata, identityUsername),
|
||||
Metadata: discoverMetadataToPrehog(e.UiDiscoverDeployServiceEvent.Metadata, userMD),
|
||||
Resource: discoverResourceToPrehog(e.UiDiscoverDeployServiceEvent.Resource),
|
||||
Status: discoverStatusToPrehog(e.UiDiscoverDeployServiceEvent.Status),
|
||||
}
|
||||
@@ -506,7 +514,7 @@ func ConvertUsageEvent(event *usageeventsv1.UsageEventOneOf, identityUsername st
|
||||
return ret, nil
|
||||
case *usageeventsv1.UsageEventOneOf_UiDiscoverDatabaseRegisterEvent:
|
||||
ret := &UIDiscoverDatabaseRegisterEvent{
|
||||
Metadata: discoverMetadataToPrehog(e.UiDiscoverDatabaseRegisterEvent.Metadata, identityUsername),
|
||||
Metadata: discoverMetadataToPrehog(e.UiDiscoverDatabaseRegisterEvent.Metadata, userMD),
|
||||
Resource: discoverResourceToPrehog(e.UiDiscoverDatabaseRegisterEvent.Resource),
|
||||
Status: discoverStatusToPrehog(e.UiDiscoverDatabaseRegisterEvent.Status),
|
||||
}
|
||||
@@ -517,7 +525,7 @@ func ConvertUsageEvent(event *usageeventsv1.UsageEventOneOf, identityUsername st
|
||||
return ret, nil
|
||||
case *usageeventsv1.UsageEventOneOf_UiDiscoverDatabaseConfigureMtlsEvent:
|
||||
ret := &UIDiscoverDatabaseConfigureMTLSEvent{
|
||||
Metadata: discoverMetadataToPrehog(e.UiDiscoverDatabaseConfigureMtlsEvent.Metadata, identityUsername),
|
||||
Metadata: discoverMetadataToPrehog(e.UiDiscoverDatabaseConfigureMtlsEvent.Metadata, userMD),
|
||||
Resource: discoverResourceToPrehog(e.UiDiscoverDatabaseConfigureMtlsEvent.Resource),
|
||||
Status: discoverStatusToPrehog(e.UiDiscoverDatabaseConfigureMtlsEvent.Status),
|
||||
}
|
||||
@@ -528,7 +536,7 @@ func ConvertUsageEvent(event *usageeventsv1.UsageEventOneOf, identityUsername st
|
||||
return ret, nil
|
||||
case *usageeventsv1.UsageEventOneOf_UiDiscoverDesktopActiveDirectoryToolsInstallEvent:
|
||||
ret := &UIDiscoverDesktopActiveDirectoryToolsInstallEvent{
|
||||
Metadata: discoverMetadataToPrehog(e.UiDiscoverDesktopActiveDirectoryToolsInstallEvent.Metadata, identityUsername),
|
||||
Metadata: discoverMetadataToPrehog(e.UiDiscoverDesktopActiveDirectoryToolsInstallEvent.Metadata, userMD),
|
||||
Resource: discoverResourceToPrehog(e.UiDiscoverDesktopActiveDirectoryToolsInstallEvent.Resource),
|
||||
Status: discoverStatusToPrehog(e.UiDiscoverDesktopActiveDirectoryToolsInstallEvent.Status),
|
||||
}
|
||||
@@ -539,7 +547,7 @@ func ConvertUsageEvent(event *usageeventsv1.UsageEventOneOf, identityUsername st
|
||||
return ret, nil
|
||||
case *usageeventsv1.UsageEventOneOf_UiDiscoverDesktopActiveDirectoryConfigureEvent:
|
||||
ret := &UIDiscoverDesktopActiveDirectoryConfigureEvent{
|
||||
Metadata: discoverMetadataToPrehog(e.UiDiscoverDesktopActiveDirectoryConfigureEvent.Metadata, identityUsername),
|
||||
Metadata: discoverMetadataToPrehog(e.UiDiscoverDesktopActiveDirectoryConfigureEvent.Metadata, userMD),
|
||||
Resource: discoverResourceToPrehog(e.UiDiscoverDesktopActiveDirectoryConfigureEvent.Resource),
|
||||
Status: discoverStatusToPrehog(e.UiDiscoverDesktopActiveDirectoryConfigureEvent.Status),
|
||||
}
|
||||
@@ -550,7 +558,7 @@ func ConvertUsageEvent(event *usageeventsv1.UsageEventOneOf, identityUsername st
|
||||
return ret, nil
|
||||
case *usageeventsv1.UsageEventOneOf_UiDiscoverAutoDiscoveredResourcesEvent:
|
||||
ret := &UIDiscoverAutoDiscoveredResourcesEvent{
|
||||
Metadata: discoverMetadataToPrehog(e.UiDiscoverAutoDiscoveredResourcesEvent.Metadata, identityUsername),
|
||||
Metadata: discoverMetadataToPrehog(e.UiDiscoverAutoDiscoveredResourcesEvent.Metadata, userMD),
|
||||
Resource: discoverResourceToPrehog(e.UiDiscoverAutoDiscoveredResourcesEvent.Resource),
|
||||
Status: discoverStatusToPrehog(e.UiDiscoverAutoDiscoveredResourcesEvent.Status),
|
||||
ResourcesCount: e.UiDiscoverAutoDiscoveredResourcesEvent.ResourcesCount,
|
||||
@@ -562,7 +570,7 @@ func ConvertUsageEvent(event *usageeventsv1.UsageEventOneOf, identityUsername st
|
||||
return ret, nil
|
||||
case *usageeventsv1.UsageEventOneOf_UiDiscoverDatabaseConfigureIamPolicyEvent:
|
||||
ret := &UIDiscoverDatabaseConfigureIAMPolicyEvent{
|
||||
Metadata: discoverMetadataToPrehog(e.UiDiscoverDatabaseConfigureIamPolicyEvent.Metadata, identityUsername),
|
||||
Metadata: discoverMetadataToPrehog(e.UiDiscoverDatabaseConfigureIamPolicyEvent.Metadata, userMD),
|
||||
Resource: discoverResourceToPrehog(e.UiDiscoverDatabaseConfigureIamPolicyEvent.Resource),
|
||||
Status: discoverStatusToPrehog(e.UiDiscoverDatabaseConfigureIamPolicyEvent.Status),
|
||||
}
|
||||
@@ -573,7 +581,7 @@ func ConvertUsageEvent(event *usageeventsv1.UsageEventOneOf, identityUsername st
|
||||
return ret, nil
|
||||
case *usageeventsv1.UsageEventOneOf_UiDiscoverPrincipalsConfigureEvent:
|
||||
ret := &UIDiscoverPrincipalsConfigureEvent{
|
||||
Metadata: discoverMetadataToPrehog(e.UiDiscoverPrincipalsConfigureEvent.Metadata, identityUsername),
|
||||
Metadata: discoverMetadataToPrehog(e.UiDiscoverPrincipalsConfigureEvent.Metadata, userMD),
|
||||
Resource: discoverResourceToPrehog(e.UiDiscoverPrincipalsConfigureEvent.Resource),
|
||||
Status: discoverStatusToPrehog(e.UiDiscoverPrincipalsConfigureEvent.Status),
|
||||
}
|
||||
@@ -584,7 +592,7 @@ func ConvertUsageEvent(event *usageeventsv1.UsageEventOneOf, identityUsername st
|
||||
return ret, nil
|
||||
case *usageeventsv1.UsageEventOneOf_UiDiscoverTestConnectionEvent:
|
||||
ret := &UIDiscoverTestConnectionEvent{
|
||||
Metadata: discoverMetadataToPrehog(e.UiDiscoverTestConnectionEvent.Metadata, identityUsername),
|
||||
Metadata: discoverMetadataToPrehog(e.UiDiscoverTestConnectionEvent.Metadata, userMD),
|
||||
Resource: discoverResourceToPrehog(e.UiDiscoverTestConnectionEvent.Resource),
|
||||
Status: discoverStatusToPrehog(e.UiDiscoverTestConnectionEvent.Status),
|
||||
}
|
||||
@@ -595,7 +603,7 @@ func ConvertUsageEvent(event *usageeventsv1.UsageEventOneOf, identityUsername st
|
||||
return ret, nil
|
||||
case *usageeventsv1.UsageEventOneOf_UiDiscoverCompletedEvent:
|
||||
ret := &UIDiscoverCompletedEvent{
|
||||
Metadata: discoverMetadataToPrehog(e.UiDiscoverCompletedEvent.Metadata, identityUsername),
|
||||
Metadata: discoverMetadataToPrehog(e.UiDiscoverCompletedEvent.Metadata, userMD),
|
||||
Resource: discoverResourceToPrehog(e.UiDiscoverCompletedEvent.Resource),
|
||||
Status: discoverStatusToPrehog(e.UiDiscoverCompletedEvent.Status),
|
||||
}
|
||||
|
||||
@@ -24,10 +24,11 @@ import (
|
||||
"github.com/gravitational/teleport/lib/utils"
|
||||
)
|
||||
|
||||
func discoverMetadataToPrehog(u *usageeventsv1.DiscoverMetadata, identityUsername string) *prehogv1.DiscoverMetadata {
|
||||
func discoverMetadataToPrehog(u *usageeventsv1.DiscoverMetadata, userMD UserMetadata) *prehogv1.DiscoverMetadata {
|
||||
return &prehogv1.DiscoverMetadata{
|
||||
Id: u.Id,
|
||||
UserName: identityUsername,
|
||||
UserName: userMD.Username,
|
||||
Sso: userMD.IsSSO,
|
||||
}
|
||||
}
|
||||
|
||||
@@ -121,6 +122,7 @@ func (u *UIDiscoverStartedEvent) Anonymize(a utils.Anonymizer) prehogv1.SubmitEv
|
||||
Metadata: &prehogv1.DiscoverMetadata{
|
||||
Id: u.Metadata.Id,
|
||||
UserName: a.AnonymizeString(u.Metadata.UserName),
|
||||
Sso: u.Metadata.Sso,
|
||||
},
|
||||
Status: u.Status,
|
||||
},
|
||||
|
||||
@@ -35,6 +35,7 @@ func TestConvertUsageEvent(t *testing.T) {
|
||||
name string
|
||||
event *usageeventsv1.UsageEventOneOf
|
||||
identityUsername string
|
||||
isSSOUser bool
|
||||
errCheck require.ErrorAssertionFunc
|
||||
expected *prehogv1.SubmitEventRequest
|
||||
}{
|
||||
@@ -53,6 +54,7 @@ func TestConvertUsageEvent(t *testing.T) {
|
||||
Metadata: &prehogv1.DiscoverMetadata{
|
||||
Id: "someid",
|
||||
UserName: expectedAnonymizedUserString,
|
||||
Sso: false,
|
||||
},
|
||||
Status: &prehogv1.DiscoverStepStatus{Status: prehogv1.DiscoverStatus_DISCOVER_STATUS_SUCCESS},
|
||||
},
|
||||
@@ -74,6 +76,7 @@ func TestConvertUsageEvent(t *testing.T) {
|
||||
Metadata: &prehogv1.DiscoverMetadata{
|
||||
Id: "someid",
|
||||
UserName: expectedAnonymizedUserString,
|
||||
Sso: false,
|
||||
},
|
||||
Resource: &prehogv1.DiscoverResourceMetadata{Resource: prehogv1.DiscoverResource_DISCOVER_RESOURCE_SERVER},
|
||||
Status: &prehogv1.DiscoverStepStatus{Status: prehogv1.DiscoverStatus_DISCOVER_STATUS_SUCCESS},
|
||||
@@ -139,6 +142,7 @@ func TestConvertUsageEvent(t *testing.T) {
|
||||
Metadata: &prehogv1.DiscoverMetadata{
|
||||
Id: "someid",
|
||||
UserName: expectedAnonymizedUserString,
|
||||
Sso: false,
|
||||
},
|
||||
Resource: &prehogv1.DiscoverResourceMetadata{Resource: prehogv1.DiscoverResource_DISCOVER_RESOURCE_SERVER},
|
||||
Status: &prehogv1.DiscoverStepStatus{Status: prehogv1.DiscoverStatus_DISCOVER_STATUS_SUCCESS},
|
||||
@@ -163,6 +167,7 @@ func TestConvertUsageEvent(t *testing.T) {
|
||||
Metadata: &prehogv1.DiscoverMetadata{
|
||||
Id: "someid",
|
||||
UserName: expectedAnonymizedUserString,
|
||||
Sso: false,
|
||||
},
|
||||
Resource: &prehogv1.DiscoverResourceMetadata{Resource: prehogv1.DiscoverResource_DISCOVER_RESOURCE_SERVER},
|
||||
Status: &prehogv1.DiscoverStepStatus{Status: prehogv1.DiscoverStatus_DISCOVER_STATUS_SUCCESS},
|
||||
@@ -184,13 +189,38 @@ func TestConvertUsageEvent(t *testing.T) {
|
||||
errCheck: func(tt require.TestingT, err error, i ...interface{}) {
|
||||
require.True(tt, trace.IsBadParameter(err), "exepcted trace.IsBadParameter error, got: %v", err)
|
||||
},
|
||||
}, {
|
||||
name: "discover started event with sso user",
|
||||
event: &usageeventsv1.UsageEventOneOf{Event: &usageeventsv1.UsageEventOneOf_UiDiscoverStartedEvent{
|
||||
UiDiscoverStartedEvent: &usageeventsv1.UIDiscoverStartedEvent{
|
||||
Metadata: &usageeventsv1.DiscoverMetadata{Id: "someid"},
|
||||
Status: &usageeventsv1.DiscoverStepStatus{Status: usageeventsv1.DiscoverStatus_DISCOVER_STATUS_SUCCESS},
|
||||
},
|
||||
}},
|
||||
identityUsername: "myuser",
|
||||
isSSOUser: true,
|
||||
errCheck: require.NoError,
|
||||
expected: &prehogv1.SubmitEventRequest{Event: &prehogv1.SubmitEventRequest_UiDiscoverStartedEvent{
|
||||
UiDiscoverStartedEvent: &prehogv1.UIDiscoverStartedEvent{
|
||||
Metadata: &prehogv1.DiscoverMetadata{
|
||||
Id: "someid",
|
||||
UserName: expectedAnonymizedUserString,
|
||||
Sso: true,
|
||||
},
|
||||
Status: &prehogv1.DiscoverStepStatus{Status: prehogv1.DiscoverStatus_DISCOVER_STATUS_SUCCESS},
|
||||
},
|
||||
}},
|
||||
},
|
||||
} {
|
||||
t.Run(tt.name, func(t *testing.T) {
|
||||
tt := tt
|
||||
t.Parallel()
|
||||
|
||||
usageEvent, err := ConvertUsageEvent(tt.event, tt.identityUsername)
|
||||
userMD := UserMetadata{
|
||||
Username: tt.identityUsername,
|
||||
IsSSO: tt.isSSOUser,
|
||||
}
|
||||
usageEvent, err := ConvertUsageEvent(tt.event, userMD)
|
||||
tt.errCheck(t, err)
|
||||
if err != nil {
|
||||
return
|
||||
|
||||
+1
-1
@@ -65,7 +65,7 @@ func NewUserListEntry(teleUser types.User) (*UserListEntry, error) {
|
||||
}
|
||||
|
||||
authType := "local"
|
||||
if teleUser.GetCreatedBy().Connector != nil {
|
||||
if teleUser.GetUserType() == types.UserTypeSSO {
|
||||
authType = teleUser.GetCreatedBy().Connector.Type
|
||||
}
|
||||
|
||||
|
||||
@@ -146,6 +146,9 @@ message DiscoverMetadata {
|
||||
|
||||
// anonymized
|
||||
string user_name = 2;
|
||||
|
||||
// SSO indicates whether the user is from an SSO provider.
|
||||
bool sso = 3;
|
||||
}
|
||||
|
||||
// DiscoverResource represents a resource type.
|
||||
|
||||
Reference in New Issue
Block a user