mirror of
https://github.com/danswer-ai/danswer.git
synced 2025-10-06 18:14:35 +02:00
handle conflicts on lowercasing emails (#4255)
Co-authored-by: Richard Kuo (Danswer) <rkuo@onyx.app>
This commit is contained in:
@@ -5,7 +5,10 @@ Revises: f1ca58b2f2ec
|
|||||||
Create Date: 2025-01-29 07:48:46.784041
|
Create Date: 2025-01-29 07:48:46.784041
|
||||||
|
|
||||||
"""
|
"""
|
||||||
|
import logging
|
||||||
|
from typing import cast
|
||||||
from alembic import op
|
from alembic import op
|
||||||
|
from sqlalchemy.exc import IntegrityError
|
||||||
from sqlalchemy.sql import text
|
from sqlalchemy.sql import text
|
||||||
|
|
||||||
|
|
||||||
@@ -15,21 +18,45 @@ down_revision = "f1ca58b2f2ec"
|
|||||||
branch_labels = None
|
branch_labels = None
|
||||||
depends_on = None
|
depends_on = None
|
||||||
|
|
||||||
|
logger = logging.getLogger("alembic.runtime.migration")
|
||||||
|
|
||||||
|
|
||||||
def upgrade() -> None:
|
def upgrade() -> None:
|
||||||
# Get database connection
|
"""Conflicts on lowercasing will result in the uppercased email getting a
|
||||||
|
unique integer suffix when converted to lowercase."""
|
||||||
|
|
||||||
connection = op.get_bind()
|
connection = op.get_bind()
|
||||||
|
|
||||||
# Update all user emails to lowercase
|
# Fetch all user emails that are not already lowercase
|
||||||
connection.execute(
|
user_emails = connection.execute(
|
||||||
text(
|
text('SELECT id, email FROM "user" WHERE email != LOWER(email)')
|
||||||
"""
|
).fetchall()
|
||||||
UPDATE "user"
|
|
||||||
SET email = LOWER(email)
|
for user_id, email in user_emails:
|
||||||
WHERE email != LOWER(email)
|
email = cast(str, email)
|
||||||
"""
|
username, domain = email.rsplit("@", 1)
|
||||||
)
|
new_email = f"{username.lower()}@{domain.lower()}"
|
||||||
)
|
attempt = 1
|
||||||
|
|
||||||
|
while True:
|
||||||
|
try:
|
||||||
|
# Try updating the email
|
||||||
|
connection.execute(
|
||||||
|
text('UPDATE "user" SET email = :new_email WHERE id = :user_id'),
|
||||||
|
{"new_email": new_email, "user_id": user_id},
|
||||||
|
)
|
||||||
|
break # Success, exit loop
|
||||||
|
except IntegrityError:
|
||||||
|
next_email = f"{username.lower()}_{attempt}@{domain.lower()}"
|
||||||
|
# Email conflict occurred, append `_1`, `_2`, etc., to the username
|
||||||
|
logger.warning(
|
||||||
|
f"Conflict while lowercasing email: "
|
||||||
|
f"old_email={email} "
|
||||||
|
f"conflicting_email={new_email} "
|
||||||
|
f"next_email={next_email}"
|
||||||
|
)
|
||||||
|
new_email = next_email
|
||||||
|
attempt += 1
|
||||||
|
|
||||||
|
|
||||||
def downgrade() -> None:
|
def downgrade() -> None:
|
||||||
|
Reference in New Issue
Block a user