Repository navigation
Conversation
AList v3.46.0 and later store the user role as a list of ints serialized into a text column (`"[1]"`, `"[2]"`), while OpenList has always used a single int. AutoMigrate rebuilds the column as integer but leaves the old values textual, so `WHERE role = 2` never matches `[2]` and both GetAdmin() and GetGuest() return gorm.ErrRecordNotFound. Because the guest lookup fails, initGuest inserts a second `guest` row, violates uni_x_users_username and kills the process with Fatalf: anyone upgrading from AList v3.46+ gets a restart loop whose only error lives in data/log/log.log, not in docker logs. Even without the crash the administrator silently loses admin rights. Normalize the legacy values right after AutoMigrate, keeping the most privileged role when a row lists several, and let initGuest take over an existing `guest` row (forced disabled) instead of refusing to boot. Fixes OpenListTeam#3261 Co-Authored-By: WorkBuddy AI Agent <noreply@workbuddy.cn>
Member
|
NOT COMPATIBLE |
Member
|
If you have these requirements, please perform manual modifications to the JSON from the import/export feature. |
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
Add this suggestion to a batch that can be applied as a single commit.This suggestion is invalid because no changes were made to the code.Suggestions cannot be applied while the pull request is closed.Suggestions cannot be applied while viewing a subset of changes.Only one suggestion per line can be applied in a batch.Add this suggestion to a batch that can be applied as a single commit.Applying suggestions on deleted lines is not supported.You must change the existing code in this line in order to create a valid suggestion.Outdated suggestions cannot be applied.This suggestion has been applied or marked resolved.Suggestions cannot be applied from pending reviews.Suggestions cannot be applied on multi-line comments.Suggestions cannot be applied while the pull request is queued to merge.Suggestion cannot be applied right now. Please check back later.
Summary / 摘要
Fixes a startup crash loop for everyone upgrading from AList v3.46.0+ (and restores the admin role that silently disappeared on such databases).
x_users.role; no schema change and no user action required.AList v3.46.0 and later model the role as a list of ints stored in a text column (
"[1]","[2]"), OpenList has always used a singleint.AutoMigraterebuilds the column as integer but the legacy rows keep their textual value, soWHERE role = 2never matches'[2]':GetGuest()reportsErrRecordNotFound→initGuest()inserts a secondguestrow →UNIQUE constraint failed: x_users.username (2067)→Fatalfand a restart loop. The error only appears indata/log/log.log,docker logsjust stops afterinit logrus..., which makes it very hard to diagnose.GetAdmin()fails too → the administrator keeps the username but silently loses admin rights, becauseIsAdmin()isRole == ADMIN.What this PR does:
internal/db:migrateUserRoles()runs right afterAutoMigrateand rewrites every legacy[N]/[N,M]value into the single-int form, preferring the most privileged role when a row lists several. Already-normalized rows are skipped, so it is idempotent and a no-op on fresh installs. Scanningroleinto astringkeeps it portable across SQLite (text and blob), MySQL and PostgreSQL.internal/bootstrap/data:initGuest()no longer callsFatalfwhen the insert fails because a row namedguestalready exists — it takes that row over as the disabled guest and logs a warning instead, so a mismatched role can never brick the instance again.internal/db/user_role_test.go: table test for the legacy value conversion.Related Issues / 关联 Issue
Closes #3261
Testing / 测试
go test ./...— ran the new package test only:go test ./internal/db/ -run TestConvertLegacyRole→ PASSReproduced on a real AList v3.52.0 SQLite database (
x_users.role=b'[2]'/b'[1]'), run with a locally built v4.2.8 binary:Before — exits during init:
After:
Also verified:
roleis already integer but theguestrow hasGENERALstill boots, with the takeover warning:[init user] Username "guest" was already taken by user id=2 and has been taken over as the disabled guest account.Not tested: MySQL and PostgreSQL backends (no instance available); the SQL used is a plain
SELECT/UPDATEwith values bound through GORM, no dialect specific syntax.Checklist / 检查清单
gofmt,go fmt, orprettierwhere applicable.AI Disclosure / AI 使用声明
Tools used / 使用工具:
Usage scope / 使用范围:
Code generation / 代码生成
Tests / 测试
Review assistance / 审查辅助
I have reviewed and validated all AI-assisted content included in this PR.
I have ensured that all AI-assisted commits include
Co-Authored-Byattribution.I can reproduce all AI-assisted content included in this PR without any AI tools.