package command import ( "context" "testing" "time" "github.com/stretchr/testify/assert" "github.com/zitadel/zitadel/internal/domain" "github.com/zitadel/zitadel/internal/eventstore" "github.com/zitadel/zitadel/internal/repository/project" "github.com/zitadel/zitadel/internal/zerrors" ) func TestCommandSide_ChangeApplicationSecret(t *testing.T) { t.Parallel() type fields struct { eventstore func(*testing.T) *eventstore.Eventstore } type args struct { ctx context.Context appID string projectID string resourceOwner string } type res struct { wantSecret string wantChangeDate time.Time err error } tests := []struct { name string fields fields args args res res }{ { name: "no projectid, invalid argument error", fields: fields{ eventstore: expectEventstore(), }, args: args{ ctx: context.Background(), appID: "app1", resourceOwner: "org1", }, res: res{ err: zerrors.ThrowInvalidArgument(nil, "COMMAND-KJ29c", "Errors.IDMissing"), }, }, { name: "no appid, invalid argument error", fields: fields{ eventstore: expectEventstore(), }, args: args{ ctx: context.Background(), projectID: "project1", appID: "", resourceOwner: "org1", }, res: res{ err: zerrors.ThrowInvalidArgumentf(nil, "COMMAND-KJ29c", "Errors.IDMissing"), }, }, { name: "app not existing, not found error", fields: fields{ eventstore: expectEventstore( expectFilter(), ), }, args: args{ ctx: context.Background(), projectID: "project1", appID: "app1", resourceOwner: "org1", }, res: res{ err: zerrors.ThrowNotFound(nil, "COMMAND-Kd92s", "Errors.Project.App.NotExisting"), }, }, { name: "change secret (OIDC), ok", fields: fields{ eventstore: expectEventstore( expectFilter( eventFromEventPusher( project.NewApplicationAddedEvent(context.Background(), &project.NewAggregate("project1", "org1").Aggregate, "app1", "app", ), ), eventFromEventPusher( project.NewOIDCConfigAddedEvent(context.Background(), &project.NewAggregate("project1", "org1").Aggregate, domain.OIDCVersionV1, "app1", "client1@project", "secret", []string{"https://test.ch"}, []domain.OIDCResponseType{domain.OIDCResponseTypeCode}, []domain.OIDCGrantType{domain.OIDCGrantTypeAuthorizationCode}, domain.OIDCApplicationTypeWeb, domain.OIDCAuthMethodTypePost, []string{"https://test.ch/logout"}, true, domain.OIDCTokenTypeBearer, true, true, true, time.Second*1, []string{"https://sub.test.ch"}, false, "", domain.LoginVersionUnspecified, "", ), ), ), expectPush( project.NewOIDCConfigSecretChangedEvent(context.Background(), &project.NewAggregate("project1", "org1").Aggregate, "app1", "secret", ), ), ), }, args: args{ ctx: context.Background(), projectID: "project1", appID: "app1", resourceOwner: "org1", }, res: res{ wantSecret: "secret", }, }, { name: "change secret (API), ok", fields: fields{ eventstore: expectEventstore( expectFilter( eventFromEventPusher( project.NewApplicationAddedEvent(context.Background(), &project.NewAggregate("project1", "org1").Aggregate, "app1", "app", ), ), eventFromEventPusher( project.NewAPIConfigAddedEvent(context.Background(), &project.NewAggregate("project1", "org1").Aggregate, "app1", "client1@project", "secret", domain.APIAuthMethodTypeBasic, ), ), ), expectPush( project.NewAPIConfigSecretChangedEvent(context.Background(), &project.NewAggregate("project1", "org1").Aggregate, "app1", "secret", ), ), ), }, args: args{ ctx: context.Background(), projectID: "project1", appID: "app1", resourceOwner: "org1", }, res: res{ wantSecret: "secret", }, }, } for _, tt := range tests { t.Run(tt.name, func(t *testing.T) { t.Parallel() r := &Commands{ eventstore: tt.fields.eventstore(t), newHashedSecret: mockHashedSecret("secret"), defaultSecretGenerators: &SecretGenerators{ ClientSecret: emptyConfig, }, checkPermission: newMockPermissionCheckAllowed(), } now := time.Now() gotSecret, gotChangeDate, err := r.ChangeApplicationSecret(tt.args.ctx, tt.args.projectID, tt.args.appID, tt.args.resourceOwner) assert.ErrorIs(t, err, tt.res.err) assert.Equal(t, tt.res.wantSecret, gotSecret) if tt.res.wantChangeDate != (time.Time{}) { assert.WithinRange(t, gotChangeDate, now, time.Now()) } }) } }