diff --git a/internal/eventstore/v3/eventstore.go b/internal/eventstore/v3/eventstore.go index 829f6a9400..4ecaf6bad2 100644 --- a/internal/eventstore/v3/eventstore.go +++ b/internal/eventstore/v3/eventstore.go @@ -6,8 +6,12 @@ import ( "github.com/zitadel/zitadel/internal/database" ) -// pushPlaceholderFmt defines how data are inserted into the events table -var pushPlaceholderFmt string +var ( + // pushPlaceholderFmt defines how data are inserted into the events table + pushPlaceholderFmt string + // uniqueConstraintPlaceholderFmt defines the format of the unique constraint error returned from the database + uniqueConstraintPlaceholderFmt string +) type Eventstore struct { client *database.DB @@ -17,8 +21,10 @@ func NewEventstore(client *database.DB) *Eventstore { switch client.Type() { case "cockroach": pushPlaceholderFmt = "($%d, $%d, $%d, $%d, $%d, $%d, $%d, $%d, $%d, hlc_to_timestamp(cluster_logical_timestamp()), cluster_logical_timestamp(), $%d)" + uniqueConstraintPlaceholderFmt = "('%s', '%s', '%s')" case "postgres": pushPlaceholderFmt = "($%d, $%d, $%d, $%d, $%d, $%d, $%d, $%d, $%d, statement_timestamp(), EXTRACT(EPOCH FROM clock_timestamp()), $%d)" + uniqueConstraintPlaceholderFmt = "(%s, %s, %s)" } return &Eventstore{client: client} diff --git a/internal/eventstore/v3/unique_constraints.go b/internal/eventstore/v3/unique_constraints.go index 0527f16874..f721e77385 100644 --- a/internal/eventstore/v3/unique_constraints.go +++ b/internal/eventstore/v3/unique_constraints.go @@ -37,15 +37,15 @@ func handleUniqueConstraints(ctx context.Context, tx *sql.Tx, commands []eventst case eventstore.UniqueConstraintAdd: addPlaceholders = append(addPlaceholders, fmt.Sprintf("($%d, $%d, $%d)", len(addArgs)+1, len(addArgs)+2, len(addArgs)+3)) addArgs = append(addArgs, command.Aggregate().InstanceID, constraint.UniqueType, constraint.UniqueField) - addConstraints[fmt.Sprintf("('%s', '%s', '%s')", command.Aggregate().InstanceID, constraint.UniqueType, constraint.UniqueField)] = constraint + addConstraints[fmt.Sprintf(uniqueConstraintPlaceholderFmt, command.Aggregate().InstanceID, constraint.UniqueType, constraint.UniqueField)] = constraint case eventstore.UniqueConstraintRemove: deletePlaceholders = append(deletePlaceholders, fmt.Sprintf("(instance_id = $%d AND unique_type = $%d AND unique_field = $%d)", len(deleteArgs)+1, len(deleteArgs)+2, len(deleteArgs)+3)) deleteArgs = append(deleteArgs, command.Aggregate().InstanceID, constraint.UniqueType, constraint.UniqueField) - deleteConstraints[fmt.Sprintf("('%s', '%s', '%s')", command.Aggregate().InstanceID, constraint.UniqueType, constraint.UniqueField)] = constraint + deleteConstraints[fmt.Sprintf(uniqueConstraintPlaceholderFmt, command.Aggregate().InstanceID, constraint.UniqueType, constraint.UniqueField)] = constraint case eventstore.UniqueConstraintInstanceRemove: deletePlaceholders = append(deletePlaceholders, fmt.Sprintf("(instance_id = $%d)", len(deleteArgs)+1)) deleteArgs = append(deleteArgs, command.Aggregate().InstanceID) - deleteConstraints[fmt.Sprintf("('%s', '%s', '%s')", command.Aggregate().InstanceID, constraint.UniqueType, constraint.UniqueField)] = constraint + deleteConstraints[fmt.Sprintf(uniqueConstraintPlaceholderFmt, command.Aggregate().InstanceID, constraint.UniqueType, constraint.UniqueField)] = constraint } } } @@ -69,7 +69,7 @@ func handleUniqueConstraints(ctx context.Context, tx *sql.Tx, commands []eventst if constraint := constraintFromErr(err, addConstraints); constraint != nil { errMessage = constraint.ErrorMessage } - return errs.ThrowInternal(err, "V3-DKcYh", errMessage) + return errs.ThrowAlreadyExists(err, "V3-DKcYh", errMessage) } } return nil