This commit is contained in:
adlerhurst
2020-11-25 20:04:32 +01:00
parent f6cdcee77a
commit 4bb9650f27
32 changed files with 1070 additions and 215 deletions

View File

@@ -17,9 +17,6 @@ const (
type Aggregate struct {
eventstore.Aggregate
// SetUpStarted Step
// SetUpDone Step
}
func NewAggregate(
@@ -54,8 +51,6 @@ func AggregateFromReadModel(rm *ReadModel) *Aggregate {
AggregateVersion,
rm.ProcessedSequence,
),
// SetUpDone: rm.SetUpDone,
// SetUpStarted: rm.SetUpStarted,
}
}
@@ -82,3 +77,13 @@ func (a *Aggregate) PushMemberRemoved(ctx context.Context, userID string) *Aggre
a.Aggregate = *a.PushEvents(NewMemberRemovedEvent(ctx, userID))
return a
}
func (a *Aggregate) PushStepStarted(ctx context.Context, step Step) *Aggregate {
a.Aggregate = *a.PushEvents(NewSetupStepStartedEvent(ctx, step))
return a
}
func (a *Aggregate) PushStepDone(ctx context.Context, step Step) *Aggregate {
a.Aggregate = *a.PushEvents(NewSetupStepDoneEvent(ctx, step))
return a
}

View File

@@ -0,0 +1,192 @@
package iam
import (
"context"
"github.com/caos/zitadel/internal/eventstore/v2"
"github.com/caos/zitadel/internal/v2/repository/idp"
"github.com/caos/zitadel/internal/v2/repository/idp/oidc"
)
const (
IDPConfigAddedEventType eventstore.EventType = "iam.idp.config.added"
IDPConfigChangedEventType eventstore.EventType = "iam.idp.config.changed"
IDPConfigRemovedEventType eventstore.EventType = "iam.idp.config.removed"
IDPConfigDeactivatedEventType eventstore.EventType = "iam.idp.config.deactivated"
IDPConfigReactivatedEventType eventstore.EventType = "iam.idp.config.reactivated"
)
type IDPConfigReadModel struct {
idp.ConfigReadModel
}
func (rm *IDPConfigReadModel) AppendEvents(events ...eventstore.EventReader) {
for _, event := range events {
switch e := event.(type) {
case *IDPConfigAddedEvent:
rm.ConfigReadModel.AppendEvents(&e.ConfigAddedEvent)
case *IDPConfigChangedEvent:
rm.ConfigReadModel.AppendEvents(&e.ConfigChangedEvent)
case *IDPConfigDeactivatedEvent:
rm.ConfigReadModel.AppendEvents(&e.ConfigDeactivatedEvent)
case *IDPConfigReactivatedEvent:
rm.ConfigReadModel.AppendEvents(&e.ConfigReactivatedEvent)
case *IDPConfigRemovedEvent:
rm.ConfigReadModel.AppendEvents(&e.ConfigRemovedEvent)
case *idp.ConfigAddedEvent,
*idp.ConfigChangedEvent,
*idp.ConfigDeactivatedEvent,
*idp.ConfigReactivatedEvent,
*idp.ConfigRemovedEvent,
*oidc.ConfigAddedEvent,
*oidc.ConfigChangedEvent:
rm.ConfigReadModel.AppendEvents(e)
}
}
}
type IDPConfigWriteModel struct {
idp.ConfigWriteModel
}
func (rm *IDPConfigWriteModel) AppendEvents(events ...eventstore.EventReader) {
for _, event := range events {
switch e := event.(type) {
case *IDPConfigAddedEvent:
rm.ConfigWriteModel.AppendEvents(&e.ConfigAddedEvent)
case *IDPConfigChangedEvent:
rm.ConfigWriteModel.AppendEvents(&e.ConfigChangedEvent)
case *IDPConfigDeactivatedEvent:
rm.ConfigWriteModel.AppendEvents(&e.ConfigDeactivatedEvent)
case *IDPConfigReactivatedEvent:
rm.ConfigWriteModel.AppendEvents(&e.ConfigReactivatedEvent)
case *IDPConfigRemovedEvent:
rm.ConfigWriteModel.AppendEvents(&e.ConfigRemovedEvent)
case *idp.ConfigAddedEvent,
*idp.ConfigChangedEvent,
*idp.ConfigDeactivatedEvent,
*idp.ConfigReactivatedEvent,
*idp.ConfigRemovedEvent:
rm.ConfigWriteModel.AppendEvents(e)
}
}
}
type IDPConfigAddedEvent struct {
idp.ConfigAddedEvent
}
func NewIDPConfigAddedEvent(
ctx context.Context,
configID string,
name string,
configType idp.ConfigType,
stylingType idp.StylingType,
) *IDPConfigAddedEvent {
return &IDPConfigAddedEvent{
ConfigAddedEvent: *idp.NewConfigAddedEvent(
eventstore.NewBaseEventForPush(
ctx,
IDPConfigAddedEventType,
),
configID,
name,
configType,
stylingType,
),
}
}
type IDPConfigChangedEvent struct {
idp.ConfigChangedEvent
}
func NewIDPConfigChangedEvent(
ctx context.Context,
current *IDPConfigWriteModel,
configID string,
name string,
configType idp.ConfigType,
stylingType idp.StylingType,
) (*IDPConfigChangedEvent, error) {
event, err := idp.NewConfigChangedEvent(
eventstore.NewBaseEventForPush(
ctx,
IDPConfigChangedEventType,
),
&current.ConfigWriteModel,
name,
stylingType,
)
if err != nil {
return nil, err
}
return &IDPConfigChangedEvent{
ConfigChangedEvent: *event,
}, nil
}
type IDPConfigRemovedEvent struct {
idp.ConfigRemovedEvent
}
func NewIDPConfigRemovedEvent(
ctx context.Context,
configID string,
) *IDPConfigRemovedEvent {
return &IDPConfigRemovedEvent{
ConfigRemovedEvent: *idp.NewConfigRemovedEvent(
eventstore.NewBaseEventForPush(
ctx,
IDPConfigRemovedEventType,
),
configID,
),
}
}
type IDPConfigDeactivatedEvent struct {
idp.ConfigDeactivatedEvent
}
func NewIDPConfigDeactivatedEvent(
ctx context.Context,
configID string,
) *IDPConfigDeactivatedEvent {
return &IDPConfigDeactivatedEvent{
ConfigDeactivatedEvent: *idp.NewConfigDeactivatedEvent(
eventstore.NewBaseEventForPush(
ctx,
IDPConfigDeactivatedEventType,
),
configID,
),
}
}
type IDPConfigReactivatedEvent struct {
idp.ConfigReactivatedEvent
}
func NewIDPConfigReactivatedEvent(
ctx context.Context,
configID string,
) *IDPConfigReactivatedEvent {
return &IDPConfigReactivatedEvent{
ConfigReactivatedEvent: *idp.NewConfigReactivatedEvent(
eventstore.NewBaseEventForPush(
ctx,
IDPConfigReactivatedEventType,
),
configID,
),
}
}

View File

@@ -0,0 +1,104 @@
package iam
import (
"context"
"github.com/caos/zitadel/internal/crypto"
"github.com/caos/zitadel/internal/eventstore/v2"
"github.com/caos/zitadel/internal/v2/repository/idp/oidc"
)
const (
IDPOIDCConfigAddedEventType eventstore.EventType = "iam.idp.oidc.config.added"
IDPOIDCConfigChangedEventType eventstore.EventType = "iam.idp.oidc.config.changed"
)
type IDPOIDCConfigWriteModel struct {
oidc.ConfigWriteModel
}
func (rm *IDPOIDCConfigWriteModel) AppendEvents(events ...eventstore.EventReader) {
for _, event := range events {
switch e := event.(type) {
case *IDPOIDCConfigAddedEvent:
rm.ConfigWriteModel.AppendEvents(&e.ConfigAddedEvent)
case *IDPOIDCConfigChangedEvent:
rm.ConfigWriteModel.AppendEvents(&e.ConfigChangedEvent)
case *oidc.ConfigAddedEvent,
*oidc.ConfigChangedEvent:
rm.ConfigWriteModel.AppendEvents(e)
}
}
}
type IDPOIDCConfigAddedEvent struct {
oidc.ConfigAddedEvent
}
func NewIDPOIDCConfigAddedEvent(
ctx context.Context,
clientID,
idpConfigID,
issuer string,
clientSecret *crypto.CryptoValue,
idpDisplayNameMapping,
userNameMapping oidc.MappingField,
scopes ...string,
) *IDPOIDCConfigAddedEvent {
return &IDPOIDCConfigAddedEvent{
ConfigAddedEvent: *oidc.NewConfigAddedEvent(
eventstore.NewBaseEventForPush(
ctx,
IDPOIDCConfigAddedEventType,
),
clientID,
idpConfigID,
issuer,
clientSecret,
idpDisplayNameMapping,
userNameMapping,
scopes...,
),
}
}
type IDPOIDCConfigChangedEvent struct {
oidc.ConfigChangedEvent
}
func NewIDPOIDCConfigChangedEvent(
ctx context.Context,
current *IDPOIDCConfigWriteModel,
clientID,
idpConfigID,
issuer string,
clientSecret *crypto.CryptoValue,
idpDisplayNameMapping,
userNameMapping oidc.MappingField,
scopes ...string,
) (*IDPOIDCConfigChangedEvent, error) {
event, err := oidc.NewConfigChangedEvent(
eventstore.NewBaseEventForPush(
ctx,
IDPOIDCConfigAddedEventType,
),
&current.ConfigWriteModel,
clientID,
issuer,
clientSecret,
idpDisplayNameMapping,
userNameMapping,
scopes...,
)
if err != nil {
return nil, err
}
return &IDPOIDCConfigChangedEvent{
ConfigChangedEvent: *event,
}, nil
}

View File

@@ -87,7 +87,7 @@ func MemberChangedEventFromExisting(
roles ...string,
) (*MemberChangedEvent, error) {
m, err := member.ChangeEventFromExisting(
event, err := member.ChangeEventFromExisting(
eventstore.NewBaseEventForPush(
ctx,
MemberChangedEventType,
@@ -100,7 +100,7 @@ func MemberChangedEventFromExisting(
}
return &MemberChangedEvent{
ChangedEvent: *m,
ChangedEvent: *event,
}, nil
}

View File

@@ -89,9 +89,7 @@ func (rm *ReadModel) Reduce() (err error) {
}
func (rm *ReadModel) AppendAndReduce(events ...eventstore.EventReader) error {
if err := rm.AppendEvents(events...); err != nil {
return err
}
rm.AppendEvents(events...)
return rm.Reduce()
}

View File

@@ -2,37 +2,10 @@ package idp
import (
"github.com/caos/zitadel/internal/eventstore/v2"
"github.com/caos/zitadel/internal/v2/repository/idp/oidc"
)
type ConfigAggregate struct {
eventstore.Aggregate
ConfigID string
Type ConfigType
Name string
StylingType StylingType
State ConfigState
// OIDCConfig *oidc.ConfigReadModel
}
type ConfigReadModel struct {
eventstore.ReadModel
ConfigID string
Type ConfigType
Name string
StylingType StylingType
State ConfigState
OIDCConfig *oidc.ConfigReadModel
}
func (rm *ConfigReadModel) AppendEvents(events ...eventstore.EventReader) {
rm.ReadModel.AppendEvents(events...)
}
func (rm *ConfigReadModel) Reduce() error {
return nil
}
type ConfigType int32
@@ -40,19 +13,50 @@ type ConfigType int32
const (
ConfigTypeOIDC ConfigType = iota
ConfigTypeSAML
//count is for validation
configTypeCount
)
func (f ConfigType) Valid() bool {
return f >= 0 && f < configTypeCount
}
type ConfigState int32
const (
ConfigStateActive ConfigState = iota
ConfigStateInactive
ConfigStateRemoved
configStateCount
)
func (f ConfigState) Valid() bool {
return f >= 0 && f < configStateCount
}
type StylingType int32
const (
StylingTypeUnspecified StylingType = iota
StylingTypeGoogle
StylingTypeGoogle StylingType = iota + 1
stylingTypeCount
)
func (f StylingType) Valid() bool {
return f >= 0 && f < stylingTypeCount
}
type ProviderType int8
const (
ProviderTypeSystem ProviderType = iota
ProviderTypeOrg
providerTypeCount
)
func (f ProviderType) Valid() bool {
return f >= 0 && f < providerTypeCount
}

View File

@@ -0,0 +1,64 @@
package idp
import (
"github.com/caos/zitadel/internal/eventstore/v2"
"github.com/caos/zitadel/internal/v2/repository/idp/oidc"
)
type ConfigReadModel struct {
eventstore.ReadModel
Type ConfigType
State ConfigState
ConfigID string
Name string
StylingType StylingType
ProviderType ProviderType
OIDCConfig *oidc.ConfigReadModel
}
func (rm *ConfigReadModel) AppendEvents(events ...eventstore.EventReader) {
rm.ReadModel.AppendEvents(events...)
for _, event := range events {
switch event.(type) {
case *oidc.ConfigAddedEvent:
rm.OIDCConfig = &oidc.ConfigReadModel{}
rm.OIDCConfig.AppendEvents(event)
case *oidc.ConfigChangedEvent:
rm.OIDCConfig.AppendEvents(event)
}
}
}
func (rm *ConfigReadModel) Reduce() error {
for _, event := range rm.Events {
switch e := event.(type) {
case *ConfigAddedEvent:
rm.ConfigID = e.ConfigID
rm.Name = e.Name
rm.StylingType = e.StylingType
rm.State = ConfigStateActive
case *ConfigChangedEvent:
if e.Name != "" {
rm.Name = e.Name
}
if e.StylingType.Valid() {
rm.StylingType = e.StylingType
}
case *ConfigDeactivatedEvent:
rm.State = ConfigStateInactive
case *ConfigReactivatedEvent:
rm.State = ConfigStateActive
case *ConfigRemovedEvent:
rm.State = ConfigStateRemoved
case *oidc.ConfigAddedEvent:
rm.Type = ConfigTypeOIDC
}
}
if err := rm.OIDCConfig.Reduce(); err != nil {
return err
}
return rm.ReadModel.Reduce()
}

View File

@@ -0,0 +1,50 @@
package idp
import (
"github.com/caos/zitadel/internal/eventstore/v2"
"github.com/caos/zitadel/internal/v2/repository/idp/oidc"
)
type ConfigWriteModel struct {
eventstore.WriteModel
ConfigID string
Name string
StylingType StylingType
OIDCConfig *oidc.ConfigWriteModel
}
func (rm *ConfigWriteModel) AppendEvents(events ...eventstore.EventReader) {
rm.WriteModel.AppendEvents(events...)
for _, event := range events {
switch event.(type) {
case *oidc.ConfigAddedEvent:
rm.OIDCConfig = &oidc.ConfigWriteModel{}
rm.OIDCConfig.AppendEvents(event)
case *oidc.ConfigChangedEvent:
rm.OIDCConfig.AppendEvents(event)
}
}
}
func (rm *ConfigWriteModel) Reduce() error {
for _, event := range rm.Events {
switch e := event.(type) {
case *ConfigAddedEvent:
rm.ConfigID = e.ConfigID
rm.Name = e.Name
rm.StylingType = e.StylingType
case *ConfigChangedEvent:
if e.Name != "" {
rm.Name = e.Name
}
if e.StylingType.Valid() {
rm.StylingType = e.StylingType
}
}
}
if err := rm.OIDCConfig.Reduce(); err != nil {
return err
}
return rm.WriteModel.Reduce()
}

View File

@@ -1,17 +1,23 @@
package idp
import "github.com/caos/zitadel/internal/eventstore/v2"
import (
"encoding/json"
"github.com/caos/zitadel/internal/errors"
"github.com/caos/zitadel/internal/eventstore/v2"
"github.com/caos/zitadel/internal/eventstore/v2/repository"
)
type ConfigAddedEvent struct {
eventstore.BaseEvent
eventstore.BaseEvent `json:"-"`
ID string `json:"idpConfigId"`
ConfigID string `json:"idpConfigId"`
Name string `json:"name"`
Type ConfigType `json:"idpType,omitempty"`
Typ ConfigType `json:"idpType,omitempty"`
StylingType StylingType `json:"stylingType,omitempty"`
}
func NewAddedEvent(
func NewConfigAddedEvent(
base *eventstore.BaseEvent,
configID string,
name string,
@@ -21,10 +27,10 @@ func NewAddedEvent(
return &ConfigAddedEvent{
BaseEvent: *base,
ID: configID,
ConfigID: configID,
Name: name,
StylingType: stylingType,
Type: configType,
Typ: configType,
}
}
@@ -36,6 +42,15 @@ func (e *ConfigAddedEvent) Data() interface{} {
return e
}
type ConfigType uint32
func ConfigAddedEventMapper(event *repository.Event) (eventstore.EventReader, error) {
e := &ConfigAddedEvent{
BaseEvent: *eventstore.BaseEventFromRepo(event),
}
type StylingType uint32
err := json.Unmarshal(event.Data, e)
if err != nil {
return nil, errors.ThrowInternal(err, "OIDC-plaBZ", "unable to unmarshal event")
}
return e, nil
}

View File

@@ -1,40 +1,44 @@
package idp
import (
"encoding/json"
"github.com/caos/zitadel/internal/errors"
"github.com/caos/zitadel/internal/eventstore/v2"
"github.com/caos/zitadel/internal/eventstore/v2/repository"
)
type ConfigChangedEvent struct {
eventstore.BaseEvent `json:"-"`
ID string `json:"idpConfigId"`
ConfigID string `json:"idpConfigId"`
Name string `json:"name,omitempty"`
StylingType StylingType `json:"stylingType,omitempty"`
hasChanged bool
}
func NewConfigChangedEvent(
base *eventstore.BaseEvent,
current,
changed *ConfigAggregate,
current *ConfigWriteModel,
name string,
stylingType StylingType,
) (*ConfigChangedEvent, error) {
change := &ConfigChangedEvent{
BaseEvent: *base,
ConfigID: current.ConfigID,
}
hasChanged := false
if current.Name != name {
change.Name = name
hasChanged = true
}
if stylingType != current.StylingType {
change.StylingType = stylingType
hasChanged = true
}
if current.ConfigID != changed.ConfigID {
change.ID = changed.ConfigID
change.hasChanged = true
}
if current.StylingType != changed.StylingType {
change.StylingType = changed.StylingType
change.hasChanged = true
}
if !change.hasChanged {
if !hasChanged {
return nil, errors.ThrowPreconditionFailed(nil, "IDP-UBJbB", "Errors.NoChanges")
}
@@ -46,8 +50,18 @@ func (e *ConfigChangedEvent) CheckPrevious() bool {
}
func (e *ConfigChangedEvent) Data() interface{} {
if e.current.Name != e.changed.Name {
e.Name = e.changed.Name
}
return e
}
func ConfigChangedEventMapper(event *repository.Event) (eventstore.EventReader, error) {
e := &ConfigChangedEvent{
BaseEvent: *eventstore.BaseEventFromRepo(event),
}
err := json.Unmarshal(event.Data, e)
if err != nil {
return nil, errors.ThrowInternal(err, "OIDC-plaBZ", "unable to unmarshal event")
}
return e, nil
}

View File

@@ -1,28 +1,47 @@
package idp
import "github.com/caos/zitadel/internal/eventstore/v2"
import (
"encoding/json"
type DeactivatedEvent struct {
eventstore.BaseEvent
"github.com/caos/zitadel/internal/errors"
"github.com/caos/zitadel/internal/eventstore/v2"
"github.com/caos/zitadel/internal/eventstore/v2/repository"
)
ID string `idpConfigId`
type ConfigDeactivatedEvent struct {
eventstore.BaseEvent `json:"-"`
ConfigID string `idpConfigId`
}
func NewDeactivatedEvent(
func NewConfigDeactivatedEvent(
base *eventstore.BaseEvent,
configID string,
) *DeactivatedEvent {
) *ConfigDeactivatedEvent {
return &DeactivatedEvent{
return &ConfigDeactivatedEvent{
BaseEvent: *base,
ID: configID,
ConfigID: configID,
}
}
func (e *DeactivatedEvent) CheckPrevious() bool {
func (e *ConfigDeactivatedEvent) CheckPrevious() bool {
return true
}
func (e *DeactivatedEvent) Data() interface{} {
func (e *ConfigDeactivatedEvent) Data() interface{} {
return e
}
func ConfigDeactivatedEventMapper(event *repository.Event) (eventstore.EventReader, error) {
e := &ConfigDeactivatedEvent{
BaseEvent: *eventstore.BaseEventFromRepo(event),
}
err := json.Unmarshal(event.Data, e)
if err != nil {
return nil, errors.ThrowInternal(err, "OIDC-plaBZ", "unable to unmarshal event")
}
return e, nil
}

View File

@@ -0,0 +1,47 @@
package idp
import (
"encoding/json"
"github.com/caos/zitadel/internal/errors"
"github.com/caos/zitadel/internal/eventstore/v2"
"github.com/caos/zitadel/internal/eventstore/v2/repository"
)
type ConfigReactivatedEvent struct {
eventstore.BaseEvent `json:"-"`
ConfigID string `idpConfigId`
}
func NewConfigReactivatedEvent(
base *eventstore.BaseEvent,
configID string,
) *ConfigReactivatedEvent {
return &ConfigReactivatedEvent{
BaseEvent: *base,
ConfigID: configID,
}
}
func (e *ConfigReactivatedEvent) CheckPrevious() bool {
return true
}
func (e *ConfigReactivatedEvent) Data() interface{} {
return e
}
func ConfigReactivatedEventMapper(event *repository.Event) (eventstore.EventReader, error) {
e := &ConfigReactivatedEvent{
BaseEvent: *eventstore.BaseEventFromRepo(event),
}
err := json.Unmarshal(event.Data, e)
if err != nil {
return nil, errors.ThrowInternal(err, "OIDC-plaBZ", "unable to unmarshal event")
}
return e, nil
}

View File

@@ -0,0 +1,47 @@
package idp
import (
"encoding/json"
"github.com/caos/zitadel/internal/errors"
"github.com/caos/zitadel/internal/eventstore/v2"
"github.com/caos/zitadel/internal/eventstore/v2/repository"
)
type ConfigRemovedEvent struct {
eventstore.BaseEvent `json:"-"`
ConfigID string `idpConfigId`
}
func NewConfigRemovedEvent(
base *eventstore.BaseEvent,
configID string,
) *ConfigRemovedEvent {
return &ConfigRemovedEvent{
BaseEvent: *base,
ConfigID: configID,
}
}
func (e *ConfigRemovedEvent) CheckPrevious() bool {
return true
}
func (e *ConfigRemovedEvent) Data() interface{} {
return e
}
func ConfigRemovedEventMapper(event *repository.Event) (eventstore.EventReader, error) {
e := &ConfigRemovedEvent{
BaseEvent: *eventstore.BaseEventFromRepo(event),
}
err := json.Unmarshal(event.Data, e)
if err != nil {
return nil, errors.ThrowInternal(err, "OIDC-plaBZ", "unable to unmarshal event")
}
return e, nil
}

View File

@@ -1,15 +0,0 @@
package oidc
import "github.com/caos/zitadel/internal/crypto"
type AddedEvent struct {
eventstore.BaseEvent
IDPConfigID string `json:"idpConfigId"`
ClientID string `json:"clientId"`
Secret *crypto.CryptoValue `json:"clientSecret"`
Issuer string `json:"issuer"`
Scopes []string `json:"scpoes"`
IDPDisplayNameMapping int32 `json:"idpDisplayNameMapping,omitempty"`
UsernameMapping int32 `json:"usernameMapping,omitempty"`
}

View File

@@ -1,3 +0,0 @@
package oidc
type ChangedEvent struct{}

View File

@@ -1,35 +0,0 @@
package oidc
import (
"github.com/caos/zitadel/internal/crypto"
"github.com/caos/zitadel/internal/eventstore/v2"
)
type ConfigReadModel struct {
eventstore.ReadModel
IDPConfigID string
ClientID string
ClientSecret *crypto.CryptoValue
ClientSecretString string
Issuer string
Scopes []string
IDPDisplayNameMapping MappingField
UsernameMapping MappingField
}
func (rm *ConfigReadModel) AppendEvents(events ...eventstore.EventReader) {
rm.ReadModel.AppendEvents(events...)
}
func (rm *ConfigReadModel) Reduce() error {
return nil
}
type MappingField int32
const (
OIDCMappingFieldUnspecified MappingField = iota
OIDCMappingFieldPreferredLoginName
OIDCMappingFieldEmail
)

View File

@@ -0,0 +1,51 @@
package oidc
import (
"github.com/caos/zitadel/internal/crypto"
"github.com/caos/zitadel/internal/eventstore/v2"
)
type ConfigReadModel struct {
eventstore.ReadModel
IDPConfigID string
ClientID string
ClientSecret *crypto.CryptoValue
Issuer string
Scopes []string
IDPDisplayNameMapping MappingField
UserNameMapping MappingField
}
func (rm *ConfigReadModel) Reduce() error {
for _, event := range rm.Events {
switch e := event.(type) {
case *ConfigAddedEvent:
rm.IDPConfigID = e.IDPConfigID
rm.ClientID = e.ClientID
rm.ClientSecret = e.ClientSecret
rm.Issuer = e.Issuer
rm.Scopes = e.Scopes
rm.IDPDisplayNameMapping = e.IDPDisplayNameMapping
rm.UserNameMapping = e.UserNameMapping
case *ConfigChangedEvent:
if e.ClientID != "" {
rm.ClientID = e.ClientID
}
if e.Issuer != "" {
rm.Issuer = e.Issuer
}
if len(e.Scopes) > 0 {
rm.Scopes = e.Scopes
}
if e.IDPDisplayNameMapping.Valid() {
rm.IDPDisplayNameMapping = e.IDPDisplayNameMapping
}
if e.UserNameMapping.Valid() {
rm.UserNameMapping = e.UserNameMapping
}
}
}
return rm.ReadModel.Reduce()
}

View File

@@ -0,0 +1,52 @@
package oidc
import (
"github.com/caos/zitadel/internal/crypto"
"github.com/caos/zitadel/internal/eventstore/v2"
)
type ConfigWriteModel struct {
eventstore.WriteModel
IDPConfigID string
ClientID string
ClientSecret *crypto.CryptoValue
Issuer string
Scopes []string
IDPDisplayNameMapping MappingField
UserNameMapping MappingField
}
func (wm *ConfigWriteModel) Reduce() error {
for _, event := range wm.Events {
switch e := event.(type) {
case *ConfigAddedEvent:
wm.IDPConfigID = e.IDPConfigID
wm.ClientID = e.ClientID
wm.ClientSecret = e.ClientSecret
wm.Issuer = e.Issuer
wm.Scopes = e.Scopes
wm.IDPDisplayNameMapping = e.IDPDisplayNameMapping
wm.UserNameMapping = e.UserNameMapping
case *ConfigChangedEvent:
if e.ClientID != "" {
wm.ClientID = e.ClientID
}
if e.Issuer != "" {
wm.Issuer = e.Issuer
}
if len(e.Scopes) > 0 {
wm.Scopes = e.Scopes
}
if e.IDPDisplayNameMapping.Valid() {
wm.IDPDisplayNameMapping = e.IDPDisplayNameMapping
}
if e.UserNameMapping.Valid() {
wm.UserNameMapping = e.UserNameMapping
}
}
}
return wm.WriteModel.Reduce()
}

View File

@@ -1,3 +0,0 @@
package oidc
type DeactivatedEvent struct{}

View File

@@ -0,0 +1,67 @@
package oidc
import (
"encoding/json"
"github.com/caos/zitadel/internal/crypto"
"github.com/caos/zitadel/internal/errors"
"github.com/caos/zitadel/internal/eventstore/v2"
"github.com/caos/zitadel/internal/eventstore/v2/repository"
)
type ConfigAddedEvent struct {
eventstore.BaseEvent
IDPConfigID string `json:"idpConfigId"`
ClientID string `json:"clientId"`
ClientSecret *crypto.CryptoValue `json:"clientSecret"`
Issuer string `json:"issuer"`
Scopes []string `json:"scpoes"`
IDPDisplayNameMapping MappingField `json:"idpDisplayNameMapping"`
UserNameMapping MappingField `json:"usernameMapping"`
}
func (e *ConfigAddedEvent) CheckPrevious() bool {
return true
}
func (e *ConfigAddedEvent) Data() interface{} {
return e
}
func NewConfigAddedEvent(
base *eventstore.BaseEvent,
clientID,
idpConfigID,
issuer string,
clientSecret *crypto.CryptoValue,
idpDisplayNameMapping,
userNameMapping MappingField,
scopes ...string,
) *ConfigAddedEvent {
return &ConfigAddedEvent{
BaseEvent: *base,
IDPConfigID: idpConfigID,
ClientID: clientID,
ClientSecret: clientSecret,
Issuer: issuer,
Scopes: scopes,
IDPDisplayNameMapping: idpDisplayNameMapping,
UserNameMapping: userNameMapping,
}
}
func ConfigAddedEventMapper(event *repository.Event) (eventstore.EventReader, error) {
e := &ConfigAddedEvent{
BaseEvent: *eventstore.BaseEventFromRepo(event),
}
err := json.Unmarshal(event.Data, e)
if err != nil {
return nil, errors.ThrowInternal(err, "OIDC-plaBZ", "unable to unmarshal event")
}
return e, nil
}

View File

@@ -0,0 +1,105 @@
package oidc
import (
"encoding/json"
"reflect"
"sort"
"github.com/caos/zitadel/internal/crypto"
"github.com/caos/zitadel/internal/errors"
"github.com/caos/zitadel/internal/eventstore/v2"
"github.com/caos/zitadel/internal/eventstore/v2/repository"
)
type ConfigChangedEvent struct {
eventstore.BaseEvent `json:"-"`
IDPConfigID string `json:"idpConfigId"`
ClientID string `json:"clientId"`
ClientSecret *crypto.CryptoValue `json:"clientSecret"`
Issuer string `json:"issuer"`
Scopes []string `json:"scpoes"`
IDPDisplayNameMapping MappingField `json:"idpDisplayNameMapping"`
UserNameMapping MappingField `json:"usernameMapping"`
}
func (e *ConfigChangedEvent) CheckPrevious() bool {
return true
}
func (e *ConfigChangedEvent) Data() interface{} {
return e
}
func NewConfigChangedEvent(
base *eventstore.BaseEvent,
current *ConfigWriteModel,
clientID,
issuer string,
clientSecret *crypto.CryptoValue,
idpDisplayNameMapping,
userNameMapping MappingField,
scopes ...string,
) (*ConfigChangedEvent, error) {
event := &ConfigChangedEvent{
BaseEvent: *base,
IDPConfigID: current.IDPConfigID,
}
hasChanged := false
if clientID != "" && clientID != current.ClientID {
event.ClientID = clientID
hasChanged = true
}
if issuer != "" && issuer != current.Issuer {
event.Issuer = issuer
hasChanged = true
}
if clientSecret != nil && clientSecret != current.ClientSecret {
event.ClientSecret = clientSecret
hasChanged = true
}
if idpDisplayNameMapping.Valid() && idpDisplayNameMapping != current.IDPDisplayNameMapping {
event.IDPDisplayNameMapping = idpDisplayNameMapping
hasChanged = true
}
if userNameMapping.Valid() && userNameMapping != current.UserNameMapping {
event.UserNameMapping = userNameMapping
hasChanged = true
}
if len(scopes) > 0 {
sort.Strings(scopes)
sort.Strings(current.Scopes)
if !reflect.DeepEqual(scopes, current.Scopes) {
event.Scopes = scopes
hasChanged = true
}
}
if !hasChanged {
return nil, errors.ThrowPreconditionFailed(nil, "OIDC-zPDOL", "Errors.NoChanges")
}
return event, nil
}
func ConfigChangedEventMapper(event *repository.Event) (eventstore.EventReader, error) {
e := &ConfigChangedEvent{
BaseEvent: *eventstore.BaseEventFromRepo(event),
}
err := json.Unmarshal(event.Data, e)
if err != nil {
return nil, errors.ThrowInternal(err, "OIDC-plaBZ", "unable to unmarshal event")
}
return e, nil
}

View File

@@ -0,0 +1,14 @@
package oidc
type MappingField int32
const (
MappingFieldPreferredLoginName MappingField = iota + 1
MappingFieldEmail
// count is for validation purposes
mappingFieldCount
)
func (f MappingField) Valid() bool {
return f > 0 && f < mappingFieldCount
}

View File

@@ -1,3 +0,0 @@
package oidc
type RemovedEvent struct{}

View File

@@ -5,7 +5,7 @@ import (
"github.com/caos/zitadel/internal/errors"
"github.com/caos/zitadel/internal/eventstore/v2"
"github.com/caos/zitadel/internal/eventstore/v2/repository"
es_repo "github.com/caos/zitadel/internal/eventstore/v2/repository"
)
const (
@@ -40,7 +40,7 @@ func NewAddedEvent(
}
}
func AddedEventMapper(event *repository.Event) (eventstore.EventReader, error) {
func AddedEventMapper(event *es_repo.Event) (eventstore.EventReader, error) {
e := &AddedEvent{
BaseEvent: *eventstore.BaseEventFromRepo(event),
}

View File

@@ -19,8 +19,6 @@ type ChangedEvent struct {
Roles []string `json:"roles,omitempty"`
UserID string `json:"userId,omitempty"`
hasChanged bool
}
func (e *ChangedEvent) CheckPrevious() bool {
@@ -38,15 +36,16 @@ func ChangeEventFromExisting(
) (*ChangedEvent, error) {
change := NewChangedEvent(base, current.userID)
hasChanged := false
sort.Strings(current.Roles)
sort.Strings(roles)
if !reflect.DeepEqual(current.Roles, roles) {
change.Roles = roles
change.hasChanged = true
hasChanged = true
}
if !change.hasChanged {
if !hasChanged {
return nil, errors.ThrowPreconditionFailed(nil, "MEMBE-SeKlD", "Errors.NoChanges")
}