{"record":{"id":"faa47f5abf299854","repo":"infiniflow/ragflow","slug":"user-username-already-exists","errorCode":null,"errorMessage":"User '{username}' already exists","messagePattern":"User '(.+?)' already exists","errorType":"http","errorClass":"UserAlreadyExistsError","httpStatus":409,"severity":"error","filePath":"admin/server/services.py","lineNumber":88,"sourceCode":"                    \"is_active\": user.is_active,\n                    \"is_anonymous\": user.is_anonymous,\n                    \"login_channel\": user.login_channel,\n                    \"status\": user.status,\n                    \"is_superuser\": user.is_superuser,\n                    \"create_date\": user.create_date,\n                    \"update_date\": user.update_date,\n                }\n            )\n        return result\n\n    @staticmethod\n    def create_user(username, password, role=\"user\") -> dict:\n        # Validate the email address\n        if not re.match(r\"^[\\w\\._-]+@([\\w_-]+\\.)+[\\w-]{2,}$\", username):\n            raise AdminException(f\"Invalid email address: {username}!\")\n        # Check if the email address is already used\n        if UserService.query(email=username):\n            raise UserAlreadyExistsError(username)\n        # Construct user info data\n        user_info_dict = {\n            \"email\": username,\n            \"nickname\": \"\",  # ask user to edit it manually in settings.\n            \"password\": decrypt(password),\n            \"login_channel\": \"password\",\n            \"is_superuser\": role == \"admin\",\n        }\n        return create_new_user(user_info_dict)\n\n    @staticmethod\n    def delete_user(username):\n        # use email to delete\n        user_list = UserService.query_user_by_email(username)\n        if not user_list:\n            raise UserNotFoundError(username)\n        if len(user_list) > 1:\n            raise AdminException(f\"Exist more than 1 user: {username}!\")","sourceCodeStart":70,"sourceCodeEnd":106,"githubUrl":"https://github.com/infiniflow/ragflow/blob/554fb1133ac3861732235ad9c377eb5e0a770665/admin/server/services.py#L70-L106","documentation":"UserAlreadyExistsError (HTTP 409) raised by UserMgr.create_user (admin/server/services.py:88) when UserService.query(email=username) already returns a row. Emails are the unique user key for the admin surface, so duplicate creation is refused before create_new_user runs. Defined in admin/server/exceptions.py:13.","triggerScenarios":"Creating a user whose email already exists in the user table; re-running a provisioning script that is not idempotent; retrying a previous create that actually succeeded but whose response was lost (timeout, network drop).","commonSituations":"CI/CD pipelines or docker-entrypoint bootstrap scripts that call 'create admin user' on every start; SSO users provisioned earlier via OIDC/OAuth occupying the same email; manual onboarding where an operator re-adds an existing member.","solutions":["Treat 409 as success for idempotent provisioning: catch UserAlreadyExistsError and continue, or first check UserService.query(email=...) before calling create_user.","Make bootstrap scripts use get-or-create semantics instead of unconditional create.","If the user should be re-created, delete it first with UserMgr.delete_user(username), then create again.","Verify you are pointed at the right environment/database (a stale dev DB often already holds the account)."],"exampleFix":"# before\nUserMgr.create_user('user@example.com', pw)  # 409 on second run\n\n# after\nfrom api.db.services import UserService\nif UserService.query(email='user@example.com'):\n    print('user exists, skipping create')\nelse:\n    UserMgr.create_user('user@example.com', pw)","handlingStrategy":"try-catch","validationCode":"from api.db.services import UserService\n\ndef user_exists(email: str) -> bool:\n    return bool(UserService.query(email=email))","typeGuard":"def is_new_user(email: str) -> bool:\n    from api.db.services import UserService\n    return UserService.query(email=email) == []","tryCatchPattern":"from admin.server.exceptions import UserAlreadyExistsError\ntry:\n    UserMgr.create_user(email, encrypted_pw, role)\nexcept UserAlreadyExistsError:\n    pass  # idempotent provisioning: already created","preventionTips":["Make bootstrap/provisioning scripts idempotent with get-or-create semantics.","Check UserService.query(email=...) before creating.","Treat HTTP 409 from the admin API as 'already provisioned', not as failure.","Keep SSO-provisioned emails and locally created emails in one registry to avoid collisions."],"tags":["conflict","user-management","admin-api","idempotency"],"backgroundTag":null,"analyzedSha":"554fb1133ac3861732235ad9c377eb5e0a770665","analyzedAt":"2026-08-15T09:20:16.380Z","schemaVersion":2},"datasetVersion":"2026-08-15T22:17:37.221Z"}