diff --git a/backend/internal/handler/user_handler.go b/backend/internal/handler/user_handler.go index 2088931e..04712326 100644 --- a/backend/internal/handler/user_handler.go +++ b/backend/internal/handler/user_handler.go @@ -1209,7 +1209,6 @@ func (h *UserHandler) UpdateUser(c *fiber.Ctx) error { } } } - finalLoginID := extractTraitString(traits, "id") userEmail := extractTraitString(traits, "email") userPhone := extractTraitString(traits, "phone") @@ -1583,7 +1582,7 @@ func extractTraitString(traits map[string]interface{}, key string) string { // syncLoginID ensures that the 'id' trait (used as Kratos identifier) is in sync with the configured custom field. func syncLoginID(traits map[string]interface{}, metadata map[string]any, tenantID string, loginIDField string) { - if loginIDField == "" || loginIDField == "id" { + if loginIDField == "" { return } @@ -1608,7 +1607,9 @@ func syncLoginID(traits map[string]interface{}, metadata map[string]any, tenantI } // 3. Check merged traits (which includes existing metadata) - if loginID == "" { + // Important: Skip this if loginIDField is "id" because traits["id"] is the TARGET, + // and we don't want to sync "id" to "id" if we already checked metadata. + if loginID == "" && loginIDField != "id" { // Existing trait (flat) if val, ok := traits[loginIDField].(string); ok && val != "" { loginID = val