256 lines
9.4 KiB
Go
256 lines
9.4 KiB
Go
package models
|
||
|
||
import (
|
||
"fmt"
|
||
|
||
"github.com/beego/beego/v2/client/orm"
|
||
beego "github.com/beego/beego/v2/server/web"
|
||
_ "github.com/go-sql-driver/mysql"
|
||
)
|
||
|
||
// Orm 全局 ORM 对象,供业务层和控制器使用
|
||
var Orm orm.Ormer
|
||
|
||
// Init 初始化模型层资源(数据库连接、模型注册等)。
|
||
func Init(_ string) {
|
||
// 从配置读取数据库连接信息
|
||
user, _ := beego.AppConfig.String("mysqluser")
|
||
pass, _ := beego.AppConfig.String("mysqlpass")
|
||
urls, _ := beego.AppConfig.String("mysqlurls")
|
||
dbname, _ := beego.AppConfig.String("mysqldb")
|
||
|
||
if user == "" || urls == "" || dbname == "" {
|
||
panic("数据库配置(mysqluser/mysqlurls/mysqldb) 未正确设置")
|
||
}
|
||
|
||
// 组装 DSN:user:pass@tcp(host:port)/dbname?charset=utf8mb4&parseTime=True&loc=Local
|
||
dsn := fmt.Sprintf("%s:%s@tcp(%s)/%s?charset=utf8mb4&parseTime=True&loc=Local", user, pass, urls, dbname)
|
||
|
||
// 注册默认数据库
|
||
if err := orm.RegisterDataBase("default", "mysql", dsn); err != nil {
|
||
panic("注册数据库失败: " + err.Error())
|
||
}
|
||
|
||
// 注册模型
|
||
orm.RegisterModel(
|
||
new(SystemTenant),
|
||
new(SystemTenantUser),
|
||
new(BackendOrganization),
|
||
new(BackendEmployee),
|
||
new(BackendPosition),
|
||
new(BackendErpContact),
|
||
new(BackendApprovalFlow),
|
||
new(BackendApprovalRecord),
|
||
new(BackendReimbursement),
|
||
new(BackendReimbursementItem),
|
||
new(BackendReimbursementExpenseType),
|
||
new(SystemMenu),
|
||
new(AdminUser),
|
||
new(AdminRole),
|
||
new(SystemFile),
|
||
new(SystemFilesCategory),
|
||
new(SystemSMSTask),
|
||
new(SystemOperationLog),
|
||
new(SystemLoginLog),
|
||
new(SystemDomainPool),
|
||
new(SystemTenantDomain),
|
||
new(SystemModules),
|
||
new(StorageConfig),
|
||
new(TenantSiteSetting),
|
||
new(ComplaintCategory),
|
||
new(PlatformComplaint),
|
||
new(SystemSoftwareUpgrade),
|
||
new(PlatformCursorEquipment),
|
||
new(PlatformCursorActivationCode),
|
||
new(PlatformCursorEquipmentIpLog),
|
||
new(PlatformAccountPoolKiro),
|
||
new(PlatformAccountPoolWindsurf),
|
||
new(PlatformAccountPoolCursor),
|
||
new(PlatformAccountPoolCodex),
|
||
new(PlatformNotebook),
|
||
new(PlatformAgentApi),
|
||
new(PlatformPasswordStore),
|
||
new(BackendPasswordStore),
|
||
new(BackendUserNotifyConfig),
|
||
new(TenantCrmCustomer),
|
||
new(TenantCrmSupplier),
|
||
new(TenantCrmClue),
|
||
new(TenantCrmBusiness),
|
||
new(TenantCrmProject),
|
||
new(TenantCrmFollow),
|
||
new(TenantCrmAttach),
|
||
new(TenantCrmEntityContact),
|
||
new(TenantCrmOperateLog),
|
||
new(TenantCrmContract),
|
||
new(ErpAccountSet),
|
||
new(ErpNormalSetting),
|
||
new(ErpCompanyContact),
|
||
new(BackendAiProvider),
|
||
new(BackendAiChatSession),
|
||
new(BackendAiChatMessage),
|
||
new(BackendAiChatPreset),
|
||
new(BackendMcpTool),
|
||
new(BackendMcpServer),
|
||
|
||
new(CmsArticleCategory),
|
||
new(CmsArticle),
|
||
new(CmsProductCategory),
|
||
new(CmsProduct),
|
||
new(CmsSolutionCategory),
|
||
new(CmsSolution),
|
||
|
||
new(CmsFrontendTemplate),
|
||
new(CmsFrontendBanner),
|
||
new(CmsFrontendFriendlink),
|
||
new(CmsFrontendOnepage),
|
||
new(BackendMenuFront),
|
||
|
||
new(SystemReminderList),
|
||
|
||
new(SystemNormalSetting),
|
||
new(PlatformNormalSetting),
|
||
new(BackendNormalSetting),
|
||
|
||
new(PlatformSchedule),
|
||
new(PlatformScheduleReminder),
|
||
new(PlatformScheduleReminderSendLog),
|
||
|
||
new(BackendNotebook),
|
||
new(BackendSchedule),
|
||
new(BackendScheduleReminder),
|
||
new(BackendScheduleReminderSendLog),
|
||
|
||
new(OaSchedule),
|
||
new(OaNotice),
|
||
new(OaDocCategory),
|
||
new(OaDoc),
|
||
new(OaDocLink),
|
||
new(OaDocShare),
|
||
new(BackendOaCompensationScheme),
|
||
new(BackendOaPayroll),
|
||
new(BackendOaPayrollItem),
|
||
new(BackendEmployeeFile),
|
||
new(BackendEmployeeFileRecord),
|
||
)
|
||
|
||
// 创建全局 Ormer
|
||
Orm = orm.NewOrm()
|
||
|
||
// 补齐历史库缺失的列(已存在时 MySQL 报 duplicate column,统一忽略)
|
||
EnsureAdminRoleTenantColumn()
|
||
EnsureAdminRoleCustomColumn()
|
||
EnsureTenantUserOrgColumn()
|
||
EnsureCrmCustomerPoolColumns()
|
||
EnsureCrmCreateUserColumn()
|
||
EnsureCrmProjectDocColumn()
|
||
EnsureCrmContractTable()
|
||
EnsureCrmContractOurRoleColumn()
|
||
}
|
||
|
||
// EnsureCrmContractOurRoleColumn 补齐合同表的我方角色字段(存量表已建时新增;
|
||
// 旧版「合同性质 contract_nature」字段弃用但保留不动,表不存在或列已存在时忽略错误)。
|
||
func EnsureCrmContractOurRoleColumn() {
|
||
sql := "ALTER TABLE " + new(TenantCrmContract).TableName() +
|
||
" ADD COLUMN our_role tinyint NOT NULL DEFAULT 2 COMMENT '我方角色:1甲方/2乙方/3丙方/4丁方'"
|
||
_, _ = Orm.Raw(sql).Exec()
|
||
}
|
||
|
||
// EnsureCrmContractTable 合同表建表(CREATE TABLE IF NOT EXISTS,可重复执行;
|
||
// 建表失败(如表已存在但结构不一致)时静默忽略,可用 sql/yz_backend_crm_contract.sql 手动修复)。
|
||
func EnsureCrmContractTable() {
|
||
sql := `CREATE TABLE IF NOT EXISTS yz_backend_crm_contract (
|
||
id bigint(20) NOT NULL AUTO_INCREMENT COMMENT '自增主键ID',
|
||
tenant_id varchar(64) NOT NULL COMMENT '租户ID',
|
||
contract_no varchar(50) NOT NULL DEFAULT '' COMMENT '合同编号',
|
||
contract_name varchar(100) NOT NULL COMMENT '合同名称',
|
||
contract_category varchar(20) NOT NULL DEFAULT '' COMMENT '合同分类:1开发/2服务/3销售/4租赁/5采购/6运维/7咨询/8其他',
|
||
our_role tinyint(4) NOT NULL DEFAULT '2' COMMENT '我方角色:1甲方/2乙方/3丙方/4丁方',
|
||
party_count tinyint(4) NOT NULL DEFAULT '2' COMMENT '合同形式:2/3/4方',
|
||
project_id bigint(20) DEFAULT NULL COMMENT '关联项目ID,空=无头合同',
|
||
project_name varchar(100) NOT NULL DEFAULT '' COMMENT '项目名称',
|
||
owner_user_id varchar(64) NOT NULL DEFAULT '' COMMENT '项目负责人用户ID',
|
||
owner_user_name varchar(128) NOT NULL DEFAULT '' COMMENT '项目负责人姓名',
|
||
sign_date date DEFAULT NULL COMMENT '签订日期',
|
||
effective_date date DEFAULT NULL COMMENT '生效日期',
|
||
expire_date date DEFAULT NULL COMMENT '结束日期',
|
||
parties text COMMENT '各方签约主体JSON',
|
||
products text COMMENT '产品清单JSON',
|
||
hardware_amount decimal(14,2) NOT NULL DEFAULT '0.00' COMMENT '硬件部分金额',
|
||
software_amount decimal(14,2) NOT NULL DEFAULT '0.00' COMMENT '软件部分金额',
|
||
other_amount decimal(14,2) NOT NULL DEFAULT '0.00' COMMENT '其他部分金额',
|
||
total_amount decimal(14,2) NOT NULL DEFAULT '0.00' COMMENT '合同总金额',
|
||
total_cost decimal(14,2) NOT NULL DEFAULT '0.00' COMMENT '产品总成本',
|
||
total_profit decimal(14,2) NOT NULL DEFAULT '0.00' COMMENT '合同总利润',
|
||
status tinyint(4) NOT NULL DEFAULT '1' COMMENT '状态:1草稿/2已完成/3已作废/4履约中/5执行异常',
|
||
step tinyint(4) NOT NULL DEFAULT '1' COMMENT '进度步骤:1合同信息/2产品清单',
|
||
remark text COMMENT '备注',
|
||
create_user_id varchar(64) NOT NULL DEFAULT '' COMMENT '创建人用户ID',
|
||
create_time datetime NOT NULL DEFAULT CURRENT_TIMESTAMP COMMENT '创建时间',
|
||
update_time datetime NOT NULL DEFAULT CURRENT_TIMESTAMP ON UPDATE CURRENT_TIMESTAMP COMMENT '更新时间',
|
||
delete_time datetime DEFAULT NULL COMMENT '删除时间(软删除)',
|
||
PRIMARY KEY (id),
|
||
KEY idx_tenant_id (tenant_id),
|
||
KEY idx_contract_name (tenant_id,contract_name),
|
||
KEY idx_contract_no (tenant_id,contract_no),
|
||
KEY idx_project (tenant_id,project_id),
|
||
KEY idx_status (tenant_id,status),
|
||
KEY idx_delete_time (delete_time)
|
||
) ENGINE=InnoDB DEFAULT CHARSET=utf8mb4 COMMENT='租户CRM合同表'`
|
||
if _, err := Orm.Raw(sql).Exec(); err != nil {
|
||
// 表已存在或执行失败时忽略(完整表结构见 sql/yz_backend_crm_contract.sql)
|
||
return
|
||
}
|
||
}
|
||
|
||
// EnsureCrmProjectDocColumn 补齐项目表的文档库文件夹分类字段(项目文档绑定 OA 文档库)。
|
||
// 表不存在或列已存在时忽略错误。
|
||
func EnsureCrmProjectDocColumn() {
|
||
sql := "ALTER TABLE " + new(TenantCrmProject).TableName() +
|
||
" ADD COLUMN doc_category_id bigint unsigned NOT NULL DEFAULT 0 COMMENT '关联OA文档库项目文件夹分类ID'"
|
||
_, _ = Orm.Raw(sql).Exec()
|
||
}
|
||
|
||
|
||
// EnsureCrmCreateUserColumn 补齐客户/供应商的创建人字段(用于删除权限校验)。
|
||
// 同样兼容历史表名差异,表不存在或列已存在时忽略错误。
|
||
func EnsureCrmCreateUserColumn() {
|
||
tables := []string{
|
||
new(TenantCrmCustomer).TableName(), "yz_tenant_crm_customer",
|
||
new(TenantCrmSupplier).TableName(), "yz_tenant_crm_supplier",
|
||
}
|
||
for _, table := range tables {
|
||
sql := "ALTER TABLE " + table +
|
||
" ADD COLUMN create_user_id varchar(64) NOT NULL DEFAULT '' COMMENT '创建人用户ID,用于删除权限校验'"
|
||
if _, err := Orm.Raw(sql).Exec(); err != nil {
|
||
continue
|
||
}
|
||
}
|
||
}
|
||
|
||
// EnsureCrmCustomerPoolColumns 补齐客户公海相关字段。
|
||
// 兼容历史表名差异:模型 TableName 为 yz_backend_erp_customer,初始化 SQL 中为 yz_tenant_crm_customer,
|
||
// 对两个候选表名都执行 ALTER(表不存在或列已存在时忽略错误)。
|
||
func EnsureCrmCustomerPoolColumns() {
|
||
candidates := []string{
|
||
new(TenantCrmCustomer).TableName(),
|
||
"yz_tenant_crm_customer",
|
||
}
|
||
cols := []string{
|
||
"in_pool tinyint NOT NULL DEFAULT 0 COMMENT '是否在公海:0-否 1-是'",
|
||
"owner_user_id varchar(64) NOT NULL DEFAULT '' COMMENT '负责人ID,公海中为空'",
|
||
"owner_user_name varchar(128) NOT NULL DEFAULT '' COMMENT '负责人姓名'",
|
||
"last_owner_name varchar(128) NOT NULL DEFAULT '' COMMENT '移入公海前的原负责人'",
|
||
"pool_in_time datetime DEFAULT NULL COMMENT '进入公海时间'",
|
||
"pool_reason varchar(200) NOT NULL DEFAULT '' COMMENT '移入公海原因'",
|
||
}
|
||
for _, table := range candidates {
|
||
for _, col := range cols {
|
||
sql := fmt.Sprintf("ALTER TABLE %s ADD COLUMN %s", table, col)
|
||
if _, err := Orm.Raw(sql).Exec(); err != nil {
|
||
// 列已存在或表不存在时忽略
|
||
continue
|
||
}
|
||
}
|
||
}
|
||
}
|