refactor(models): 模型双轨收敛——gerp 侧 31 处 ForeignKey 改 UUIDField,与 SDK 映射对齐

- models.py: Tenant/Company/Dept/WorkOrder/Message/Menu 等 31 处 FK→UUIDField(db_column 不变)
- 8 张有 CompanyUUID 的表补齐 TenantUUID(Dept/Workgroup/FileAsset/Menu/WorkgroupRole/UserRoleWorkgroup/UserRoleDepartment/CompanyApp)
- 迁移 0028 扩展回填全 8 表;迁移 0029 AlterField 对齐字段类型(DB 列无实际变化)
- 消除 select_related/_id 行为差异,SDK 与主库模型字段类型统一
This commit is contained in:
TermiNexus committed 2026-08-13 17:52:08 +08:00
1 parent 3460de0f88
commit b0bdd78d3b
3 files changed
+256 -47

No files matched your search

@@ -1,30 +1,32 @@
"""Add TenantUUID to Dept / Workgroup (backfill from Company.TenantUUID)
"""Add TenantUUID to organization tables (backfill from Company.TenantUUID)
组织表补齐租户 UUID,消除跨租户查询的反射补偿:
- Dept.TenantUUID 回填 = CompanyUUID → Company.TenantUUID
- Workgroup.TenantUUID 回填 = CompanyUUID → Company.TenantUUID
组织/关联表补齐租户 UUID,消除跨租户查询的反射补偿与跨表过滤:
- Dept / Workgroup / FileAsset / Menu / WorkgroupRole /
UserRoleWorkgroup / UserRoleDepartment / CompanyApp
TenantUUID 回填 = CompanyUUID → Company.TenantUUID
"""
from django.db import migrations
import gvsds.apps.core.models
#: 需要回填 TenantUUID 的表(均通过 CompanyUUID 关联 Company)
_BACKFILL_TABLES = (
'Department', 'Workgroup', 'FileAsset', 'Menu',
'WorkgroupRole', 'UserRoleWorkgroup', 'UserRoleDepartment', 'CompanyApp',
)
def backfill_tenant_uuid(apps, schema_editor):
"""从关联 Company 的 TenantUUID 回填 Dept/Workgroup.TenantUUID"""
"""从关联 Company 的 TenantUUID 回填各表 TenantUUID"""
Company = apps.get_model('gerp', 'Company')
Department = apps.get_model('gerp', 'Department')
Workgroup = apps.get_model('gerp', 'Workgroup')
company_tenant = dict(
Company.objects.exclude(TenantUUID__isnull=True).values_list('CompanyUUID', 'TenantUUID')
)
for dept in Department.objects.select_related('CompanyUUID').only('DeptUUID', 'CompanyUUID').iterator():
tenant = company_tenant.get(dept.CompanyUUID_id)
if tenant:
Department.objects.filter(DeptUUID=dept.DeptUUID).update(TenantUUID=tenant)
for wg in Workgroup.objects.select_related('CompanyUUID').only('WorkgroupUUID', 'CompanyUUID').iterator():
tenant = company_tenant.get(wg.CompanyUUID_id)
if tenant:
Workgroup.objects.filter(WorkgroupUUID=wg.WorkgroupUUID).update(TenantUUID=tenant)
for name in _BACKFILL_TABLES:
model = apps.get_model('gerp', name)
for obj in model.objects.exclude(CompanyUUID__isnull=True).only('pk', 'CompanyUUID').iterator():
tenant = company_tenant.get(obj.CompanyUUID_id)
if tenant:
model.objects.filter(pk=obj.pk).update(TenantUUID=tenant)
class Migration(migrations.Migration):
@@ -44,5 +46,35 @@ class Migration(migrations.Migration):
name='TenantUUID',
field=gvsds.apps.core.models.UUIDField(blank=True, null=True, verbose_name='租户UUID'),
),
migrations.AddField(
model_name='fileasset',
name='TenantUUID',
field=gvsds.apps.core.models.UUIDField(blank=True, null=True, verbose_name='租户UUID'),
),
migrations.AddField(
model_name='menu',
name='TenantUUID',
field=gvsds.apps.core.models.UUIDField(blank=True, null=True, verbose_name='租户UUID'),
),
migrations.AddField(
model_name='workgrouprole',
name='TenantUUID',
field=gvsds.apps.core.models.UUIDField(blank=True, null=True, verbose_name='租户UUID'),
),
migrations.AddField(
model_name='userroleworkgroup',
name='TenantUUID',
field=gvsds.apps.core.models.UUIDField(blank=True, null=True, verbose_name='租户UUID'),
),
migrations.AddField(
model_name='userroledepartment',
name='TenantUUID',
field=gvsds.apps.core.models.UUIDField(blank=True, null=True, verbose_name='租户UUID'),
),
migrations.AddField(
model_name='companyapp',
name='TenantUUID',
field=gvsds.apps.core.models.UUIDField(blank=True, null=True, verbose_name='租户UUID'),
),
migrations.RunPython(backfill_tenant_uuid, migrations.RunPython.noop),
]
@@ -0,0 +1,172 @@
"""Convert ForeignKey fields to UUIDField (align with gvsdsdk mapping models)
模型双轨收敛:gerp 侧业务表字段与 gvsdsdk 映射模型对齐,
全部 ForeignKey 改为 UUIDField(db_column 不变,数据库列无实际变化)。
"""
from django.db import migrations
import gvsds.apps.core.models
class Migration(migrations.Migration):
dependencies = [
('gerp', '0028_tenant_uuid_backfill'),
]
operations = [
migrations.AlterField(
model_name='companyinfo',
name='tenant_uuid',
field=gvsds.apps.core.models.UUIDField(null=True, blank=True, db_column='TenantUUID', verbose_name='租户UUID'),
),
migrations.AlterField(
model_name='company',
name='tenant_uuid',
field=gvsds.apps.core.models.UUIDField(db_column='TenantUUID', verbose_name='租户UUID'),
),
migrations.AlterField(
model_name='company',
name='parent_company_uuid',
field=gvsds.apps.core.models.UUIDField(null=True, blank=True, db_column='ParentCompanyUUID', verbose_name='上级公司UUID'),
),
migrations.AlterField(
model_name='department',
name='company_uuid',
field=gvsds.apps.core.models.UUIDField(db_column='CompanyUUID', verbose_name='公司UUID'),
),
migrations.AlterField(
model_name='department',
name='parent_dept_uuid',
field=gvsds.apps.core.models.UUIDField(null=True, blank=True, db_column='ParentDeptUUID', verbose_name='上级部门UUID'),
),
migrations.AlterField(
model_name='fileasset',
name='company_uuid',
field=gvsds.apps.core.models.UUIDField(null=True, blank=True, db_column='CompanyUUID', verbose_name='公司UUID'),
),
migrations.AlterField(
model_name='workorder',
name='creator_uuid',
field=gvsds.apps.core.models.UUIDField(db_index=True, db_column='CreatorUUID', verbose_name='创建人UUID'),
),
migrations.AlterField(
model_name='workorder',
name='assignee_uuid',
field=gvsds.apps.core.models.UUIDField(null=True, blank=True, db_column='AssigneeUUID', verbose_name='指派人UUID'),
),
migrations.AlterField(
model_name='message',
name='sender_uuid',
field=gvsds.apps.core.models.UUIDField(null=True, blank=True, db_column='SenderUUID', verbose_name='发送者UUID'),
),
migrations.AlterField(
model_name='message',
name='receiver_uuid',
field=gvsds.apps.core.models.UUIDField(db_index=True, db_column='ReceiverUUID', verbose_name='接收者UUID'),
),
migrations.AlterField(
model_name='menu',
name='company_uuid',
field=gvsds.apps.core.models.UUIDField(null=True, blank=True, db_column='CompanyUUID', verbose_name='公司UUID'),
),
migrations.AlterField(
model_name='menu',
name='parent_menu_uuid',
field=gvsds.apps.core.models.UUIDField(null=True, blank=True, db_column='ParentMenuUUID', verbose_name='上级菜单UUID'),
),
migrations.AlterField(
model_name='workgroup',
name='CompanyUUID',
field=gvsds.apps.core.models.UUIDField(db_column='CompanyUUID', verbose_name='公司UUID'),
),
migrations.AlterField(
model_name='workgrouprole',
name='WorkgroupUUID',
field=gvsds.apps.core.models.UUIDField(db_column='WorkgroupUUID', verbose_name='工作组UUID'),
),
migrations.AlterField(
model_name='workgrouprole',
name='CompanyUUID',
field=gvsds.apps.core.models.UUIDField(db_column='CompanyUUID', verbose_name='公司UUID'),
),
migrations.AlterField(
model_name='userroleworkgroup',
name='WorkgroupUUID',
field=gvsds.apps.core.models.UUIDField(db_column='WorkgroupUUID', verbose_name='工作组UUID'),
),
migrations.AlterField(
model_name='userroleworkgroup',
name='CompanyUUID',
field=gvsds.apps.core.models.UUIDField(db_column='CompanyUUID', verbose_name='公司UUID'),
),
migrations.AlterField(
model_name='userroledepartment',
name='DeptUUID',
field=gvsds.apps.core.models.UUIDField(db_column='DeptUUID', verbose_name='部门UUID'),
),
migrations.AlterField(
model_name='userroledepartment',
name='CompanyUUID',
field=gvsds.apps.core.models.UUIDField(db_column='CompanyUUID', verbose_name='公司UUID'),
),
migrations.AlterField(
model_name='backpack',
name='user_uuid',
field=gvsds.apps.core.models.UUIDField(db_column='UserUUID', verbose_name='用户UUID'),
),
migrations.AlterField(
model_name='backpack',
name='item_template_uuid',
field=gvsds.apps.core.models.UUIDField(db_column='ItemTemplateUUID', verbose_name='物品模板UUID'),
),
migrations.AlterField(
model_name='usersettings',
name='UserUUID',
field=gvsds.apps.core.models.UUIDField(unique=True, db_column='UserUUID', verbose_name='用户UUID'),
),
migrations.AlterField(
model_name='auditlog',
name='tenant_uuid',
field=gvsds.apps.core.models.UUIDField(null=True, blank=True, db_column='TenantUUID', verbose_name='租户UUID'),
),
migrations.AlterField(
model_name='auditlog',
name='company_uuid',
field=gvsds.apps.core.models.UUIDField(null=True, blank=True, db_column='CompanyUUID', verbose_name='公司UUID'),
),
migrations.AlterField(
model_name='auditlog',
name='user_uuid',
field=gvsds.apps.core.models.UUIDField(null=True, blank=True, db_column='UserUUID', verbose_name='操作人UUID'),
),
migrations.AlterField(
model_name='abnormaluserlog',
name='tenant_uuid',
field=gvsds.apps.core.models.UUIDField(null=True, blank=True, db_column='TenantUUID', verbose_name='租户UUID'),
),
migrations.AlterField(
model_name='abnormaluserlog',
name='company_uuid',
field=gvsds.apps.core.models.UUIDField(null=True, blank=True, db_column='CompanyUUID', verbose_name='公司UUID'),
),
migrations.AlterField(
model_name='abnormaluserlog',
name='user_uuid',
field=gvsds.apps.core.models.UUIDField(null=True, blank=True, db_column='UserUUID', verbose_name='用户UUID'),
),
migrations.AlterField(
model_name='usermailbox',
name='user_uuid',
field=gvsds.apps.core.models.UUIDField(db_column='UserUUID', db_index=True, verbose_name='用户UUID'),
),
migrations.AlterField(
model_name='mailcontact',
name='user_uuid',
field=gvsds.apps.core.models.UUIDField(db_column='UserUUID', db_index=True, verbose_name='归属用户UUID'),
),
migrations.AlterField(
model_name='usergiteaaccount',
name='user_uuid',
field=gvsds.apps.core.models.UUIDField(db_column='UserUUID', db_index=True, verbose_name='用户UUID'),
),
]
+36 -31
View File
@@ -51,7 +51,7 @@ class CompanyInfo(QModel):
"""企业信息表——工商注册与企业详情"""
CompanyInfoUUID = UUIDField(primary_key=True, verbose_name='企业信息UUID')
TenantUUID = models.ForeignKey('Tenant', on_delete=models.SET_NULL, null=True, blank=True, related_name='+', db_column='TenantUUID', verbose_name='租户UUID')
TenantUUID = UUIDField(null=True, blank=True, db_column='TenantUUID', verbose_name='租户UUID')
EnterpriseName = models.CharField(max_length=256, verbose_name='企业全称')
EnterpriseShortName = models.CharField(max_length=100, verbose_name='企业简称')
CreditCode = models.CharField(max_length=64, unique=True, verbose_name='统一社会信用代码')
@@ -140,8 +140,8 @@ class Company(QModel):
"""公司表——系统内组织机构"""
CompanyUUID = UUIDField(primary_key=True, verbose_name='公司UUID')
TenantUUID = models.ForeignKey('Tenant', on_delete=models.CASCADE, related_name='+', db_column='TenantUUID', verbose_name='租户UUID')
ParentCompanyUUID = models.ForeignKey('self', on_delete=models.SET_NULL, null=True, blank=True, related_name='+', db_column='ParentCompanyUUID', verbose_name='上级公司UUID')
TenantUUID = UUIDField(db_column='TenantUUID', verbose_name='租户UUID')
ParentCompanyUUID = UUIDField(null=True, blank=True, db_column='ParentCompanyUUID', verbose_name='上级公司UUID')
CompanyName = models.CharField(max_length=256, verbose_name='公司全称')
CompanyShort = models.CharField(max_length=100, verbose_name='公司简称')
CompanyIcon = models.CharField(max_length=512, null=True, blank=True, db_column='CompanyIcon', verbose_name='公司图标')
@@ -164,8 +164,8 @@ class Department(QModel):
DeptUUID = UUIDField(primary_key=True, verbose_name='部门UUID')
TenantUUID = UUIDField(null=True, blank=True, verbose_name='租户UUID')
CompanyUUID = models.ForeignKey('Company', on_delete=models.CASCADE, related_name='department_set', db_column='CompanyUUID', verbose_name='公司UUID')
ParentDeptUUID = models.ForeignKey('self', on_delete=models.SET_NULL, null=True, blank=True, related_name='children', db_column='ParentDeptUUID', verbose_name='上级部门UUID')
CompanyUUID = UUIDField(db_column='CompanyUUID', verbose_name='公司UUID')
ParentDeptUUID = UUIDField(null=True, blank=True, db_column='ParentDeptUUID', verbose_name='上级部门UUID')
DeptName = models.CharField(max_length=256, verbose_name='部门名称')
DeptSort = models.IntegerField(default=0, verbose_name='排序')
DeptStatus = models.SmallIntegerField(default=1, verbose_name='部门状态')
@@ -186,7 +186,8 @@ class FileAsset(QModel):
"""文件资产表——文件存储与引用管理"""
AssetUUID = UUIDField(primary_key=True, verbose_name='资产UUID')
CompanyUUID = models.ForeignKey('Company', on_delete=models.SET_NULL, null=True, blank=True, related_name='fileasset_set', db_column='CompanyUUID', verbose_name='公司UUID')
TenantUUID = UUIDField(null=True, blank=True, verbose_name='租户UUID')
CompanyUUID = UUIDField(null=True, blank=True, db_column='CompanyUUID', verbose_name='公司UUID')
FileName = models.CharField(max_length=256, verbose_name='文件名')
FileSHA1 = models.CharField(max_length=40, unique=True, verbose_name='文件SHA1')
FileSize = models.IntegerField(verbose_name='文件大小')
@@ -213,8 +214,8 @@ class WorkOrder(QModel):
Category = models.CharField(max_length=64, default='other', verbose_name='分类')
Priority = models.SmallIntegerField(default=0, verbose_name='优先级')
Status = models.SmallIntegerField(default=0, verbose_name='状态')
CreatorUUID = models.ForeignKey(User, on_delete=models.CASCADE, related_name='+', db_index=True, db_column='CreatorUUID', verbose_name='创建人UUID')
AssigneeUUID = models.ForeignKey(User, on_delete=models.SET_NULL, null=True, blank=True, related_name='+', db_column='AssigneeUUID', verbose_name='指派人UUID')
CreatorUUID = UUIDField(db_index=True, db_column='CreatorUUID', verbose_name='创建人UUID')
AssigneeUUID = UUIDField(null=True, blank=True, db_column='AssigneeUUID', verbose_name='指派人UUID')
Resolution = models.CharField(max_length=4096, default='', verbose_name='解决方案')
CreateTime = models.DateTimeField(default=datetime.datetime.utcnow, verbose_name='创建时间')
UpdateTime = models.DateTimeField(null=True, blank=True, verbose_name='更新时间')
@@ -232,8 +233,8 @@ class Message(QModel):
"""消息表——系统通知与站内信"""
MessageUUID = UUIDField(primary_key=True, verbose_name='消息UUID')
SenderUUID = models.ForeignKey(User, on_delete=models.SET_NULL, null=True, blank=True, related_name='+', db_column='SenderUUID', verbose_name='发送者UUID')
ReceiverUUID = models.ForeignKey(User, on_delete=models.CASCADE, related_name='+', db_index=True, db_column='ReceiverUUID', verbose_name='接收者UUID')
SenderUUID = UUIDField(null=True, blank=True, db_column='SenderUUID', verbose_name='发送者UUID')
ReceiverUUID = UUIDField(db_index=True, db_column='ReceiverUUID', verbose_name='接收者UUID')
Title = models.CharField(max_length=256, verbose_name='标题')
Content = models.TextField(default='', verbose_name='内容')
MsgType = models.SmallIntegerField(default=0, verbose_name='消息类型')
@@ -254,8 +255,8 @@ class Menu(QModel):
"""菜单表——系统导航与功能入口"""
MenuUUID = UUIDField(primary_key=True, verbose_name='菜单UUID')
CompanyUUID = models.ForeignKey('Company', on_delete=models.SET_NULL, null=True, blank=True, related_name='menu_set', db_column='CompanyUUID', verbose_name='公司UUID')
ParentMenuUUID = models.ForeignKey('self', on_delete=models.SET_NULL, null=True, blank=True, related_name='children', db_column='ParentMenuUUID', verbose_name='上级菜单UUID')
CompanyUUID = UUIDField(null=True, blank=True, db_column='CompanyUUID', verbose_name='公司UUID')
ParentMenuUUID = UUIDField(null=True, blank=True, db_column='ParentMenuUUID', verbose_name='上级菜单UUID')
MenuName = models.CharField(max_length=128, verbose_name='菜单名称')
MenuTitle = models.CharField(max_length=128, verbose_name='菜单标题')
MenuIcon = models.CharField(max_length=128, default='', verbose_name='菜单图标')
@@ -308,7 +309,7 @@ class Workgroup(QModel):
WorkgroupUUID = UUIDField(primary_key=True, verbose_name='工作组UUID')
TenantUUID = UUIDField(null=True, blank=True, verbose_name='租户UUID')
CompanyUUID = models.ForeignKey('Company', on_delete=models.CASCADE, related_name='+', db_column='CompanyUUID', verbose_name='公司UUID')
CompanyUUID = UUIDField(db_column='CompanyUUID', verbose_name='公司UUID')
WorkgroupName = models.CharField(max_length=256, verbose_name='工作组名称')
WorkgroupEnglishName = models.CharField(max_length=256, verbose_name='工作组英文名')
WorkgroupIntroduction = models.CharField(max_length=1024, verbose_name='工作组介绍')
@@ -331,9 +332,10 @@ class WorkgroupRole(QModel):
"""
WorkgroupRoleUUID = UUIDField(primary_key=True, verbose_name='关联UUID')
WorkgroupUUID = models.ForeignKey('Workgroup', on_delete=models.CASCADE, related_name='+', db_column='WorkgroupUUID', verbose_name='工作组UUID')
WorkgroupUUID = UUIDField(db_column='WorkgroupUUID', verbose_name='工作组UUID')
RoleUUID = UUIDField(verbose_name='角色UUID')
CompanyUUID = models.ForeignKey('Company', on_delete=models.CASCADE, related_name='+', db_column='CompanyUUID', verbose_name='公司UUID')
TenantUUID = UUIDField(null=True, blank=True, verbose_name='租户UUID')
CompanyUUID = UUIDField(db_column='CompanyUUID', verbose_name='公司UUID')
RoleType = models.SmallIntegerField(default=0, verbose_name='角色类型')
CreateTime = models.DateTimeField(default=datetime.datetime.utcnow, verbose_name='创建时间')
@@ -356,8 +358,9 @@ class UserRoleWorkgroup(QModel):
UserRoleWorkgroupUUID = UUIDField(primary_key=True, verbose_name='关联UUID')
UserRoleUUID = UUIDField(verbose_name='用户-角色关联UUID')
WorkgroupUUID = models.ForeignKey('Workgroup', on_delete=models.CASCADE, related_name='+', db_column='WorkgroupUUID', verbose_name='工作组UUID')
CompanyUUID = models.ForeignKey('Company', on_delete=models.CASCADE, related_name='+', db_column='CompanyUUID', verbose_name='公司UUID')
WorkgroupUUID = UUIDField(db_column='WorkgroupUUID', verbose_name='工作组UUID')
TenantUUID = UUIDField(null=True, blank=True, verbose_name='租户UUID')
CompanyUUID = UUIDField(db_column='CompanyUUID', verbose_name='公司UUID')
RoleType = models.SmallIntegerField(default=0, verbose_name='角色类型')
CreateTime = models.DateTimeField(default=datetime.datetime.utcnow, verbose_name='创建时间')
@@ -381,8 +384,9 @@ class UserRoleDepartment(QModel):
UserRoleDepartmentUUID = UUIDField(primary_key=True, verbose_name='关联UUID')
UserRoleUUID = UUIDField(verbose_name='用户-角色关联UUID')
DeptUUID = models.ForeignKey('Department', on_delete=models.CASCADE, related_name='+', db_column='DeptUUID', verbose_name='部门UUID')
CompanyUUID = models.ForeignKey('Company', on_delete=models.CASCADE, related_name='+', db_column='CompanyUUID', verbose_name='公司UUID')
DeptUUID = UUIDField(db_column='DeptUUID', verbose_name='部门UUID')
TenantUUID = UUIDField(null=True, blank=True, verbose_name='租户UUID')
CompanyUUID = UUIDField(db_column='CompanyUUID', verbose_name='公司UUID')
RoleType = models.SmallIntegerField(default=0, verbose_name='角色类型')
CreateTime = models.DateTimeField(default=datetime.datetime.utcnow, verbose_name='创建时间')
@@ -416,8 +420,8 @@ class Backpack(QModel):
"""背包表——用户物品栏"""
BackpackItemUUID = UUIDField(primary_key=True, verbose_name='背包物品UUID')
UserUUID = models.ForeignKey(User, on_delete=models.CASCADE, related_name='+', db_column='UserUUID', verbose_name='用户UUID')
ItemTemplateUUID = models.ForeignKey('ItemReference', on_delete=models.CASCADE, related_name='+', db_column='ItemTemplateUUID', verbose_name='物品模板UUID')
UserUUID = UUIDField(db_column='UserUUID', verbose_name='用户UUID')
ItemTemplateUUID = UUIDField(db_column='ItemTemplateUUID', verbose_name='物品模板UUID')
_ItemName = models.CharField(max_length=128, null=True, blank=True, verbose_name='物品名称缓存')
_ItemIcon = models.CharField(max_length=512, null=True, blank=True, verbose_name='物品图标缓存')
_ItemIconColor = models.CharField(max_length=6, null=True, blank=True, verbose_name='图标颜色缓存')
@@ -616,7 +620,7 @@ class PersonalPage(QModel):
class UserSettings(QModel):
"""用户设置表——存储每位用户的个性化系统设置"""
UserUUID = models.ForeignKey(User, on_delete=models.CASCADE, unique=True, db_column='UserUUID', verbose_name='用户UUID')
UserUUID = UUIDField(unique=True, db_column='UserUUID', verbose_name='用户UUID')
SettingsData = models.TextField(default='', verbose_name='设置数据')
class Meta:
@@ -635,9 +639,9 @@ class AuditLog(QModel):
"""
AuditLogUUID = UUIDField(primary_key=True, verbose_name='日志UUID')
TenantUUID = models.ForeignKey('Tenant', on_delete=models.SET_NULL, null=True, blank=True, related_name='+', db_column='TenantUUID', verbose_name='租户UUID')
CompanyUUID = models.ForeignKey('Company', on_delete=models.SET_NULL, null=True, blank=True, related_name='+', db_column='CompanyUUID', verbose_name='公司UUID')
UserUUID = models.ForeignKey(User, on_delete=models.SET_NULL, null=True, blank=True, related_name='+', db_column='UserUUID', verbose_name='操作人UUID')
TenantUUID = UUIDField(null=True, blank=True, db_column='TenantUUID', verbose_name='租户UUID')
CompanyUUID = UUIDField(null=True, blank=True, db_column='CompanyUUID', verbose_name='公司UUID')
UserUUID = UUIDField(null=True, blank=True, db_column='UserUUID', verbose_name='操作人UUID')
TableName = models.CharField(max_length=64, db_index=True, verbose_name='表名')
Action = models.CharField(max_length=16, verbose_name='操作类型')
TargetUUID = UUIDField(null=True, blank=True, verbose_name='目标记录UUID')
@@ -665,9 +669,9 @@ class AbnormalUserLog(QModel):
"""
LogUUID = UUIDField(primary_key=True, verbose_name='日志UUID')
TenantUUID = models.ForeignKey('Tenant', on_delete=models.SET_NULL, null=True, blank=True, related_name='+', db_column='TenantUUID', verbose_name='租户UUID')
CompanyUUID = models.ForeignKey('Company', on_delete=models.SET_NULL, null=True, blank=True, related_name='+', db_column='CompanyUUID', verbose_name='公司UUID')
UserUUID = models.ForeignKey(User, on_delete=models.SET_NULL, null=True, blank=True, related_name='+', db_column='UserUUID', verbose_name='用户UUID')
TenantUUID = UUIDField(null=True, blank=True, db_column='TenantUUID', verbose_name='租户UUID')
CompanyUUID = UUIDField(null=True, blank=True, db_column='CompanyUUID', verbose_name='公司UUID')
UserUUID = UUIDField(null=True, blank=True, db_column='UserUUID', verbose_name='用户UUID')
AccountID = models.CharField(max_length=64, default='', db_index=True, verbose_name='账号标识')
IPAddress = models.CharField(max_length=64, default='', db_index=True, verbose_name='客户端IP')
RealIP = models.CharField(max_length=64, default='', verbose_name='真实IP')
@@ -702,7 +706,7 @@ class UserMailbox(QModel):
"""
UserMailboxUUID = UUIDField(primary_key=True, verbose_name='邮箱记录UUID')
UserUUID = models.ForeignKey(User, on_delete=models.CASCADE, db_column='UserUUID', db_index=True, verbose_name='用户UUID')
UserUUID = UUIDField(db_column='UserUUID', db_index=True, verbose_name='用户UUID')
MailboxName = models.CharField(max_length=256, unique=True, verbose_name='邮箱名称')
PrincipalId = models.IntegerField(null=True, blank=True, verbose_name='Stalwart账户ID')
QuotaMB = models.IntegerField(default=1024, verbose_name='配额(MB)')
@@ -728,7 +732,7 @@ class MailContact(QModel):
"""
MailContactUUID = UUIDField(primary_key=True, default=_NewUuidBytes, verbose_name='联系人UUID')
UserUUID = models.ForeignKey(User, on_delete=models.CASCADE, db_column='UserUUID', db_index=True, verbose_name='归属用户UUID')
UserUUID = UUIDField(db_column='UserUUID', db_index=True, verbose_name='归属用户UUID')
ContactName = models.CharField(max_length=128, default='', blank=True, verbose_name='联系人名称')
ContactEmail = models.CharField(max_length=256, db_index=True, verbose_name='联系人邮箱')
CreateTime = models.DateTimeField(default=datetime.datetime.utcnow, verbose_name='创建时间')
@@ -756,7 +760,7 @@ class UserGiteaAccount(QModel):
"""
UserGiteaAccountUUID = UUIDField(primary_key=True, verbose_name='Gitea记录UUID')
UserUUID = models.ForeignKey(User, on_delete=models.CASCADE, db_column='UserUUID', db_index=True, verbose_name='用户UUID')
UserUUID = UUIDField(db_column='UserUUID', db_index=True, verbose_name='用户UUID')
GiteaLogin = models.CharField(max_length=256, unique=True, verbose_name='Gitea用户名')
GiteaUserId = models.IntegerField(null=True, blank=True, verbose_name='Gitea用户ID')
Email = models.CharField(max_length=256, default='', blank=True, db_column='Email', verbose_name='工作邮箱')
@@ -848,6 +852,7 @@ class CompanyApp(QModel):
"""
CompanyAppUUID = UUIDField(primary_key=True, verbose_name='公司安装记录UUID')
TenantUUID = UUIDField(null=True, blank=True, verbose_name='租户UUID')
CompanyUUID = UUIDField(db_column='CompanyUUID', verbose_name='公司UUID')
AppUUID = UUIDField(db_column='AppUUID', verbose_name='应用UUID')
InstallStatus = models.SmallIntegerField(default=1, verbose_name='安装状态(1启用/0停用)')