refactor: migrate wechat to user attributes and enhance users list

Migrate the hardcoded wechat field to the new extensible user
attributes system and improve the users management UI.

Migration:
- Add migration 019 to move wechat data to user_attribute_values
- Remove wechat field from User entity, DTOs, and API contracts
- Clean up wechat-related code from backend and frontend

UsersView enhancements:
- Add text labels to action buttons (Filter Settings, Column Settings,
  Attributes Config) for better UX
- Change status column to show colored dot + Chinese text instead of
  English text
- Add dynamic attribute columns support with batch loading
- Add column visibility settings with localStorage persistence
- Add filter settings modal for search and filter preferences
- Update i18n translations

🤖 Generated with [Claude Code](https://claude.com/claude-code)

Co-Authored-By: Claude Opus 4.5 <noreply@anthropic.com>
This commit is contained in:
Edric Li
2026-01-01 18:59:38 +08:00
parent f44cf642bc
commit 404bf0f8d2
30 changed files with 1390 additions and 462 deletions

View File

@@ -7,7 +7,6 @@
export interface User {
id: number
username: string
wechat: string
notes: string
email: string
role: 'admin' | 'user' // User role for authorization
@@ -634,7 +633,6 @@ export interface UpdateUserRequest {
email?: string
password?: string
username?: string
wechat?: string
notes?: string
role?: 'admin' | 'user'
balance?: number
@@ -771,3 +769,76 @@ export interface AccountUsageStatsResponse {
summary: AccountUsageSummary
models: ModelStat[]
}
// ==================== User Attribute Types ====================
export type UserAttributeType = 'text' | 'textarea' | 'number' | 'email' | 'url' | 'date' | 'select' | 'multi_select'
export interface UserAttributeOption {
value: string
label: string
}
export interface UserAttributeValidation {
min_length?: number
max_length?: number
min?: number
max?: number
pattern?: string
message?: string
}
export interface UserAttributeDefinition {
id: number
key: string
name: string
description: string
type: UserAttributeType
options: UserAttributeOption[]
required: boolean
validation: UserAttributeValidation
placeholder: string
display_order: number
enabled: boolean
created_at: string
updated_at: string
}
export interface UserAttributeValue {
id: number
user_id: number
attribute_id: number
value: string
created_at: string
updated_at: string
}
export interface CreateUserAttributeRequest {
key: string
name: string
description?: string
type: UserAttributeType
options?: UserAttributeOption[]
required?: boolean
validation?: UserAttributeValidation
placeholder?: string
display_order?: number
enabled?: boolean
}
export interface UpdateUserAttributeRequest {
key?: string
name?: string
description?: string
type?: UserAttributeType
options?: UserAttributeOption[]
required?: boolean
validation?: UserAttributeValidation
placeholder?: string
display_order?: number
enabled?: boolean
}
export interface UserAttributeValuesMap {
[attributeId: number]: string
}