feat: add ldap external idp to login api (#5938)

* fix: handling of ldap login through separate endpoint

* fix: handling of ldap login through separate endpoint

* fix: handling of ldap login through separate endpoint

* fix: successful intent for ldap

* fix: successful intent for ldap

* fix: successful intent for ldap

* fix: add changes from code review

* fix: remove set intent credentials and handle ldap errors

* fix: remove set intent credentials and handle ldap errors

* refactor into separate methods and fix merge

* remove mocks

---------

Co-authored-by: Livio Spring <livio.a@gmail.com>
This commit is contained in:
Stefan Benz
2023-08-16 13:29:57 +02:00
committed by GitHub
parent 1b923425cd
commit 52f68f8db8
27 changed files with 726 additions and 149 deletions

View File

@@ -10,6 +10,7 @@ import (
"github.com/stretchr/testify/require"
"github.com/zitadel/oidc/v2/pkg/oidc"
"golang.org/x/oauth2"
"golang.org/x/text/language"
"github.com/zitadel/zitadel/internal/api/authz"
"github.com/zitadel/zitadel/internal/crypto"
@@ -199,9 +200,13 @@ func TestCommands_CreateIntent(t *testing.T) {
eventstore: tt.fields.eventstore,
idGenerator: tt.fields.idGenerator,
}
intentID, details, err := c.CreateIntent(tt.args.ctx, tt.args.idpID, tt.args.successURL, tt.args.failureURL, tt.args.resourceOwner)
intentWriteModel, details, err := c.CreateIntent(tt.args.ctx, tt.args.idpID, tt.args.successURL, tt.args.failureURL, tt.args.resourceOwner)
require.ErrorIs(t, err, tt.res.err)
assert.Equal(t, tt.res.intentID, intentID)
if intentWriteModel != nil {
assert.Equal(t, tt.res.intentID, intentWriteModel.AggregateID)
} else {
assert.Equal(t, tt.res.intentID, "")
}
assert.Equal(t, tt.res.details, details)
})
}
@@ -580,6 +585,103 @@ func TestCommands_SucceedIDPIntent(t *testing.T) {
}
}
func TestCommands_SucceedLDAPIDPIntent(t *testing.T) {
type fields struct {
eventstore *eventstore.Eventstore
idpConfigEncryption crypto.EncryptionAlgorithm
}
type args struct {
ctx context.Context
writeModel *IDPIntentWriteModel
idpUser idp.User
userID string
attributes map[string][]string
}
type res struct {
token string
err error
}
tests := []struct {
name string
fields fields
args args
res res
}{
{
"encryption fails",
fields{
idpConfigEncryption: func() crypto.EncryptionAlgorithm {
m := crypto.NewMockEncryptionAlgorithm(gomock.NewController(t))
m.EXPECT().Encrypt(gomock.Any()).Return(nil, z_errors.ThrowInternal(nil, "id", "encryption failed"))
return m
}(),
},
args{
ctx: context.Background(),
writeModel: NewIDPIntentWriteModel("id", "ro"),
},
res{
err: z_errors.ThrowInternal(nil, "id", "encryption failed"),
},
},
{
"push",
fields{
idpConfigEncryption: crypto.CreateMockEncryptionAlg(gomock.NewController(t)),
eventstore: eventstoreExpect(t,
expectPush(
eventPusherToEvents(
idpintent.NewLDAPSucceededEvent(
context.Background(),
&idpintent.NewAggregate("id", "ro").Aggregate,
[]byte(`{"id":"id","preferredUsername":"username","preferredLanguage":"und"}`),
"id",
"username",
"",
map[string][]string{"id": {"id"}},
),
),
),
),
},
args{
ctx: context.Background(),
writeModel: NewIDPIntentWriteModel("id", "ro"),
attributes: map[string][]string{"id": {"id"}},
idpUser: ldap.NewUser(
"id",
"",
"",
"",
"",
"username",
"",
false,
"",
false,
language.Tag{},
"",
"",
),
},
res{
token: "aWQ",
},
},
}
for _, tt := range tests {
t.Run(tt.name, func(t *testing.T) {
c := &Commands{
eventstore: tt.fields.eventstore,
idpConfigEncryption: tt.fields.idpConfigEncryption,
}
got, err := c.SucceedLDAPIDPIntent(tt.args.ctx, tt.args.writeModel, tt.args.idpUser, tt.args.userID, tt.args.attributes)
require.ErrorIs(t, err, tt.res.err)
assert.Equal(t, tt.res.token, got)
})
}
}
func TestCommands_FailIDPIntent(t *testing.T) {
type fields struct {
eventstore *eventstore.Eventstore