From f17953b5011c8b2163d18ffe5c196372ecf13fa9 Mon Sep 17 00:00:00 2001 From: Stefan Benz <46600784+stebenz@users.noreply.github.com> Date: Mon, 23 Jun 2025 14:12:35 +0200 Subject: [PATCH] fix: deprecated api calls for v3 tests --- .../grpc/user/v2/integration_test/key_test.go | 659 ------- .../grpc/user/v2/integration_test/pat_test.go | 615 ------ .../user/v2/integration_test/secret_test.go | 347 ---- .../user/v2/integration_test/user_test.go | 1700 +---------------- internal/integration/client.go | 41 +- 5 files changed, 9 insertions(+), 3353 deletions(-) delete mode 100644 internal/api/grpc/user/v2/integration_test/key_test.go delete mode 100644 internal/api/grpc/user/v2/integration_test/pat_test.go delete mode 100644 internal/api/grpc/user/v2/integration_test/secret_test.go diff --git a/internal/api/grpc/user/v2/integration_test/key_test.go b/internal/api/grpc/user/v2/integration_test/key_test.go deleted file mode 100644 index e85903b2cb..0000000000 --- a/internal/api/grpc/user/v2/integration_test/key_test.go +++ /dev/null @@ -1,659 +0,0 @@ -//go:build integration - -package user_test - -import ( - "context" - "fmt" - "slices" - "testing" - "time" - - "github.com/brianvoe/gofakeit/v6" - "github.com/google/go-cmp/cmp" - "github.com/stretchr/testify/assert" - "github.com/stretchr/testify/require" - "google.golang.org/protobuf/testing/protocmp" - "google.golang.org/protobuf/types/known/timestamppb" - - "github.com/zitadel/zitadel/internal/integration" - "github.com/zitadel/zitadel/pkg/grpc/filter/v2" - "github.com/zitadel/zitadel/pkg/grpc/user/v2" -) - -func TestServer_AddKey(t *testing.T) { - resp := Instance.CreateUserTypeMachine(IamCTX) - userId := resp.GetId() - expirationDate := timestamppb.New(time.Now().Add(time.Hour * 24)) - type args struct { - req *user.AddKeyRequest - prepare func(request *user.AddKeyRequest) error - } - tests := []struct { - name string - args args - wantErr bool - wantEmtpyKey bool - }{ - { - name: "add key, user not existing", - args: args{ - &user.AddKeyRequest{ - UserId: "notexisting", - ExpirationDate: expirationDate, - }, - func(request *user.AddKeyRequest) error { return nil }, - }, - wantErr: true, - }, - { - name: "generate key pair, ok", - args: args{ - &user.AddKeyRequest{ - ExpirationDate: expirationDate, - }, - func(request *user.AddKeyRequest) error { - request.UserId = userId - return nil - }, - }, - }, - { - name: "add valid public key, ok", - args: args{ - &user.AddKeyRequest{ - ExpirationDate: expirationDate, - // This is the public key of the tester system user. This must be valid. - PublicKey: []byte(` ------BEGIN PUBLIC KEY----- -MIIBIjANBgkqhkiG9w0BAQEFAAOCAQ8AMIIBCgKCAQEAzi+FFSJL7f5yw4KTwzgM -P34ePGycm/M+kT0M7V4Cgx5V3EaDIvTQKTLfBaEB45zb9LtjIXzDw0rXRoS2hO6t -h+CYQCz3KCvh09C0IzxZiB2IS3H/aT+5Bx9EFY+vnAkZjccbyG5YNRvmtOlnvIeI -H7qZ0tEwkPfF5GEZNPJPtmy3UGV7iofdVQS1xRj73+aMw5rvH4D8IdyiAC3VekIb -pt0Vj0SUX3DwKtog337BzTiPk3aXRF0sbFhQoqdJRI8NqgZjCwjq9yfI5tyxYswn -+JGzHGdHvW3idODlmwEt5K2pasiRIWK2OGfq+w0EcltQHabuqEPgZlmhCkRdNfix -BwIDAQAB ------END PUBLIC KEY----- -`), - }, - func(request *user.AddKeyRequest) error { - request.UserId = userId - return nil - }, - }, - wantEmtpyKey: true, - }, - { - name: "add invalid public key, error", - args: args{ - &user.AddKeyRequest{ - ExpirationDate: expirationDate, - PublicKey: []byte(` ------BEGIN PUBLIC KEY----- -abcdefghijklmnopqrstuvwxyzABCDEFGHIJKLMNOPQRSTUVWXYZ0123456789 ------END PUBLIC KEY----- -`), - }, - func(request *user.AddKeyRequest) error { - request.UserId = userId - return nil - }, - }, - wantErr: true, - }, - { - name: "add key human, error", - args: args{ - &user.AddKeyRequest{ - ExpirationDate: expirationDate, - }, - func(request *user.AddKeyRequest) error { - resp := Instance.CreateUserTypeHuman(IamCTX) - request.UserId = resp.Id - return nil - }, - }, - wantErr: true, - }, - { - name: "add another key, ok", - args: args{ - &user.AddKeyRequest{ - ExpirationDate: expirationDate, - }, - func(request *user.AddKeyRequest) error { - request.UserId = userId - _, err := Client.AddKey(IamCTX, &user.AddKeyRequest{ - ExpirationDate: expirationDate, - UserId: userId, - }) - return err - }, - }, - }, - } - for _, tt := range tests { - t.Run(tt.name, func(t *testing.T) { - now := time.Now() - err := tt.args.prepare(tt.args.req) - require.NoError(t, err) - got, err := Client.AddKey(CTX, tt.args.req) - if tt.wantErr { - require.Error(t, err) - return - } - require.NoError(t, err) - assert.NotEmpty(t, got.KeyId, "key id is empty") - if tt.wantEmtpyKey { - assert.Empty(t, got.KeyContent, "key content is not empty") - } else { - assert.NotEmpty(t, got.KeyContent, "key content is empty") - } - creationDate := got.CreationDate.AsTime() - assert.Greater(t, creationDate, now, "creation date is before the test started") - assert.Less(t, creationDate, time.Now(), "creation date is in the future") - }) - } -} - -func TestServer_AddKey_Permission(t *testing.T) { - OrgCTX := CTX - otherOrg := Instance.CreateOrganization(IamCTX, fmt.Sprintf("AddKey-%s", gofakeit.AppName()), gofakeit.Email()) - otherOrgUser, err := Client.CreateUser(IamCTX, &user.CreateUserRequest{ - OrganizationId: otherOrg.OrganizationId, - UserType: &user.CreateUserRequest_Machine_{ - Machine: &user.CreateUserRequest_Machine{ - Name: gofakeit.Name(), - }, - }, - }) - require.NoError(t, err) - request := &user.AddKeyRequest{ - ExpirationDate: timestamppb.New(time.Now().Add(time.Hour * 24)), - UserId: otherOrgUser.GetId(), - } - type args struct { - ctx context.Context - req *user.AddKeyRequest - } - tests := []struct { - name string - args args - wantErr bool - }{ - { - name: "system, ok", - args: args{SystemCTX, request}, - }, - { - name: "instance, ok", - args: args{IamCTX, request}, - }, - { - name: "org, error", - args: args{OrgCTX, request}, - wantErr: true, - }, - { - name: "user, error", - args: args{UserCTX, request}, - wantErr: true, - }, - } - for _, tt := range tests { - t.Run(tt.name, func(t *testing.T) { - now := time.Now() - require.NoError(t, err) - got, err := Client.AddKey(tt.args.ctx, tt.args.req) - if tt.wantErr { - require.Error(t, err) - return - } - require.NoError(t, err) - assert.NotEmpty(t, got.KeyId, "key id is empty") - assert.NotEmpty(t, got.KeyContent, "key content is empty") - creationDate := got.CreationDate.AsTime() - assert.Greater(t, creationDate, now, "creation date is before the test started") - assert.Less(t, creationDate, time.Now(), "creation date is in the future") - }) - } -} - -func TestServer_RemoveKey(t *testing.T) { - resp := Instance.CreateUserTypeMachine(IamCTX) - userId := resp.GetId() - expirationDate := timestamppb.New(time.Now().Add(time.Hour * 24)) - type args struct { - req *user.RemoveKeyRequest - prepare func(request *user.RemoveKeyRequest) error - } - tests := []struct { - name string - args args - wantErr bool - }{ - { - name: "remove key, user not existing", - args: args{ - &user.RemoveKeyRequest{ - UserId: "notexisting", - }, - func(request *user.RemoveKeyRequest) error { - key, err := Client.AddKey(IamCTX, &user.AddKeyRequest{ - ExpirationDate: expirationDate, - UserId: userId, - }) - request.KeyId = key.GetKeyId() - return err - }, - }, - wantErr: true, - }, - { - name: "remove key, not existing", - args: args{ - &user.RemoveKeyRequest{ - KeyId: "notexisting", - }, - func(request *user.RemoveKeyRequest) error { - request.UserId = userId - return nil - }, - }, - wantErr: true, - }, - { - name: "remove key, ok", - args: args{ - &user.RemoveKeyRequest{}, - func(request *user.RemoveKeyRequest) error { - key, err := Client.AddKey(IamCTX, &user.AddKeyRequest{ - ExpirationDate: expirationDate, - UserId: userId, - }) - request.KeyId = key.GetKeyId() - request.UserId = userId - return err - }, - }, - }, - } - for _, tt := range tests { - t.Run(tt.name, func(t *testing.T) { - now := time.Now() - err := tt.args.prepare(tt.args.req) - require.NoError(t, err) - got, err := Client.RemoveKey(CTX, tt.args.req) - if tt.wantErr { - require.Error(t, err) - return - } - require.NoError(t, err) - deletionDate := got.DeletionDate.AsTime() - assert.Greater(t, deletionDate, now, "creation date is before the test started") - assert.Less(t, deletionDate, time.Now(), "creation date is in the future") - }) - } -} - -func TestServer_RemoveKey_Permission(t *testing.T) { - OrgCTX := CTX - otherOrg := Instance.CreateOrganization(IamCTX, fmt.Sprintf("RemoveKey-%s", gofakeit.AppName()), gofakeit.Email()) - otherOrgUser, err := Client.CreateUser(IamCTX, &user.CreateUserRequest{ - OrganizationId: otherOrg.OrganizationId, - UserType: &user.CreateUserRequest_Machine_{ - Machine: &user.CreateUserRequest_Machine{ - Name: gofakeit.Name(), - }, - }, - }) - request := &user.RemoveKeyRequest{ - UserId: otherOrgUser.GetId(), - } - prepare := func(request *user.RemoveKeyRequest) error { - key, err := Client.AddKey(IamCTX, &user.AddKeyRequest{ - ExpirationDate: timestamppb.New(time.Now().Add(time.Hour * 24)), - UserId: otherOrgUser.GetId(), - }) - request.KeyId = key.GetKeyId() - return err - } - require.NoError(t, err) - type args struct { - ctx context.Context - req *user.RemoveKeyRequest - prepare func(request *user.RemoveKeyRequest) error - } - tests := []struct { - name string - args args - wantErr bool - }{ - { - name: "system, ok", - args: args{SystemCTX, request, prepare}, - }, - { - name: "instance, ok", - args: args{IamCTX, request, prepare}, - }, - { - name: "org, error", - args: args{OrgCTX, request, prepare}, - wantErr: true, - }, - { - name: "user, error", - args: args{UserCTX, request, prepare}, - wantErr: true, - }, - } - for _, tt := range tests { - t.Run(tt.name, func(t *testing.T) { - now := time.Now() - require.NoError(t, tt.args.prepare(tt.args.req)) - got, err := Client.RemoveKey(tt.args.ctx, tt.args.req) - if tt.wantErr { - require.Error(t, err) - return - } - require.NoError(t, err) - assert.NotEmpty(t, got.DeletionDate, "client key is empty") - creationDate := got.DeletionDate.AsTime() - assert.Greater(t, creationDate, now, "creation date is before the test started") - assert.Less(t, creationDate, time.Now(), "creation date is in the future") - }) - } -} - -func TestServer_ListKeys(t *testing.T) { - type args struct { - ctx context.Context - req *user.ListKeysRequest - } - type testCase struct { - name string - args args - want *user.ListKeysResponse - } - OrgCTX := CTX - otherOrg := Instance.CreateOrganization(SystemCTX, fmt.Sprintf("ListKeys-%s", gofakeit.AppName()), gofakeit.Email()) - otherOrgUser, err := Client.CreateUser(SystemCTX, &user.CreateUserRequest{ - OrganizationId: otherOrg.OrganizationId, - UserType: &user.CreateUserRequest_Machine_{ - Machine: &user.CreateUserRequest_Machine{ - Name: gofakeit.Name(), - }, - }, - }) - require.NoError(t, err) - otherOrgUserId := otherOrgUser.GetId() - otherUserId := Instance.CreateUserTypeMachine(SystemCTX).GetId() - onlySinceTestStartFilter := &user.KeysSearchFilter{Filter: &user.KeysSearchFilter_CreatedDateFilter{CreatedDateFilter: &filter.TimestampFilter{ - Timestamp: timestamppb.Now(), - Method: filter.TimestampFilterMethod_TIMESTAMP_FILTER_METHOD_AFTER_OR_EQUALS, - }}} - myOrgId := Instance.DefaultOrg.GetId() - myUserId := Instance.Users.Get(integration.UserTypeNoPermission).ID - expiresInADay := time.Now().Truncate(time.Hour).Add(time.Hour * 24) - myDataPoint := setupKeyDataPoint(t, myUserId, myOrgId, expiresInADay) - otherUserDataPoint := setupKeyDataPoint(t, otherUserId, myOrgId, expiresInADay) - otherOrgDataPointExpiringSoon := setupKeyDataPoint(t, otherOrgUserId, otherOrg.OrganizationId, time.Now().Truncate(time.Hour).Add(time.Hour)) - otherOrgDataPointExpiringLate := setupKeyDataPoint(t, otherOrgUserId, otherOrg.OrganizationId, expiresInADay.Add(time.Hour*24*30)) - sortingColumnExpirationDate := user.KeyFieldName_KEY_FIELD_NAME_KEY_EXPIRATION_DATE - awaitKeys(t, onlySinceTestStartFilter, - otherOrgDataPointExpiringSoon.GetId(), - otherOrgDataPointExpiringLate.GetId(), - otherUserDataPoint.GetId(), - myDataPoint.GetId(), - ) - tests := []testCase{ - { - name: "list all, instance", - args: args{ - IamCTX, - &user.ListKeysRequest{Filters: []*user.KeysSearchFilter{onlySinceTestStartFilter}}, - }, - want: &user.ListKeysResponse{ - Result: []*user.Key{ - otherOrgDataPointExpiringLate, - otherOrgDataPointExpiringSoon, - otherUserDataPoint, - myDataPoint, - }, - Pagination: &filter.PaginationResponse{ - TotalResult: 4, - AppliedLimit: 100, - }, - }, - }, - { - name: "list all, org", - args: args{ - OrgCTX, - &user.ListKeysRequest{Filters: []*user.KeysSearchFilter{onlySinceTestStartFilter}}, - }, - want: &user.ListKeysResponse{ - Result: []*user.Key{ - otherUserDataPoint, - myDataPoint, - }, - Pagination: &filter.PaginationResponse{ - TotalResult: 2, - AppliedLimit: 100, - }, - }, - }, - { - name: "list all, user", - args: args{ - UserCTX, - &user.ListKeysRequest{Filters: []*user.KeysSearchFilter{onlySinceTestStartFilter}}, - }, - want: &user.ListKeysResponse{ - Result: []*user.Key{ - myDataPoint, - }, - Pagination: &filter.PaginationResponse{ - TotalResult: 1, - AppliedLimit: 100, - }, - }, - }, - { - name: "list by id", - args: args{ - IamCTX, - &user.ListKeysRequest{ - Filters: []*user.KeysSearchFilter{ - onlySinceTestStartFilter, - { - Filter: &user.KeysSearchFilter_KeyIdFilter{ - KeyIdFilter: &filter.IDFilter{Id: otherOrgDataPointExpiringSoon.Id}, - }, - }, - }, - }, - }, - want: &user.ListKeysResponse{ - Result: []*user.Key{ - otherOrgDataPointExpiringSoon, - }, - Pagination: &filter.PaginationResponse{ - TotalResult: 1, - AppliedLimit: 100, - }, - }, - }, - { - name: "list all from other org", - args: args{ - IamCTX, - &user.ListKeysRequest{ - Filters: []*user.KeysSearchFilter{ - onlySinceTestStartFilter, - { - Filter: &user.KeysSearchFilter_OrganizationIdFilter{ - OrganizationIdFilter: &filter.IDFilter{Id: otherOrg.OrganizationId}, - }, - }, - }, - }, - }, - want: &user.ListKeysResponse{ - Result: []*user.Key{ - otherOrgDataPointExpiringLate, - otherOrgDataPointExpiringSoon, - }, - Pagination: &filter.PaginationResponse{ - TotalResult: 2, - AppliedLimit: 100, - }, - }, - }, - { - name: "sort by next expiration dates", - args: args{ - IamCTX, - &user.ListKeysRequest{ - Pagination: &filter.PaginationRequest{ - Asc: true, - }, - SortingColumn: &sortingColumnExpirationDate, - Filters: []*user.KeysSearchFilter{ - onlySinceTestStartFilter, - {Filter: &user.KeysSearchFilter_OrganizationIdFilter{OrganizationIdFilter: &filter.IDFilter{Id: otherOrg.OrganizationId}}}, - }, - }, - }, - want: &user.ListKeysResponse{ - Result: []*user.Key{ - otherOrgDataPointExpiringSoon, - otherOrgDataPointExpiringLate, - }, - Pagination: &filter.PaginationResponse{ - TotalResult: 2, - AppliedLimit: 100, - }, - }, - }, - { - name: "get page", - args: args{ - IamCTX, - &user.ListKeysRequest{ - Pagination: &filter.PaginationRequest{ - Offset: 2, - Limit: 2, - Asc: true, - }, - Filters: []*user.KeysSearchFilter{ - onlySinceTestStartFilter, - }, - }, - }, - want: &user.ListKeysResponse{ - Result: []*user.Key{ - otherOrgDataPointExpiringSoon, - otherOrgDataPointExpiringLate, - }, - Pagination: &filter.PaginationResponse{ - TotalResult: 4, - AppliedLimit: 2, - }, - }, - }, - { - name: "empty list", - args: args{ - UserCTX, - &user.ListKeysRequest{ - Filters: []*user.KeysSearchFilter{ - { - Filter: &user.KeysSearchFilter_KeyIdFilter{ - KeyIdFilter: &filter.IDFilter{Id: otherUserDataPoint.Id}, - }, - }, - }, - }, - }, - want: &user.ListKeysResponse{ - Result: []*user.Key{}, - Pagination: &filter.PaginationResponse{ - TotalResult: 0, - AppliedLimit: 100, - }, - }, - }, - } - t.Run("with permission flag v2", func(t *testing.T) { - setPermissionCheckV2Flag(t, true) - defer setPermissionCheckV2Flag(t, false) - for _, tt := range tests { - t.Run(tt.name, func(t *testing.T) { - got, err := Client.ListKeys(tt.args.ctx, tt.args.req) - require.NoError(t, err) - assert.Len(t, got.Result, len(tt.want.Result)) - if diff := cmp.Diff(tt.want, got, protocmp.Transform()); diff != "" { - t.Errorf("ListKeys() mismatch (-want +got):\n%s", diff) - } - }) - } - }) - t.Run("without permission flag v2", func(t *testing.T) { - for _, tt := range tests { - t.Run(tt.name, func(t *testing.T) { - got, err := Client.ListKeys(tt.args.ctx, tt.args.req) - require.NoError(t, err) - assert.Len(t, got.Result, len(tt.want.Result)) - // ignore the total result, as this is a known bug with the in-memory permission checks. - // The command can't know how many keys exist in the system if the SQL statement has a limit. - // This is fixed, once the in-memory permission checks are removed with https://github.com/zitadel/zitadel/issues/9188 - tt.want.Pagination.TotalResult = got.Pagination.TotalResult - if diff := cmp.Diff(tt.want, got, protocmp.Transform()); diff != "" { - t.Errorf("ListKeys() mismatch (-want +got):\n%s", diff) - } - }) - } - }) -} - -func setupKeyDataPoint(t *testing.T, userId, orgId string, expirationDate time.Time) *user.Key { - expirationDatePb := timestamppb.New(expirationDate) - newKey, err := Client.AddKey(SystemCTX, &user.AddKeyRequest{ - UserId: userId, - ExpirationDate: expirationDatePb, - PublicKey: nil, - }) - require.NoError(t, err) - return &user.Key{ - CreationDate: newKey.CreationDate, - ChangeDate: newKey.CreationDate, - Id: newKey.GetKeyId(), - UserId: userId, - OrganizationId: orgId, - ExpirationDate: expirationDatePb, - } -} - -func awaitKeys(t *testing.T, sinceTestStartFilter *user.KeysSearchFilter, keyIds ...string) { - sortingColumn := user.KeyFieldName_KEY_FIELD_NAME_ID - slices.Sort(keyIds) - require.EventuallyWithT(t, func(collect *assert.CollectT) { - result, err := Client.ListKeys(SystemCTX, &user.ListKeysRequest{ - Filters: []*user.KeysSearchFilter{sinceTestStartFilter}, - SortingColumn: &sortingColumn, - Pagination: &filter.PaginationRequest{ - Asc: true, - }, - }) - require.NoError(t, err) - if !assert.Len(collect, result.Result, len(keyIds)) { - return - } - for i := range keyIds { - keyId := keyIds[i] - require.Equal(collect, keyId, result.Result[i].GetId()) - } - }, 5*time.Second, time.Second, "key not created in time") -} diff --git a/internal/api/grpc/user/v2/integration_test/pat_test.go b/internal/api/grpc/user/v2/integration_test/pat_test.go deleted file mode 100644 index ce974e0407..0000000000 --- a/internal/api/grpc/user/v2/integration_test/pat_test.go +++ /dev/null @@ -1,615 +0,0 @@ -//go:build integration - -package user_test - -import ( - "context" - "fmt" - "slices" - "testing" - "time" - - "github.com/brianvoe/gofakeit/v6" - "github.com/google/go-cmp/cmp" - "github.com/stretchr/testify/assert" - "github.com/stretchr/testify/require" - "google.golang.org/protobuf/testing/protocmp" - "google.golang.org/protobuf/types/known/timestamppb" - - "github.com/zitadel/zitadel/internal/integration" - "github.com/zitadel/zitadel/pkg/grpc/filter/v2" - "github.com/zitadel/zitadel/pkg/grpc/user/v2" -) - -func TestServer_AddPersonalAccessToken(t *testing.T) { - resp := Instance.CreateUserTypeMachine(IamCTX) - userId := resp.GetId() - expirationDate := timestamppb.New(time.Now().Add(time.Hour * 24)) - type args struct { - req *user.AddPersonalAccessTokenRequest - prepare func(request *user.AddPersonalAccessTokenRequest) error - } - tests := []struct { - name string - args args - wantErr bool - }{ - { - name: "add pat, user not existing", - args: args{ - &user.AddPersonalAccessTokenRequest{ - UserId: "notexisting", - ExpirationDate: expirationDate, - }, - func(request *user.AddPersonalAccessTokenRequest) error { return nil }, - }, - wantErr: true, - }, - { - name: "add pat, ok", - args: args{ - &user.AddPersonalAccessTokenRequest{ - ExpirationDate: expirationDate, - }, - func(request *user.AddPersonalAccessTokenRequest) error { - request.UserId = userId - return nil - }, - }, - }, - { - name: "add pat human, not ok", - args: args{ - &user.AddPersonalAccessTokenRequest{ - ExpirationDate: expirationDate, - }, - func(request *user.AddPersonalAccessTokenRequest) error { - resp := Instance.CreateUserTypeHuman(IamCTX) - request.UserId = resp.Id - return nil - }, - }, - wantErr: true, - }, - { - name: "add another pat, ok", - args: args{ - &user.AddPersonalAccessTokenRequest{ - ExpirationDate: expirationDate, - }, - func(request *user.AddPersonalAccessTokenRequest) error { - request.UserId = userId - _, err := Client.AddPersonalAccessToken(IamCTX, &user.AddPersonalAccessTokenRequest{ - ExpirationDate: expirationDate, - UserId: userId, - }) - return err - }, - }, - }, - } - for _, tt := range tests { - t.Run(tt.name, func(t *testing.T) { - now := time.Now() - err := tt.args.prepare(tt.args.req) - require.NoError(t, err) - got, err := Client.AddPersonalAccessToken(CTX, tt.args.req) - if tt.wantErr { - require.Error(t, err) - return - } - require.NoError(t, err) - assert.NotEmpty(t, got.TokenId, "id is empty") - assert.NotEmpty(t, got.Token, "token is empty") - creationDate := got.CreationDate.AsTime() - assert.Greater(t, creationDate, now, "creation date is before the test started") - assert.Less(t, creationDate, time.Now(), "creation date is in the future") - }) - } -} - -func TestServer_AddPersonalAccessToken_Permission(t *testing.T) { - OrgCTX := CTX - otherOrg := Instance.CreateOrganization(IamCTX, fmt.Sprintf("AddPersonalAccessToken-%s", gofakeit.AppName()), gofakeit.Email()) - otherOrgUser, err := Client.CreateUser(IamCTX, &user.CreateUserRequest{ - OrganizationId: otherOrg.OrganizationId, - UserType: &user.CreateUserRequest_Machine_{ - Machine: &user.CreateUserRequest_Machine{ - Name: gofakeit.Name(), - }, - }, - }) - require.NoError(t, err) - request := &user.AddPersonalAccessTokenRequest{ - ExpirationDate: timestamppb.New(time.Now().Add(time.Hour * 24)), - UserId: otherOrgUser.GetId(), - } - type args struct { - ctx context.Context - req *user.AddPersonalAccessTokenRequest - } - tests := []struct { - name string - args args - wantErr bool - }{ - { - name: "system, ok", - args: args{SystemCTX, request}, - }, - { - name: "instance, ok", - args: args{IamCTX, request}, - }, - { - name: "org, error", - args: args{OrgCTX, request}, - wantErr: true, - }, - { - name: "user, error", - args: args{UserCTX, request}, - wantErr: true, - }, - } - for _, tt := range tests { - t.Run(tt.name, func(t *testing.T) { - now := time.Now() - require.NoError(t, err) - got, err := Client.AddPersonalAccessToken(tt.args.ctx, tt.args.req) - if tt.wantErr { - require.Error(t, err) - return - } - require.NoError(t, err) - assert.NotEmpty(t, got.TokenId, "id is empty") - assert.NotEmpty(t, got.Token, "token is empty") - creationDate := got.CreationDate.AsTime() - assert.Greater(t, creationDate, now, "creation date is before the test started") - assert.Less(t, creationDate, time.Now(), "creation date is in the future") - }) - } -} - -func TestServer_RemovePersonalAccessToken(t *testing.T) { - resp := Instance.CreateUserTypeMachine(IamCTX) - userId := resp.GetId() - expirationDate := timestamppb.New(time.Now().Add(time.Hour * 24)) - type args struct { - req *user.RemovePersonalAccessTokenRequest - prepare func(request *user.RemovePersonalAccessTokenRequest) error - } - tests := []struct { - name string - args args - wantErr bool - }{ - { - name: "remove pat, user not existing", - args: args{ - &user.RemovePersonalAccessTokenRequest{ - UserId: "notexisting", - }, - func(request *user.RemovePersonalAccessTokenRequest) error { - pat, err := Client.AddPersonalAccessToken(CTX, &user.AddPersonalAccessTokenRequest{ - ExpirationDate: expirationDate, - UserId: userId, - }) - request.TokenId = pat.GetTokenId() - return err - }, - }, - wantErr: true, - }, - { - name: "remove pat, not existing", - args: args{ - &user.RemovePersonalAccessTokenRequest{ - TokenId: "notexisting", - }, - func(request *user.RemovePersonalAccessTokenRequest) error { - request.UserId = userId - return nil - }, - }, - wantErr: true, - }, - { - name: "remove pat, ok", - args: args{ - &user.RemovePersonalAccessTokenRequest{}, - func(request *user.RemovePersonalAccessTokenRequest) error { - pat, err := Client.AddPersonalAccessToken(CTX, &user.AddPersonalAccessTokenRequest{ - ExpirationDate: expirationDate, - UserId: userId, - }) - request.TokenId = pat.GetTokenId() - request.UserId = userId - return err - }, - }, - }, - } - for _, tt := range tests { - t.Run(tt.name, func(t *testing.T) { - now := time.Now() - err := tt.args.prepare(tt.args.req) - require.NoError(t, err) - got, err := Client.RemovePersonalAccessToken(CTX, tt.args.req) - if tt.wantErr { - require.Error(t, err) - return - } - require.NoError(t, err) - deletionDate := got.DeletionDate.AsTime() - assert.Greater(t, deletionDate, now, "creation date is before the test started") - assert.Less(t, deletionDate, time.Now(), "creation date is in the future") - }) - } -} - -func TestServer_RemovePersonalAccessToken_Permission(t *testing.T) { - otherOrg := Instance.CreateOrganization(IamCTX, fmt.Sprintf("RemovePersonalAccessToken-%s", gofakeit.AppName()), gofakeit.Email()) - otherOrgUser, err := Client.CreateUser(IamCTX, &user.CreateUserRequest{ - OrganizationId: otherOrg.OrganizationId, - UserType: &user.CreateUserRequest_Machine_{ - Machine: &user.CreateUserRequest_Machine{ - Name: gofakeit.Name(), - }, - }, - }) - request := &user.RemovePersonalAccessTokenRequest{ - UserId: otherOrgUser.GetId(), - } - prepare := func(request *user.RemovePersonalAccessTokenRequest) error { - pat, err := Client.AddPersonalAccessToken(IamCTX, &user.AddPersonalAccessTokenRequest{ - ExpirationDate: timestamppb.New(time.Now().Add(time.Hour * 24)), - UserId: otherOrgUser.GetId(), - }) - request.TokenId = pat.GetTokenId() - return err - } - require.NoError(t, err) - type args struct { - ctx context.Context - req *user.RemovePersonalAccessTokenRequest - prepare func(request *user.RemovePersonalAccessTokenRequest) error - } - tests := []struct { - name string - args args - wantErr bool - }{ - { - name: "system, ok", - args: args{SystemCTX, request, prepare}, - }, - { - name: "instance, ok", - args: args{IamCTX, request, prepare}, - }, - { - name: "org, error", - args: args{CTX, request, prepare}, - wantErr: true, - }, - { - name: "user, error", - args: args{UserCTX, request, prepare}, - wantErr: true, - }, - } - for _, tt := range tests { - t.Run(tt.name, func(t *testing.T) { - now := time.Now() - require.NoError(t, tt.args.prepare(tt.args.req)) - got, err := Client.RemovePersonalAccessToken(tt.args.ctx, tt.args.req) - if tt.wantErr { - require.Error(t, err) - return - } - require.NoError(t, err) - assert.NotEmpty(t, got.DeletionDate, "client pat is empty") - creationDate := got.DeletionDate.AsTime() - assert.Greater(t, creationDate, now, "creation date is before the test started") - assert.Less(t, creationDate, time.Now(), "creation date is in the future") - }) - } -} - -func TestServer_ListPersonalAccessTokens(t *testing.T) { - type args struct { - ctx context.Context - req *user.ListPersonalAccessTokensRequest - } - type testCase struct { - name string - args args - want *user.ListPersonalAccessTokensResponse - } - OrgCTX := CTX - otherOrg := Instance.CreateOrganization(SystemCTX, fmt.Sprintf("ListPersonalAccessTokens-%s", gofakeit.AppName()), gofakeit.Email()) - otherOrgUser, err := Client.CreateUser(SystemCTX, &user.CreateUserRequest{ - OrganizationId: otherOrg.OrganizationId, - UserType: &user.CreateUserRequest_Machine_{ - Machine: &user.CreateUserRequest_Machine{ - Name: gofakeit.Name(), - }, - }, - }) - require.NoError(t, err) - otherOrgUserId := otherOrgUser.GetId() - otherUserId := Instance.CreateUserTypeMachine(SystemCTX).GetId() - onlySinceTestStartFilter := &user.PersonalAccessTokensSearchFilter{Filter: &user.PersonalAccessTokensSearchFilter_CreatedDateFilter{CreatedDateFilter: &filter.TimestampFilter{ - Timestamp: timestamppb.Now(), - Method: filter.TimestampFilterMethod_TIMESTAMP_FILTER_METHOD_AFTER_OR_EQUALS, - }}} - myOrgId := Instance.DefaultOrg.GetId() - myUserId := Instance.Users.Get(integration.UserTypeNoPermission).ID - expiresInADay := time.Now().Truncate(time.Hour).Add(time.Hour * 24) - myDataPoint := setupPATDataPoint(t, myUserId, myOrgId, expiresInADay) - otherUserDataPoint := setupPATDataPoint(t, otherUserId, myOrgId, expiresInADay) - otherOrgDataPointExpiringSoon := setupPATDataPoint(t, otherOrgUserId, otherOrg.OrganizationId, time.Now().Truncate(time.Hour).Add(time.Hour)) - otherOrgDataPointExpiringLate := setupPATDataPoint(t, otherOrgUserId, otherOrg.OrganizationId, expiresInADay.Add(time.Hour*24*30)) - sortingColumnExpirationDate := user.PersonalAccessTokenFieldName_PERSONAL_ACCESS_TOKEN_FIELD_NAME_EXPIRATION_DATE - awaitPersonalAccessTokens(t, - onlySinceTestStartFilter, - otherOrgDataPointExpiringSoon.GetId(), - otherOrgDataPointExpiringLate.GetId(), - otherUserDataPoint.GetId(), - myDataPoint.GetId(), - ) - tests := []testCase{ - { - name: "list all, instance", - args: args{ - IamCTX, - &user.ListPersonalAccessTokensRequest{ - Filters: []*user.PersonalAccessTokensSearchFilter{onlySinceTestStartFilter}, - }, - }, - want: &user.ListPersonalAccessTokensResponse{ - Result: []*user.PersonalAccessToken{ - otherOrgDataPointExpiringLate, - otherOrgDataPointExpiringSoon, - otherUserDataPoint, - myDataPoint, - }, - Pagination: &filter.PaginationResponse{ - TotalResult: 4, - AppliedLimit: 100, - }, - }, - }, - { - name: "list all, org", - args: args{ - OrgCTX, - &user.ListPersonalAccessTokensRequest{ - Filters: []*user.PersonalAccessTokensSearchFilter{onlySinceTestStartFilter}, - }, - }, - want: &user.ListPersonalAccessTokensResponse{ - Result: []*user.PersonalAccessToken{ - otherUserDataPoint, - myDataPoint, - }, - Pagination: &filter.PaginationResponse{ - TotalResult: 2, - AppliedLimit: 100, - }, - }, - }, - { - name: "list all, user", - args: args{ - UserCTX, - &user.ListPersonalAccessTokensRequest{ - Filters: []*user.PersonalAccessTokensSearchFilter{onlySinceTestStartFilter}, - }, - }, - want: &user.ListPersonalAccessTokensResponse{ - Result: []*user.PersonalAccessToken{ - myDataPoint, - }, - Pagination: &filter.PaginationResponse{ - TotalResult: 1, - AppliedLimit: 100, - }, - }, - }, - { - name: "list by id", - args: args{ - IamCTX, - &user.ListPersonalAccessTokensRequest{ - Filters: []*user.PersonalAccessTokensSearchFilter{ - onlySinceTestStartFilter, - { - Filter: &user.PersonalAccessTokensSearchFilter_TokenIdFilter{ - TokenIdFilter: &filter.IDFilter{Id: otherOrgDataPointExpiringSoon.Id}, - }, - }, - }, - }, - }, - want: &user.ListPersonalAccessTokensResponse{ - Result: []*user.PersonalAccessToken{ - otherOrgDataPointExpiringSoon, - }, - Pagination: &filter.PaginationResponse{ - TotalResult: 1, - AppliedLimit: 100, - }, - }, - }, - { - name: "list all from other org", - args: args{ - IamCTX, - &user.ListPersonalAccessTokensRequest{ - Filters: []*user.PersonalAccessTokensSearchFilter{ - onlySinceTestStartFilter, - { - Filter: &user.PersonalAccessTokensSearchFilter_OrganizationIdFilter{ - OrganizationIdFilter: &filter.IDFilter{Id: otherOrg.OrganizationId}, - }, - }}, - }, - }, - want: &user.ListPersonalAccessTokensResponse{ - Result: []*user.PersonalAccessToken{ - otherOrgDataPointExpiringLate, - otherOrgDataPointExpiringSoon, - }, - Pagination: &filter.PaginationResponse{ - TotalResult: 2, - AppliedLimit: 100, - }, - }, - }, - { - name: "sort by next expiration dates", - args: args{ - IamCTX, - &user.ListPersonalAccessTokensRequest{ - Pagination: &filter.PaginationRequest{ - Asc: true, - }, - SortingColumn: &sortingColumnExpirationDate, - Filters: []*user.PersonalAccessTokensSearchFilter{ - onlySinceTestStartFilter, - {Filter: &user.PersonalAccessTokensSearchFilter_OrganizationIdFilter{OrganizationIdFilter: &filter.IDFilter{Id: otherOrg.OrganizationId}}}, - }, - }, - }, - want: &user.ListPersonalAccessTokensResponse{ - Result: []*user.PersonalAccessToken{ - otherOrgDataPointExpiringSoon, - otherOrgDataPointExpiringLate, - }, - Pagination: &filter.PaginationResponse{ - TotalResult: 2, - AppliedLimit: 100, - }, - }, - }, - { - name: "get page", - args: args{ - IamCTX, - &user.ListPersonalAccessTokensRequest{ - Pagination: &filter.PaginationRequest{ - Offset: 2, - Limit: 2, - Asc: true, - }, - Filters: []*user.PersonalAccessTokensSearchFilter{ - onlySinceTestStartFilter, - }, - }, - }, - want: &user.ListPersonalAccessTokensResponse{ - Result: []*user.PersonalAccessToken{ - otherOrgDataPointExpiringSoon, - otherOrgDataPointExpiringLate, - }, - Pagination: &filter.PaginationResponse{ - TotalResult: 4, - AppliedLimit: 2, - }, - }, - }, - { - name: "empty list", - args: args{ - UserCTX, - &user.ListPersonalAccessTokensRequest{ - Filters: []*user.PersonalAccessTokensSearchFilter{ - { - Filter: &user.PersonalAccessTokensSearchFilter_TokenIdFilter{ - TokenIdFilter: &filter.IDFilter{Id: otherUserDataPoint.Id}, - }, - }, - }, - }, - }, - want: &user.ListPersonalAccessTokensResponse{ - Result: []*user.PersonalAccessToken{}, - Pagination: &filter.PaginationResponse{ - TotalResult: 0, - AppliedLimit: 100, - }, - }, - }, - } - t.Run("with permission flag v2", func(t *testing.T) { - setPermissionCheckV2Flag(t, true) - defer setPermissionCheckV2Flag(t, false) - for _, tt := range tests { - t.Run(tt.name, func(t *testing.T) { - got, err := Client.ListPersonalAccessTokens(tt.args.ctx, tt.args.req) - require.NoError(t, err) - assert.Len(t, got.Result, len(tt.want.Result)) - if diff := cmp.Diff(tt.want, got, protocmp.Transform()); diff != "" { - t.Errorf("ListPersonalAccessTokens() mismatch (-want +got):\n%s", diff) - } - }) - } - }) - t.Run("without permission flag v2", func(t *testing.T) { - for _, tt := range tests { - t.Run(tt.name, func(t *testing.T) { - got, err := Client.ListPersonalAccessTokens(tt.args.ctx, tt.args.req) - require.NoError(t, err) - assert.Len(t, got.Result, len(tt.want.Result)) - // ignore the total result, as this is a known bug with the in-memory permission checks. - // The command can't know how many keys exist in the system if the SQL statement has a limit. - // This is fixed, once the in-memory permission checks are removed with https://github.com/zitadel/zitadel/issues/9188 - tt.want.Pagination.TotalResult = got.Pagination.TotalResult - if diff := cmp.Diff(tt.want, got, protocmp.Transform()); diff != "" { - t.Errorf("ListPersonalAccessTokens() mismatch (-want +got):\n%s", diff) - } - }) - } - }) -} - -func setupPATDataPoint(t *testing.T, userId, orgId string, expirationDate time.Time) *user.PersonalAccessToken { - expirationDatePb := timestamppb.New(expirationDate) - newPersonalAccessToken, err := Client.AddPersonalAccessToken(SystemCTX, &user.AddPersonalAccessTokenRequest{ - UserId: userId, - ExpirationDate: expirationDatePb, - }) - require.NoError(t, err) - return &user.PersonalAccessToken{ - CreationDate: newPersonalAccessToken.CreationDate, - ChangeDate: newPersonalAccessToken.CreationDate, - Id: newPersonalAccessToken.GetTokenId(), - UserId: userId, - OrganizationId: orgId, - ExpirationDate: expirationDatePb, - } -} - -func awaitPersonalAccessTokens(t *testing.T, sinceTestStartFilter *user.PersonalAccessTokensSearchFilter, patIds ...string) { - sortingColumn := user.PersonalAccessTokenFieldName_PERSONAL_ACCESS_TOKEN_FIELD_NAME_ID - slices.Sort(patIds) - require.EventuallyWithT(t, func(collect *assert.CollectT) { - result, err := Client.ListPersonalAccessTokens(SystemCTX, &user.ListPersonalAccessTokensRequest{ - Filters: []*user.PersonalAccessTokensSearchFilter{sinceTestStartFilter}, - SortingColumn: &sortingColumn, - Pagination: &filter.PaginationRequest{ - Asc: true, - }, - }) - require.NoError(t, err) - if !assert.Len(collect, result.Result, len(patIds)) { - return - } - for i := range patIds { - patId := patIds[i] - require.Equal(collect, patId, result.Result[i].GetId()) - } - }, 5*time.Second, time.Second, "pat not created in time") -} diff --git a/internal/api/grpc/user/v2/integration_test/secret_test.go b/internal/api/grpc/user/v2/integration_test/secret_test.go deleted file mode 100644 index 8ff537b1fd..0000000000 --- a/internal/api/grpc/user/v2/integration_test/secret_test.go +++ /dev/null @@ -1,347 +0,0 @@ -//go:build integration - -package user_test - -import ( - "context" - "fmt" - "testing" - "time" - - "github.com/brianvoe/gofakeit/v6" - "github.com/stretchr/testify/assert" - "github.com/stretchr/testify/require" - - "github.com/zitadel/zitadel/pkg/grpc/user/v2" -) - -func TestServer_AddSecret(t *testing.T) { - type args struct { - ctx context.Context - req *user.AddSecretRequest - prepare func(request *user.AddSecretRequest) error - } - tests := []struct { - name string - args args - wantErr bool - }{ - { - name: "add secret, user not existing", - args: args{ - CTX, - &user.AddSecretRequest{ - UserId: "notexisting", - }, - func(request *user.AddSecretRequest) error { return nil }, - }, - wantErr: true, - }, - { - name: "add secret, ok", - args: args{ - CTX, - &user.AddSecretRequest{}, - func(request *user.AddSecretRequest) error { - resp := Instance.CreateUserTypeMachine(CTX) - request.UserId = resp.GetId() - return nil - }, - }, - }, - { - name: "add secret human, not ok", - args: args{ - CTX, - &user.AddSecretRequest{}, - func(request *user.AddSecretRequest) error { - resp := Instance.CreateUserTypeMachine(CTX) - request.UserId = resp.GetId() - return nil - }, - }, - }, - { - name: "overwrite secret, ok", - args: args{ - CTX, - &user.AddSecretRequest{}, - func(request *user.AddSecretRequest) error { - resp := Instance.CreateUserTypeMachine(CTX) - request.UserId = resp.GetId() - _, err := Client.AddSecret(CTX, &user.AddSecretRequest{ - UserId: resp.GetId(), - }) - return err - }, - }, - }, - } - for _, tt := range tests { - t.Run(tt.name, func(t *testing.T) { - now := time.Now() - err := tt.args.prepare(tt.args.req) - require.NoError(t, err) - got, err := Client.AddSecret(tt.args.ctx, tt.args.req) - if tt.wantErr { - require.Error(t, err) - return - } - require.NoError(t, err) - assert.NotEmpty(t, got.ClientSecret, "client secret is empty") - creationDate := got.CreationDate.AsTime() - assert.Greater(t, creationDate, now, "creation date is before the test started") - assert.Less(t, creationDate, time.Now(), "creation date is in the future") - }) - } -} - -func TestServer_AddSecret_Permission(t *testing.T) { - otherOrg := Instance.CreateOrganization(IamCTX, fmt.Sprintf("AddSecret-%s", gofakeit.AppName()), gofakeit.Email()) - otherOrgUser, err := Instance.Client.UserV2.CreateUser(IamCTX, &user.CreateUserRequest{ - OrganizationId: otherOrg.OrganizationId, - UserType: &user.CreateUserRequest_Machine_{ - Machine: &user.CreateUserRequest_Machine{ - Name: gofakeit.Name(), - }, - }, - }) - require.NoError(t, err) - - type args struct { - ctx context.Context - req *user.AddSecretRequest - } - tests := []struct { - name string - args args - wantErr bool - }{ - { - name: "system, ok", - args: args{ - SystemCTX, - &user.AddSecretRequest{ - UserId: otherOrgUser.GetId(), - }, - }, - }, - { - name: "instance, ok", - args: args{ - IamCTX, - &user.AddSecretRequest{ - UserId: otherOrgUser.GetId(), - }, - }, - }, - { - name: "org, error", - args: args{ - CTX, - &user.AddSecretRequest{ - UserId: otherOrgUser.GetId(), - }, - }, - wantErr: true, - }, - { - name: "user, error", - args: args{ - UserCTX, - &user.AddSecretRequest{ - UserId: otherOrgUser.GetId(), - }, - }, - wantErr: true, - }, - } - for _, tt := range tests { - t.Run(tt.name, func(t *testing.T) { - now := time.Now() - require.NoError(t, err) - got, err := Client.AddSecret(tt.args.ctx, tt.args.req) - if tt.wantErr { - require.Error(t, err) - return - } - require.NoError(t, err) - assert.NotEmpty(t, got.ClientSecret, "client secret is empty") - creationDate := got.CreationDate.AsTime() - assert.Greater(t, creationDate, now, "creation date is before the test started") - assert.Less(t, creationDate, time.Now(), "creation date is in the future") - }) - } -} - -func TestServer_RemoveSecret(t *testing.T) { - type args struct { - ctx context.Context - req *user.RemoveSecretRequest - prepare func(request *user.RemoveSecretRequest) error - } - tests := []struct { - name string - args args - wantErr bool - }{ - { - name: "remove secret, user not existing", - args: args{ - CTX, - &user.RemoveSecretRequest{ - UserId: "notexisting", - }, - func(request *user.RemoveSecretRequest) error { return nil }, - }, - wantErr: true, - }, - { - name: "remove secret, not existing", - args: args{ - CTX, - &user.RemoveSecretRequest{}, - func(request *user.RemoveSecretRequest) error { - resp := Instance.CreateUserTypeMachine(CTX) - request.UserId = resp.GetId() - return nil - }, - }, - wantErr: true, - }, - { - name: "remove secret, ok", - args: args{ - CTX, - &user.RemoveSecretRequest{}, - func(request *user.RemoveSecretRequest) error { - resp := Instance.CreateUserTypeMachine(CTX) - request.UserId = resp.GetId() - _, err := Instance.Client.UserV2.AddSecret(CTX, &user.AddSecretRequest{ - UserId: resp.GetId(), - }) - return err - }, - }, - }, - } - for _, tt := range tests { - t.Run(tt.name, func(t *testing.T) { - now := time.Now() - err := tt.args.prepare(tt.args.req) - require.NoError(t, err) - got, err := Client.RemoveSecret(tt.args.ctx, tt.args.req) - if tt.wantErr { - require.Error(t, err) - return - } - require.NoError(t, err) - deletionDate := got.DeletionDate.AsTime() - assert.Greater(t, deletionDate, now, "creation date is before the test started") - assert.Less(t, deletionDate, time.Now(), "creation date is in the future") - }) - } -} - -func TestServer_RemoveSecret_Permission(t *testing.T) { - otherOrg := Instance.CreateOrganization(IamCTX, fmt.Sprintf("RemoveSecret-%s", gofakeit.AppName()), gofakeit.Email()) - otherOrgUser, err := Instance.Client.UserV2.CreateUser(IamCTX, &user.CreateUserRequest{ - OrganizationId: otherOrg.OrganizationId, - UserType: &user.CreateUserRequest_Machine_{ - Machine: &user.CreateUserRequest_Machine{ - Name: gofakeit.Name(), - }, - }, - }) - require.NoError(t, err) - - type args struct { - ctx context.Context - req *user.RemoveSecretRequest - prepare func(request *user.RemoveSecretRequest) error - } - tests := []struct { - name string - args args - wantErr bool - }{ - { - name: "system, ok", - args: args{ - SystemCTX, - &user.RemoveSecretRequest{ - UserId: otherOrgUser.GetId(), - }, - func(request *user.RemoveSecretRequest) error { - _, err := Instance.Client.UserV2.AddSecret(IamCTX, &user.AddSecretRequest{ - UserId: otherOrgUser.GetId(), - }) - return err - }, - }, - }, - { - name: "instance, ok", - args: args{ - IamCTX, - &user.RemoveSecretRequest{ - UserId: otherOrgUser.GetId(), - }, - func(request *user.RemoveSecretRequest) error { - _, err := Instance.Client.UserV2.AddSecret(IamCTX, &user.AddSecretRequest{ - UserId: otherOrgUser.GetId(), - }) - return err - }, - }, - }, - { - name: "org, error", - args: args{ - CTX, - &user.RemoveSecretRequest{ - UserId: otherOrgUser.GetId(), - }, - func(request *user.RemoveSecretRequest) error { - _, err := Instance.Client.UserV2.AddSecret(IamCTX, &user.AddSecretRequest{ - UserId: otherOrgUser.GetId(), - }) - return err - }, - }, - wantErr: true, - }, - { - name: "user, error", - args: args{ - UserCTX, - &user.RemoveSecretRequest{ - UserId: otherOrgUser.GetId(), - }, - func(request *user.RemoveSecretRequest) error { - _, err := Instance.Client.UserV2.AddSecret(IamCTX, &user.AddSecretRequest{ - UserId: otherOrgUser.GetId(), - }) - return err - }, - }, - wantErr: true, - }, - } - for _, tt := range tests { - t.Run(tt.name, func(t *testing.T) { - now := time.Now() - require.NoError(t, tt.args.prepare(tt.args.req)) - got, err := Client.RemoveSecret(tt.args.ctx, tt.args.req) - if tt.wantErr { - require.Error(t, err) - return - } - require.NoError(t, err) - assert.NotEmpty(t, got.DeletionDate, "client secret is empty") - creationDate := got.DeletionDate.AsTime() - assert.Greater(t, creationDate, now, "creation date is before the test started") - assert.Less(t, creationDate, time.Now(), "creation date is in the future") - }) - } -} diff --git a/internal/api/grpc/user/v2/integration_test/user_test.go b/internal/api/grpc/user/v2/integration_test/user_test.go index 4eee44ab44..bb1dc00d0e 100644 --- a/internal/api/grpc/user/v2/integration_test/user_test.go +++ b/internal/api/grpc/user/v2/integration_test/user_test.go @@ -1834,26 +1834,15 @@ func TestServer_DeleteUser(t *testing.T) { args: args{ req: &user.DeleteUserRequest{}, prepare: func(t *testing.T, request *user.DeleteUserRequest) context.Context { - removeUser, err := Client.CreateUser(CTX, &user.CreateUserRequest{ - OrganizationId: Instance.DefaultOrg.Id, - UserType: &user.CreateUserRequest_Human_{ - Human: &user.CreateUserRequest_Human{ - Profile: &user.SetHumanProfile{ - GivenName: "givenName", - FamilyName: "familyName", - }, - Email: &user.SetHumanEmail{ - Email: gofakeit.Email(), - Verification: &user.SetHumanEmail_IsVerified{IsVerified: true}, - }, - }, - }, + removeUser, err := Instance.Client.Mgmt.AddMachineUser(CTX, &mgmt.AddMachineUserRequest{ + UserName: gofakeit.Username(), + Name: gofakeit.Name(), }) + request.UserId = removeUser.UserId require.NoError(t, err) - request.UserId = removeUser.Id - Instance.RegisterUserPasskey(CTX, removeUser.Id) - _, token, _, _ := Instance.CreateVerifiedWebAuthNSession(t, CTX, removeUser.Id) - return integration.WithAuthorizationToken(UserCTX, token) + tokenResp, err := Instance.Client.Mgmt.AddPersonalAccessToken(CTX, &mgmt.AddPersonalAccessTokenRequest{UserId: removeUser.UserId}) + require.NoError(t, err) + return integration.WithAuthorizationToken(UserCTX, tokenResp.Token) }, }, want: &user.DeleteUserResponse{ @@ -3634,1678 +3623,3 @@ func TestServer_HumanMFAInitSkipped(t *testing.T) { }) } } - -func TestServer_CreateUser(t *testing.T) { - type args struct { - ctx context.Context - req *user.CreateUserRequest - } - type testCase struct { - args args - want *user.CreateUserResponse - wantErr bool - } - tests := []struct { - name string - testCase func(runId string) testCase - }{ - { - name: "default verification", - testCase: func(runId string) testCase { - username := fmt.Sprintf("donald.duck+%s", runId) - email := username + "@example.com" - return testCase{ - args: args{ - CTX, - &user.CreateUserRequest{ - OrganizationId: Instance.DefaultOrg.Id, - Username: &username, - UserType: &user.CreateUserRequest_Human_{ - Human: &user.CreateUserRequest_Human{ - Profile: &user.SetHumanProfile{ - GivenName: "Donald", - FamilyName: "Duck", - }, - Email: &user.SetHumanEmail{ - Email: email, - }, - }, - }, - }, - }, - want: &user.CreateUserResponse{ - Id: "is generated", - }, - wantErr: false, - } - }, - }, - { - name: "return email verification code", - testCase: func(runId string) testCase { - username := fmt.Sprintf("donald.duck+%s", runId) - email := username + "@example.com" - return testCase{ - args: args{ - CTX, - &user.CreateUserRequest{ - OrganizationId: Instance.DefaultOrg.Id, - Username: &username, - UserType: &user.CreateUserRequest_Human_{ - Human: &user.CreateUserRequest_Human{ - Profile: &user.SetHumanProfile{ - GivenName: "Donald", - FamilyName: "Duck", - }, - Email: &user.SetHumanEmail{ - Email: email, - Verification: &user.SetHumanEmail_ReturnCode{ - ReturnCode: &user.ReturnEmailVerificationCode{}, - }, - }, - }, - }, - }, - }, - want: &user.CreateUserResponse{ - Id: "is generated", - EmailCode: gu.Ptr("something"), - }, - } - }, - }, - { - name: "custom template", - testCase: func(runId string) testCase { - username := fmt.Sprintf("donald.duck+%s", runId) - email := username + "@example.com" - return testCase{ - args: args{ - CTX, - &user.CreateUserRequest{ - OrganizationId: Instance.DefaultOrg.Id, - Username: &username, - UserType: &user.CreateUserRequest_Human_{ - Human: &user.CreateUserRequest_Human{ - Profile: &user.SetHumanProfile{ - GivenName: "Donald", - FamilyName: "Duck", - }, - Email: &user.SetHumanEmail{ - Email: email, - Verification: &user.SetHumanEmail_SendCode{ - SendCode: &user.SendEmailVerificationCode{ - UrlTemplate: gu.Ptr("https://example.com/email/verify?userID={{.UserID}}&code={{.Code}}&orgID={{.OrgID}}"), - }, - }, - }, - }, - }, - }, - }, - want: &user.CreateUserResponse{ - Id: "is generated", - }, - } - }, - }, - { - name: "return phone verification code", - testCase: func(runId string) testCase { - username := fmt.Sprintf("donald.duck+%s", runId) - email := username + "@example.com" - return testCase{ - args: args{ - CTX, - &user.CreateUserRequest{ - OrganizationId: Instance.DefaultOrg.Id, - Username: &username, - UserType: &user.CreateUserRequest_Human_{ - Human: &user.CreateUserRequest_Human{ - Profile: &user.SetHumanProfile{ - GivenName: "Donald", - FamilyName: "Duck", - }, - Email: &user.SetHumanEmail{ - Email: email, - }, - Phone: &user.SetHumanPhone{ - Phone: "+41791234567", - Verification: &user.SetHumanPhone_ReturnCode{ - ReturnCode: &user.ReturnPhoneVerificationCode{}, - }, - }, - }, - }, - }, - }, - want: &user.CreateUserResponse{ - Id: "is generated", - PhoneCode: gu.Ptr("something"), - }, - } - }, - }, - { - name: "custom template error", - testCase: func(runId string) testCase { - username := fmt.Sprintf("donald.duck+%s", runId) - email := username + "@example.com" - return testCase{ - args: args{ - CTX, - &user.CreateUserRequest{ - OrganizationId: Instance.DefaultOrg.Id, - Username: &username, - UserType: &user.CreateUserRequest_Human_{ - Human: &user.CreateUserRequest_Human{ - Profile: &user.SetHumanProfile{ - GivenName: "Donald", - FamilyName: "Duck", - }, - Email: &user.SetHumanEmail{ - Email: email, - Verification: &user.SetHumanEmail_SendCode{ - SendCode: &user.SendEmailVerificationCode{ - UrlTemplate: gu.Ptr("{{"), - }, - }, - }, - }, - }, - }, - }, - wantErr: true, - } - }, - }, - { - name: "missing REQUIRED profile", - testCase: func(runId string) testCase { - username := fmt.Sprintf("donald.duck+%s", runId) - email := username + "@example.com" - return testCase{ - args: args{ - CTX, - &user.CreateUserRequest{ - OrganizationId: Instance.DefaultOrg.Id, - Username: &username, - UserType: &user.CreateUserRequest_Human_{ - Human: &user.CreateUserRequest_Human{ - Email: &user.SetHumanEmail{ - Email: email, - Verification: &user.SetHumanEmail_ReturnCode{ - ReturnCode: &user.ReturnEmailVerificationCode{}, - }, - }, - }, - }, - }, - }, - wantErr: true, - } - }, - }, - { - name: "missing REQUIRED email", - testCase: func(runId string) testCase { - username := fmt.Sprintf("donald.duck+%s", runId) - return testCase{ - args: args{ - CTX, - &user.CreateUserRequest{ - OrganizationId: Instance.DefaultOrg.Id, - Username: &username, - UserType: &user.CreateUserRequest_Human_{ - Human: &user.CreateUserRequest_Human{ - Profile: &user.SetHumanProfile{ - GivenName: "Donald", - FamilyName: "Duck", - }, - }, - }, - }, - }, - wantErr: true, - } - }, - }, - { - name: "missing empty email", - testCase: func(runId string) testCase { - username := fmt.Sprintf("donald.duck+%s", runId) - return testCase{ - args: args{ - CTX, - &user.CreateUserRequest{ - OrganizationId: Instance.DefaultOrg.Id, - Username: &username, - UserType: &user.CreateUserRequest_Human_{ - Human: &user.CreateUserRequest_Human{ - Profile: &user.SetHumanProfile{ - GivenName: "Donald", - FamilyName: "Duck", - }, - Email: &user.SetHumanEmail{}, - }, - }, - }, - }, - wantErr: true, - } - }, - }, - { - name: "missing idp", - testCase: func(runId string) testCase { - username := fmt.Sprintf("donald.duck+%s", runId) - email := username + "@example.com" - return testCase{ - args: args{ - CTX, - &user.CreateUserRequest{ - OrganizationId: Instance.DefaultOrg.Id, - Username: &username, - UserType: &user.CreateUserRequest_Human_{ - Human: &user.CreateUserRequest_Human{ - Profile: &user.SetHumanProfile{ - GivenName: "Donald", - FamilyName: "Duck", - }, - Email: &user.SetHumanEmail{ - Email: email, - Verification: &user.SetHumanEmail_IsVerified{ - IsVerified: true, - }, - }, - IdpLinks: []*user.IDPLink{ - { - IdpId: "idpID", - UserId: "userID", - UserName: "username", - }, - }, - }, - }, - }, - }, - wantErr: true, - } - }, - }, - { - name: "with idp", - testCase: func(runId string) testCase { - username := fmt.Sprintf("donald.duck+%s", runId) - email := username + "@example.com" - idpResp := Instance.AddGenericOAuthProvider(IamCTX, Instance.DefaultOrg.Id) - return testCase{ - args: args{ - CTX, - &user.CreateUserRequest{ - OrganizationId: Instance.DefaultOrg.Id, - Username: &username, - UserType: &user.CreateUserRequest_Human_{ - Human: &user.CreateUserRequest_Human{ - Profile: &user.SetHumanProfile{ - GivenName: "Donald", - FamilyName: "Duck", - }, - Email: &user.SetHumanEmail{ - Email: email, - Verification: &user.SetHumanEmail_IsVerified{ - IsVerified: true, - }, - }, - IdpLinks: []*user.IDPLink{ - { - IdpId: idpResp.Id, - UserId: "userID", - UserName: "username", - }, - }, - }, - }, - }, - }, - want: &user.CreateUserResponse{ - Id: "is generated", - }, - } - }, - }, - { - name: "with totp", - testCase: func(runId string) testCase { - username := fmt.Sprintf("donald.duck+%s", runId) - email := username + "@example.com" - return testCase{ - args: args{ - CTX, - &user.CreateUserRequest{ - OrganizationId: Instance.DefaultOrg.Id, - Username: &username, - UserType: &user.CreateUserRequest_Human_{ - Human: &user.CreateUserRequest_Human{ - Profile: &user.SetHumanProfile{ - GivenName: "Donald", - FamilyName: "Duck", - }, - Email: &user.SetHumanEmail{ - Email: email, - Verification: &user.SetHumanEmail_IsVerified{ - IsVerified: true, - }, - }, - TotpSecret: gu.Ptr("secret"), - }, - }, - }, - }, - want: &user.CreateUserResponse{ - Id: "is generated", - }, - } - }, - }, - { - name: "password not complexity conform", - testCase: func(runId string) testCase { - username := fmt.Sprintf("donald.duck+%s", runId) - email := username + "@example.com" - return testCase{ - args: args{ - CTX, - &user.CreateUserRequest{ - OrganizationId: Instance.DefaultOrg.Id, - Username: &username, - UserType: &user.CreateUserRequest_Human_{ - Human: &user.CreateUserRequest_Human{ - Profile: &user.SetHumanProfile{ - GivenName: "Donald", - FamilyName: "Duck", - NickName: gu.Ptr("Dukkie"), - DisplayName: gu.Ptr("Donald Duck"), - PreferredLanguage: gu.Ptr("en"), - Gender: user.Gender_GENDER_DIVERSE.Enum(), - }, - Email: &user.SetHumanEmail{ - Email: email, - }, - PasswordType: &user.CreateUserRequest_Human_Password{ - Password: &user.Password{ - Password: "insufficient", - }, - }, - }, - }, - }, - }, - wantErr: true, - } - }, - }, - { - name: "hashed password", - testCase: func(runId string) testCase { - username := fmt.Sprintf("donald.duck+%s", runId) - email := username + "@example.com" - return testCase{ - args: args{ - CTX, - &user.CreateUserRequest{ - OrganizationId: Instance.DefaultOrg.Id, - Username: &username, - UserType: &user.CreateUserRequest_Human_{ - Human: &user.CreateUserRequest_Human{ - Profile: &user.SetHumanProfile{ - GivenName: "Donald", - FamilyName: "Duck", - }, - Email: &user.SetHumanEmail{ - Email: email, - }, - PasswordType: &user.CreateUserRequest_Human_HashedPassword{ - HashedPassword: &user.HashedPassword{ - Hash: "$2y$12$hXUrnqdq1RIIYZ2HPytIIe5lXdIvbhqrTvdPsSF7o.jFh817Z6lwm", - }, - }, - }, - }, - }, - }, - want: &user.CreateUserResponse{ - Id: "is generated", - }, - } - }, - }, - { - name: "unsupported hashed password", - testCase: func(runId string) testCase { - username := fmt.Sprintf("donald.duck+%s", runId) - email := username + "@example.com" - return testCase{ - args: args{ - CTX, - &user.CreateUserRequest{ - OrganizationId: Instance.DefaultOrg.Id, - Username: &username, - UserType: &user.CreateUserRequest_Human_{ - Human: &user.CreateUserRequest_Human{ - Profile: &user.SetHumanProfile{ - GivenName: "Donald", - FamilyName: "Duck", - }, - Email: &user.SetHumanEmail{ - Email: email, - }, - PasswordType: &user.CreateUserRequest_Human_HashedPassword{ - HashedPassword: &user.HashedPassword{ - Hash: "$scrypt$ln=16,r=8,p=1$cmFuZG9tc2FsdGlzaGFyZA$Rh+NnJNo1I6nRwaNqbDm6kmADswD1+7FTKZ7Ln9D8nQ", - }, - }, - }, - }, - }, - }, - wantErr: true, - } - }, - }, - { - name: "human default username", - testCase: func(runId string) testCase { - username := fmt.Sprintf("donald.duck+%s", runId) - email := username + "@example.com" - return testCase{ - args: args{ - CTX, - &user.CreateUserRequest{ - OrganizationId: Instance.DefaultOrg.Id, - UserType: &user.CreateUserRequest_Human_{ - Human: &user.CreateUserRequest_Human{ - Profile: &user.SetHumanProfile{ - GivenName: "Donald", - FamilyName: "Duck", - }, - Email: &user.SetHumanEmail{ - Email: email, - }, - }, - }, - }, - }, - want: &user.CreateUserResponse{ - Id: "is generated", - }, - } - }, - }, - { - name: "machine user", - testCase: func(runId string) testCase { - username := fmt.Sprintf("donald.duck+%s", runId) - return testCase{ - args: args{ - CTX, - &user.CreateUserRequest{ - OrganizationId: Instance.DefaultOrg.Id, - Username: &username, - UserType: &user.CreateUserRequest_Machine_{ - Machine: &user.CreateUserRequest_Machine{ - Name: "donald", - }, - }, - }, - }, - want: &user.CreateUserResponse{ - Id: "is generated", - }, - } - }, - }, - { - name: "machine default username to generated id", - testCase: func(runId string) testCase { - return testCase{ - args: args{ - CTX, - &user.CreateUserRequest{ - OrganizationId: Instance.DefaultOrg.Id, - UserType: &user.CreateUserRequest_Machine_{ - Machine: &user.CreateUserRequest_Machine{ - Name: "donald", - }, - }, - }, - }, - want: &user.CreateUserResponse{ - Id: "is generated", - }, - } - }, - }, - { - name: "machine default username to given id", - testCase: func(runId string) testCase { - return testCase{ - args: args{ - CTX, - &user.CreateUserRequest{ - UserId: &runId, - OrganizationId: Instance.DefaultOrg.Id, - UserType: &user.CreateUserRequest_Machine_{ - Machine: &user.CreateUserRequest_Machine{ - Name: "donald", - }, - }, - }, - }, - want: &user.CreateUserResponse{ - Id: runId, - }, - } - }, - }, - { - name: "org does not exist human, error", - testCase: func(runId string) testCase { - username := fmt.Sprintf("donald.duck+%s", runId) - email := username + "@example.com" - return testCase{ - args: args{ - CTX, - &user.CreateUserRequest{ - OrganizationId: "does not exist", - Username: &username, - UserType: &user.CreateUserRequest_Human_{ - Human: &user.CreateUserRequest_Human{ - Profile: &user.SetHumanProfile{ - GivenName: "Donald", - FamilyName: "Duck", - }, - Email: &user.SetHumanEmail{ - Email: email, - }, - }, - }, - }, - }, - wantErr: true, - } - }, - }, - { - name: "org does not exist machine, error", - testCase: func(runId string) testCase { - username := fmt.Sprintf("donald.duck+%s", runId) - return testCase{ - args: args{ - CTX, - &user.CreateUserRequest{ - OrganizationId: "does not exist", - Username: &username, - UserType: &user.CreateUserRequest_Machine_{ - Machine: &user.CreateUserRequest_Machine{ - Name: gofakeit.Name(), - }, - }, - }, - }, - wantErr: true, - } - }, - }, - } - for i, tt := range tests { - t.Run(tt.name, func(t *testing.T) { - now := time.Now() - runId := fmt.Sprint(now.UnixNano() + int64(i)) - test := tt.testCase(runId) - got, err := Client.CreateUser(test.args.ctx, test.args.req) - if test.wantErr { - require.Error(t, err) - return - } - require.NoError(t, err) - creationDate := got.CreationDate.AsTime() - assert.Greater(t, creationDate, now, "creation date is before the test started") - assert.Less(t, creationDate, time.Now(), "creation date is in the future") - if test.want.GetEmailCode() != "" { - assert.NotEmpty(t, got.GetEmailCode(), "email code is empty") - } else { - assert.Empty(t, got.GetEmailCode(), "email code is not empty") - } - if test.want.GetPhoneCode() != "" { - assert.NotEmpty(t, got.GetPhoneCode(), "phone code is empty") - } else { - assert.Empty(t, got.GetPhoneCode(), "phone code is not empty") - } - if test.want.GetId() == "is generated" { - assert.Len(t, got.GetId(), 18, "ID is not 18 characters") - } else { - assert.Equal(t, test.want.GetId(), got.GetId(), "ID is not the same") - } - }) - } -} - -func TestServer_CreateUser_And_Compare(t *testing.T) { - type args struct { - ctx context.Context - req *user.CreateUserRequest - } - type testCase struct { - name string - args args - assert func(t *testing.T, createResponse *user.CreateUserResponse, getResponse *user.GetUserByIDResponse) - } - tests := []struct { - name string - testCase func(runId string) testCase - }{{ - name: "human given username", - testCase: func(runId string) testCase { - username := fmt.Sprintf("donald.duck+%s", runId) - email := username + "@example.com" - return testCase{ - args: args{ - ctx: CTX, - req: &user.CreateUserRequest{ - OrganizationId: Instance.DefaultOrg.Id, - Username: &username, - UserType: &user.CreateUserRequest_Human_{ - Human: &user.CreateUserRequest_Human{ - Profile: &user.SetHumanProfile{ - GivenName: "Donald", - FamilyName: "Duck", - }, - Email: &user.SetHumanEmail{ - Email: email, - }, - }, - }, - }, - }, - assert: func(t *testing.T, _ *user.CreateUserResponse, getResponse *user.GetUserByIDResponse) { - assert.Equal(t, username, getResponse.GetUser().GetUsername()) - }, - } - }, - }, { - name: "human username default to email", - testCase: func(runId string) testCase { - username := fmt.Sprintf("donald.duck+%s", runId) - email := username + "@example.com" - return testCase{ - args: args{ - ctx: CTX, - req: &user.CreateUserRequest{ - OrganizationId: Instance.DefaultOrg.Id, - UserType: &user.CreateUserRequest_Human_{ - Human: &user.CreateUserRequest_Human{ - Profile: &user.SetHumanProfile{ - GivenName: "Donald", - FamilyName: "Duck", - }, - Email: &user.SetHumanEmail{ - Email: email, - }, - }, - }, - }, - }, - assert: func(t *testing.T, _ *user.CreateUserResponse, getResponse *user.GetUserByIDResponse) { - assert.Equal(t, email, getResponse.GetUser().GetUsername()) - }, - } - }, - }, { - name: "machine username given", - testCase: func(runId string) testCase { - username := fmt.Sprintf("donald.duck+%s", runId) - return testCase{ - args: args{ - ctx: CTX, - req: &user.CreateUserRequest{ - OrganizationId: Instance.DefaultOrg.Id, - Username: &username, - UserType: &user.CreateUserRequest_Machine_{ - Machine: &user.CreateUserRequest_Machine{ - Name: "donald", - }, - }, - }, - }, - assert: func(t *testing.T, _ *user.CreateUserResponse, getResponse *user.GetUserByIDResponse) { - assert.Equal(t, username, getResponse.GetUser().GetUsername()) - }, - } - }, - }, { - name: "machine username default to generated id", - testCase: func(runId string) testCase { - return testCase{ - args: args{ - ctx: CTX, - req: &user.CreateUserRequest{ - OrganizationId: Instance.DefaultOrg.Id, - UserType: &user.CreateUserRequest_Machine_{ - Machine: &user.CreateUserRequest_Machine{ - Name: "donald", - }, - }, - }, - }, - assert: func(t *testing.T, createResponse *user.CreateUserResponse, getResponse *user.GetUserByIDResponse) { - assert.Equal(t, createResponse.GetId(), getResponse.GetUser().GetUsername()) - }, - } - }, - }, { - name: "machine username default to given id", - testCase: func(runId string) testCase { - return testCase{ - args: args{ - ctx: CTX, - req: &user.CreateUserRequest{ - OrganizationId: Instance.DefaultOrg.Id, - UserId: &runId, - UserType: &user.CreateUserRequest_Machine_{ - Machine: &user.CreateUserRequest_Machine{ - Name: "donald", - }, - }, - }, - }, - assert: func(t *testing.T, createResponse *user.CreateUserResponse, getResponse *user.GetUserByIDResponse) { - assert.Equal(t, runId, getResponse.GetUser().GetUsername()) - }, - } - }, - }} - for i, tt := range tests { - t.Run(tt.name, func(t *testing.T) { - now := time.Now() - runId := fmt.Sprint(now.UnixNano() + int64(i)) - test := tt.testCase(runId) - createResponse, err := Client.CreateUser(test.args.ctx, test.args.req) - require.NoError(t, err) - Instance.TriggerUserByID(test.args.ctx, createResponse.GetId()) - getResponse, err := Client.GetUserByID(test.args.ctx, &user.GetUserByIDRequest{ - UserId: createResponse.GetId(), - }) - require.NoError(t, err) - test.assert(t, createResponse, getResponse) - }) - } -} - -func TestServer_CreateUser_Permission(t *testing.T) { - newOrgOwnerEmail := gofakeit.Email() - newOrg := Instance.CreateOrganization(IamCTX, fmt.Sprintf("AddHuman-%s", gofakeit.AppName()), newOrgOwnerEmail) - type args struct { - ctx context.Context - req *user.CreateUserRequest - } - tests := []struct { - name string - args args - wantErr bool - }{ - { - name: "human system, ok", - args: args{ - SystemCTX, - &user.CreateUserRequest{ - OrganizationId: newOrg.GetOrganizationId(), - UserType: &user.CreateUserRequest_Human_{ - Human: &user.CreateUserRequest_Human{ - Profile: &user.SetHumanProfile{ - GivenName: "Donald", - FamilyName: "Duck", - }, - Email: &user.SetHumanEmail{ - Email: "this is overwritten with a unique address", - }, - }, - }, - }, - }, - }, - { - name: "human instance, ok", - args: args{ - IamCTX, - &user.CreateUserRequest{ - OrganizationId: newOrg.GetOrganizationId(), - UserType: &user.CreateUserRequest_Human_{ - Human: &user.CreateUserRequest_Human{ - Profile: &user.SetHumanProfile{ - GivenName: "Donald", - FamilyName: "Duck", - }, - Email: &user.SetHumanEmail{ - Email: "this is overwritten with a unique address", - }, - }, - }, - }, - }, - }, - { - name: "human org, error", - args: args{ - CTX, - &user.CreateUserRequest{ - OrganizationId: newOrg.GetOrganizationId(), - UserType: &user.CreateUserRequest_Human_{ - Human: &user.CreateUserRequest_Human{ - Profile: &user.SetHumanProfile{ - GivenName: "Donald", - FamilyName: "Duck", - }, - Email: &user.SetHumanEmail{ - Email: "this is overwritten with a unique address", - }, - }, - }, - }, - }, - wantErr: true, - }, - { - name: "human user, error", - args: args{ - UserCTX, - &user.CreateUserRequest{ - OrganizationId: newOrg.GetOrganizationId(), - UserType: &user.CreateUserRequest_Human_{ - Human: &user.CreateUserRequest_Human{ - Profile: &user.SetHumanProfile{ - GivenName: "Donald", - FamilyName: "Duck", - }, - Email: &user.SetHumanEmail{ - Email: "this is overwritten with a unique address", - }, - }, - }, - }, - }, - wantErr: true, - }, - { - name: "machine system, ok", - args: args{ - SystemCTX, - &user.CreateUserRequest{ - OrganizationId: newOrg.GetOrganizationId(), - UserType: &user.CreateUserRequest_Machine_{ - Machine: &user.CreateUserRequest_Machine{ - Name: "donald", - }, - }, - }, - }, - }, - { - name: "machine instance, ok", - args: args{ - IamCTX, - &user.CreateUserRequest{ - OrganizationId: newOrg.GetOrganizationId(), - UserType: &user.CreateUserRequest_Machine_{ - Machine: &user.CreateUserRequest_Machine{ - Name: "donald", - }, - }, - }, - }, - }, - { - name: "machine org, error", - args: args{ - CTX, - &user.CreateUserRequest{ - OrganizationId: newOrg.GetOrganizationId(), - UserType: &user.CreateUserRequest_Machine_{ - Machine: &user.CreateUserRequest_Machine{ - Name: "donald", - }, - }, - }, - }, - wantErr: true, - }, - { - name: "machine user, error", - args: args{ - UserCTX, - &user.CreateUserRequest{ - OrganizationId: newOrg.GetOrganizationId(), - UserType: &user.CreateUserRequest_Machine_{ - Machine: &user.CreateUserRequest_Machine{ - Name: "donald", - }, - }, - }, - }, - wantErr: true, - }, - } - for i, tt := range tests { - t.Run(tt.name, func(t *testing.T) { - userID := fmt.Sprint(time.Now().UnixNano() + int64(i)) - tt.args.req.UserId = &userID - if email := tt.args.req.GetHuman().GetEmail(); email != nil { - email.Email = fmt.Sprintf("%s@example.com", userID) - } - _, err := Client.CreateUser(tt.args.ctx, tt.args.req) - if tt.wantErr { - require.Error(t, err) - return - } - require.NoError(t, err) - }) - } -} - -func TestServer_UpdateUserTypeHuman(t *testing.T) { - type args struct { - ctx context.Context - req *user.UpdateUserRequest - } - type testCase struct { - args args - want *user.UpdateUserResponse - wantErr bool - } - tests := []struct { - name string - testCase func(runId, userId string) testCase - }{ - { - name: "default verification", - testCase: func(runId, userId string) testCase { - username := fmt.Sprintf("donald.duck+%s", runId) - email := username + "@example.com" - return testCase{ - args: args{ - CTX, - &user.UpdateUserRequest{ - UserId: userId, - UserType: &user.UpdateUserRequest_Human_{ - Human: &user.UpdateUserRequest_Human{ - Email: &user.SetHumanEmail{ - Email: email, - }, - }, - }, - }, - }, - want: &user.UpdateUserResponse{}, - wantErr: false, - } - }, - }, - { - name: "return email verification code", - testCase: func(runId, userId string) testCase { - username := fmt.Sprintf("donald.duck+%s", runId) - email := username + "@example.com" - return testCase{ - args: args{ - CTX, - &user.UpdateUserRequest{ - UserId: userId, - UserType: &user.UpdateUserRequest_Human_{ - Human: &user.UpdateUserRequest_Human{ - Email: &user.SetHumanEmail{ - Email: email, - Verification: &user.SetHumanEmail_ReturnCode{ - ReturnCode: &user.ReturnEmailVerificationCode{}, - }, - }, - }, - }, - }, - }, - want: &user.UpdateUserResponse{ - EmailCode: gu.Ptr("something"), - }, - } - }, - }, - { - name: "custom template", - testCase: func(runId, userId string) testCase { - username := fmt.Sprintf("donald.duck+%s", runId) - email := username + "@example.com" - return testCase{ - args: args{ - CTX, - &user.UpdateUserRequest{ - UserId: userId, - UserType: &user.UpdateUserRequest_Human_{ - Human: &user.UpdateUserRequest_Human{ - Email: &user.SetHumanEmail{ - Email: email, - Verification: &user.SetHumanEmail_SendCode{ - SendCode: &user.SendEmailVerificationCode{ - UrlTemplate: gu.Ptr("https://example.com/email/verify?userID={{.UserID}}&code={{.Code}}&orgID={{.OrgID}}"), - }, - }, - }, - }, - }, - }, - }, - want: &user.UpdateUserResponse{}, - } - }, - }, - { - name: "return phone verification code", - testCase: func(runId, userId string) testCase { - return testCase{ - args: args{ - CTX, - &user.UpdateUserRequest{ - UserId: userId, - UserType: &user.UpdateUserRequest_Human_{ - Human: &user.UpdateUserRequest_Human{ - Phone: &user.SetHumanPhone{ - Phone: "+41791234568", - Verification: &user.SetHumanPhone_ReturnCode{ - ReturnCode: &user.ReturnPhoneVerificationCode{}, - }, - }, - }, - }, - }, - }, - want: &user.UpdateUserResponse{ - PhoneCode: gu.Ptr("something"), - }, - } - }, - }, - { - name: "custom template error", - testCase: func(runId, userId string) testCase { - username := fmt.Sprintf("donald.duck+%s", runId) - email := username + "@example.com" - return testCase{ - args: args{ - CTX, - &user.UpdateUserRequest{ - UserId: userId, - UserType: &user.UpdateUserRequest_Human_{ - Human: &user.UpdateUserRequest_Human{ - Email: &user.SetHumanEmail{ - Email: email, - Verification: &user.SetHumanEmail_SendCode{ - SendCode: &user.SendEmailVerificationCode{ - UrlTemplate: gu.Ptr("{{"), - }, - }, - }, - }, - }, - }, - }, - wantErr: true, - } - }, - }, - { - name: "missing empty email", - testCase: func(runId, userId string) testCase { - return testCase{ - args: args{ - CTX, - &user.UpdateUserRequest{ - UserId: userId, - UserType: &user.UpdateUserRequest_Human_{ - Human: &user.UpdateUserRequest_Human{ - Email: &user.SetHumanEmail{}, - }, - }, - }, - }, - wantErr: true, - } - }, - }, - { - name: "password not complexity conform", - testCase: func(runId, userId string) testCase { - return testCase{ - args: args{ - CTX, - &user.UpdateUserRequest{ - UserId: userId, - UserType: &user.UpdateUserRequest_Human_{ - Human: &user.UpdateUserRequest_Human{ - Password: &user.SetPassword{ - PasswordType: &user.SetPassword_Password{ - Password: &user.Password{ - Password: "insufficient", - }, - }, - }, - }, - }, - }, - }, - wantErr: true, - } - }, - }, - { - name: "hashed password", - testCase: func(runId, userId string) testCase { - return testCase{ - args: args{ - CTX, - &user.UpdateUserRequest{ - UserId: userId, - UserType: &user.UpdateUserRequest_Human_{ - Human: &user.UpdateUserRequest_Human{ - Password: &user.SetPassword{ - PasswordType: &user.SetPassword_HashedPassword{ - HashedPassword: &user.HashedPassword{ - Hash: "$2y$12$hXUrnqdq1RIIYZ2HPytIIe5lXdIvbhqrTvdPsSF7o.jFh817Z6lwm", - }, - }, - }, - }, - }, - }, - }, - want: &user.UpdateUserResponse{}, - } - }, - }, - { - name: "unsupported hashed password", - testCase: func(runId, userId string) testCase { - return testCase{ - args: args{ - CTX, - &user.UpdateUserRequest{ - UserId: userId, - UserType: &user.UpdateUserRequest_Human_{ - Human: &user.UpdateUserRequest_Human{ - Password: &user.SetPassword{ - PasswordType: &user.SetPassword_HashedPassword{ - HashedPassword: &user.HashedPassword{ - Hash: "$scrypt$ln=16,r=8,p=1$cmFuZG9tc2FsdGlzaGFyZA$Rh+NnJNo1I6nRwaNqbDm6kmADswD1+7FTKZ7Ln9D8nQ", - }, - }, - }, - }, - }, - }, - }, - wantErr: true, - } - }, - }, - { - name: "update human user with machine fields, error", - testCase: func(runId, userId string) testCase { - return testCase{ - args: args{ - CTX, - &user.UpdateUserRequest{ - UserId: userId, - UserType: &user.UpdateUserRequest_Machine_{ - Machine: &user.UpdateUserRequest_Machine{ - Name: &runId, - }, - }, - }, - }, - wantErr: true, - } - }, - }, - } - for i, tt := range tests { - t.Run(tt.name, func(t *testing.T) { - now := time.Now() - runId := fmt.Sprint(now.UnixNano() + int64(i)) - userId := Instance.CreateUserTypeHuman(CTX).GetId() - test := tt.testCase(runId, userId) - got, err := Client.UpdateUser(test.args.ctx, test.args.req) - if test.wantErr { - require.Error(t, err) - return - } - require.NoError(t, err) - changeDate := got.ChangeDate.AsTime() - assert.Greater(t, changeDate, now, "change date is before the test started") - assert.Less(t, changeDate, time.Now(), "change date is in the future") - if test.want.GetEmailCode() != "" { - assert.NotEmpty(t, got.GetEmailCode(), "email code is empty") - } else { - assert.Empty(t, got.GetEmailCode(), "email code is not empty") - } - if test.want.GetPhoneCode() != "" { - assert.NotEmpty(t, got.GetPhoneCode(), "phone code is empty") - } else { - assert.Empty(t, got.GetPhoneCode(), "phone code is not empty") - } - }) - } -} - -func TestServer_UpdateUserTypeMachine(t *testing.T) { - type args struct { - ctx context.Context - req *user.UpdateUserRequest - } - type testCase struct { - args args - wantErr bool - } - tests := []struct { - name string - testCase func(runId, userId string) testCase - }{ - { - name: "update machine, ok", - testCase: func(runId, userId string) testCase { - return testCase{ - args: args{ - CTX, - &user.UpdateUserRequest{ - UserId: userId, - UserType: &user.UpdateUserRequest_Machine_{ - Machine: &user.UpdateUserRequest_Machine{ - Name: gu.Ptr("donald"), - }, - }, - }, - }, - } - }, - }, - { - name: "update machine user with human fields, error", - testCase: func(runId, userId string) testCase { - return testCase{ - args: args{ - CTX, - &user.UpdateUserRequest{ - UserId: userId, - UserType: &user.UpdateUserRequest_Human_{ - Human: &user.UpdateUserRequest_Human{ - Profile: &user.UpdateUserRequest_Human_Profile{ - GivenName: gu.Ptr("Donald"), - }, - }, - }, - }, - }, - wantErr: true, - } - }, - }, - } - for i, tt := range tests { - t.Run(tt.name, func(t *testing.T) { - now := time.Now() - runId := fmt.Sprint(now.UnixNano() + int64(i)) - userId := Instance.CreateUserTypeMachine(CTX).GetId() - test := tt.testCase(runId, userId) - got, err := Client.UpdateUser(test.args.ctx, test.args.req) - if test.wantErr { - require.Error(t, err) - return - } - require.NoError(t, err) - changeDate := got.ChangeDate.AsTime() - assert.Greater(t, changeDate, now, "change date is before the test started") - assert.Less(t, changeDate, time.Now(), "change date is in the future") - }) - } -} - -func TestServer_UpdateUser_And_Compare(t *testing.T) { - type args struct { - ctx context.Context - create *user.CreateUserRequest - update *user.UpdateUserRequest - } - type testCase struct { - args args - assert func(t *testing.T, getResponse *user.GetUserByIDResponse) - } - tests := []struct { - name string - testCase func(runId string) testCase - }{{ - name: "human remove phone", - testCase: func(runId string) testCase { - username := fmt.Sprintf("donald.duck+%s", runId) - email := username + "@example.com" - return testCase{ - args: args{ - ctx: CTX, - create: &user.CreateUserRequest{ - OrganizationId: Instance.DefaultOrg.Id, - UserId: &runId, - UserType: &user.CreateUserRequest_Human_{ - Human: &user.CreateUserRequest_Human{ - Profile: &user.SetHumanProfile{ - GivenName: "Donald", - FamilyName: "Duck", - }, - Email: &user.SetHumanEmail{ - Email: email, - }, - Phone: &user.SetHumanPhone{ - Phone: "+1234567890", - }, - }, - }, - }, - update: &user.UpdateUserRequest{ - UserId: runId, - UserType: &user.UpdateUserRequest_Human_{ - Human: &user.UpdateUserRequest_Human{ - Phone: &user.SetHumanPhone{}, - }, - }, - }, - }, - assert: func(t *testing.T, getResponse *user.GetUserByIDResponse) { - assert.Empty(t, getResponse.GetUser().GetHuman().GetPhone().GetPhone(), "phone is not empty") - }, - } - }, - }, { - name: "human username", - testCase: func(runId string) testCase { - username := fmt.Sprintf("donald.duck+%s", runId) - email := username + "@example.com" - return testCase{ - args: args{ - ctx: CTX, - create: &user.CreateUserRequest{ - OrganizationId: Instance.DefaultOrg.Id, - UserId: &runId, - UserType: &user.CreateUserRequest_Human_{ - Human: &user.CreateUserRequest_Human{ - Profile: &user.SetHumanProfile{ - GivenName: "Donald", - FamilyName: "Duck", - }, - Email: &user.SetHumanEmail{ - Email: email, - }, - }, - }, - }, - update: &user.UpdateUserRequest{ - UserId: runId, - Username: &username, - UserType: &user.UpdateUserRequest_Human_{ - Human: &user.UpdateUserRequest_Human{}, - }, - }, - }, - assert: func(t *testing.T, getResponse *user.GetUserByIDResponse) { - assert.Equal(t, username, getResponse.GetUser().GetUsername()) - }, - } - }, - }, { - name: "machine username", - testCase: func(runId string) testCase { - username := fmt.Sprintf("donald.duck+%s", runId) - return testCase{ - args: args{ - ctx: CTX, - create: &user.CreateUserRequest{ - OrganizationId: Instance.DefaultOrg.Id, - UserId: &runId, - UserType: &user.CreateUserRequest_Machine_{ - Machine: &user.CreateUserRequest_Machine{ - Name: "Donald", - }, - }, - }, - update: &user.UpdateUserRequest{ - UserId: runId, - Username: &username, - UserType: &user.UpdateUserRequest_Machine_{ - Machine: &user.UpdateUserRequest_Machine{}, - }, - }, - }, - assert: func(t *testing.T, getResponse *user.GetUserByIDResponse) { - assert.Equal(t, username, getResponse.GetUser().GetUsername()) - }, - } - }, - }} - for i, tt := range tests { - t.Run(tt.name, func(t *testing.T) { - now := time.Now() - runId := fmt.Sprint(now.UnixNano() + int64(i)) - test := tt.testCase(runId) - createResponse, err := Client.CreateUser(test.args.ctx, test.args.create) - require.NoError(t, err) - _, err = Client.UpdateUser(test.args.ctx, test.args.update) - require.NoError(t, err) - Instance.TriggerUserByID(test.args.ctx, createResponse.GetId()) - getResponse, err := Client.GetUserByID(test.args.ctx, &user.GetUserByIDRequest{ - UserId: createResponse.GetId(), - }) - require.NoError(t, err) - test.assert(t, getResponse) - }) - } -} - -func TestServer_UpdateUser_Permission(t *testing.T) { - newOrgOwnerEmail := gofakeit.Email() - newOrg := Instance.CreateOrganization(IamCTX, fmt.Sprintf("AddHuman-%s", gofakeit.AppName()), newOrgOwnerEmail) - newHumanUserID := newOrg.CreatedAdmins[0].GetUserId() - machineUserResp, err := Instance.Client.UserV2.CreateUser(IamCTX, &user.CreateUserRequest{ - OrganizationId: newOrg.OrganizationId, - UserType: &user.CreateUserRequest_Machine_{ - Machine: &user.CreateUserRequest_Machine{ - Name: "Donald", - }, - }, - }) - require.NoError(t, err) - newMachineUserID := machineUserResp.GetId() - Instance.TriggerUserByID(IamCTX, newMachineUserID) - type args struct { - ctx context.Context - req *user.UpdateUserRequest - } - type testCase struct { - args args - wantErr bool - } - tests := []struct { - name string - testCase func() testCase - }{ - { - name: "human, system, ok", - testCase: func() testCase { - return testCase{ - args: args{ - SystemCTX, - &user.UpdateUserRequest{ - UserId: newHumanUserID, - UserType: &user.UpdateUserRequest_Human_{ - Human: &user.UpdateUserRequest_Human{ - Profile: &user.UpdateUserRequest_Human_Profile{ - GivenName: gu.Ptr("Donald"), - }, - }, - }, - }, - }, - } - }, - }, - { - name: "human instance, ok", - testCase: func() testCase { - return testCase{ - args: args{ - IamCTX, - &user.UpdateUserRequest{ - UserId: newHumanUserID, - UserType: &user.UpdateUserRequest_Human_{ - Human: &user.UpdateUserRequest_Human{ - Profile: &user.UpdateUserRequest_Human_Profile{ - GivenName: gu.Ptr("Donald"), - }, - }, - }, - }, - }, - } - }, - }, - { - name: "human org, error", - testCase: func() testCase { - return testCase{ - args: args{ - CTX, - &user.UpdateUserRequest{ - UserId: newHumanUserID, - UserType: &user.UpdateUserRequest_Human_{ - Human: &user.UpdateUserRequest_Human{ - Profile: &user.UpdateUserRequest_Human_Profile{ - GivenName: gu.Ptr("Donald"), - }, - }, - }, - }, - }, - wantErr: true, - } - }, - }, - { - name: "human user, error", - testCase: func() testCase { - return testCase{ - args: args{ - UserCTX, - &user.UpdateUserRequest{ - UserId: newHumanUserID, - UserType: &user.UpdateUserRequest_Human_{ - Human: &user.UpdateUserRequest_Human{ - Profile: &user.UpdateUserRequest_Human_Profile{ - GivenName: gu.Ptr("Donald"), - }, - }, - }, - }, - }, - wantErr: true, - } - }, - }, - { - name: "machine system, ok", - testCase: func() testCase { - return testCase{ - args: args{ - SystemCTX, - &user.UpdateUserRequest{ - UserId: newMachineUserID, - UserType: &user.UpdateUserRequest_Machine_{ - Machine: &user.UpdateUserRequest_Machine{ - Name: gu.Ptr("Donald"), - }, - }, - }, - }, - } - }, - }, - { - name: "machine instance, ok", - testCase: func() testCase { - return testCase{ - args: args{ - IamCTX, - &user.UpdateUserRequest{ - UserId: newMachineUserID, - UserType: &user.UpdateUserRequest_Machine_{ - Machine: &user.UpdateUserRequest_Machine{ - Name: gu.Ptr("Donald"), - }, - }, - }, - }, - } - }, - }, - { - name: "machine org, error", - testCase: func() testCase { - return testCase{ - args: args{ - CTX, - &user.UpdateUserRequest{ - UserId: newMachineUserID, - UserType: &user.UpdateUserRequest_Machine_{ - Machine: &user.UpdateUserRequest_Machine{ - Name: gu.Ptr("Donald"), - }, - }, - }, - }, - wantErr: true, - } - }, - }, - { - name: "machine user, error", - testCase: func() testCase { - return testCase{ - args: args{ - UserCTX, - &user.UpdateUserRequest{ - UserId: newMachineUserID, - UserType: &user.UpdateUserRequest_Machine_{ - Machine: &user.UpdateUserRequest_Machine{ - Name: gu.Ptr("Donald"), - }, - }, - }, - }, - wantErr: true, - } - }, - }, - } - for _, tt := range tests { - t.Run(tt.name, func(t *testing.T) { - test := tt.testCase() - _, err := Client.UpdateUser(test.args.ctx, test.args.req) - if test.wantErr { - require.Error(t, err) - return - } - require.NoError(t, err) - }) - } -} diff --git a/internal/integration/client.go b/internal/integration/client.go index 20c98b5628..f30e504c72 100644 --- a/internal/integration/client.go +++ b/internal/integration/client.go @@ -233,45 +233,8 @@ func (i *Instance) CreateHumanUserWithTOTP(ctx context.Context, secret string) * return resp } -func (i *Instance) CreateUserTypeHuman(ctx context.Context) *user_v2.CreateUserResponse { - resp, err := i.Client.UserV2.CreateUser(ctx, &user_v2.CreateUserRequest{ - OrganizationId: i.DefaultOrg.GetId(), - UserType: &user_v2.CreateUserRequest_Human_{ - Human: &user_v2.CreateUserRequest_Human{ - Profile: &user_v2.SetHumanProfile{ - GivenName: "Mickey", - FamilyName: "Mouse", - }, - Email: &user_v2.SetHumanEmail{ - Email: fmt.Sprintf("%d@mouse.com", time.Now().UnixNano()), - Verification: &user_v2.SetHumanEmail_ReturnCode{ - ReturnCode: &user_v2.ReturnEmailVerificationCode{}, - }, - }, - }, - }, - }) - logging.OnError(err).Panic("create human user") - i.TriggerUserByID(ctx, resp.GetId()) - return resp -} - -func (i *Instance) CreateUserTypeMachine(ctx context.Context) *user_v2.CreateUserResponse { - resp, err := i.Client.UserV2.CreateUser(ctx, &user_v2.CreateUserRequest{ - OrganizationId: i.DefaultOrg.GetId(), - UserType: &user_v2.CreateUserRequest_Machine_{ - Machine: &user_v2.CreateUserRequest_Machine{ - Name: "machine", - }, - }, - }) - logging.OnError(err).Panic("create machine user") - i.TriggerUserByID(ctx, resp.GetId()) - return resp -} - -func (i *Instance) CreatePersonalAccessToken(ctx context.Context, userID string) *user_v2.AddPersonalAccessTokenResponse { - resp, err := i.Client.UserV2.AddPersonalAccessToken(ctx, &user_v2.AddPersonalAccessTokenRequest{ +func (i *Instance) CreatePersonalAccessToken(ctx context.Context, userID string) *mgmt.AddPersonalAccessTokenResponse { + resp, err := i.Client.Mgmt.AddPersonalAccessToken(ctx, &mgmt.AddPersonalAccessTokenRequest{ UserId: userID, ExpirationDate: timestamppb.New(time.Now().Add(30 * time.Minute)), })