-- ============================================================
-- 补全 / 恢复 code_count 全库表与字段 COMMENT
-- 可重复执行：列存在才 MODIFY；已有相同注释再跑无害。
-- 用法：
--   mysql -u root -p code_count < migrations/20260815_restore_column_comments.sql
-- 说明：
--   - 不改业务数据；仅重写列类型元数据中的 COMMENT（类型/默认值与 init.sql 对齐）
--   - 若某列尚未升级出来（旧库缺列），对应语句自动跳过
-- ============================================================

USE code_count;

-- 通用：表存在且列存在时才执行 ALTER
-- 用法示例见下方各 CALL 风格的动态 SQL

-- -------------------- users --------------------
ALTER TABLE users COMMENT='应用账号';
SET @sql = IF((SELECT COUNT(*) FROM information_schema.COLUMNS WHERE TABLE_SCHEMA=DATABASE() AND TABLE_NAME='users' AND COLUMN_NAME='id')>0,
  'ALTER TABLE users MODIFY COLUMN id BIGINT NOT NULL AUTO_INCREMENT COMMENT ''用户ID''', 'SELECT 1');
PREPARE st FROM @sql; EXECUTE st; DEALLOCATE PREPARE st;
SET @sql = IF((SELECT COUNT(*) FROM information_schema.COLUMNS WHERE TABLE_SCHEMA=DATABASE() AND TABLE_NAME='users' AND COLUMN_NAME='username')>0,
  'ALTER TABLE users MODIFY COLUMN username VARCHAR(64) NOT NULL COMMENT ''登录名''', 'SELECT 1');
PREPARE st FROM @sql; EXECUTE st; DEALLOCATE PREPARE st;
SET @sql = IF((SELECT COUNT(*) FROM information_schema.COLUMNS WHERE TABLE_SCHEMA=DATABASE() AND TABLE_NAME='users' AND COLUMN_NAME='password_hash')>0,
  'ALTER TABLE users MODIFY COLUMN password_hash VARCHAR(100) NOT NULL COMMENT ''bcrypt 密码哈希''', 'SELECT 1');
PREPARE st FROM @sql; EXECUTE st; DEALLOCATE PREPARE st;
SET @sql = IF((SELECT COUNT(*) FROM information_schema.COLUMNS WHERE TABLE_SCHEMA=DATABASE() AND TABLE_NAME='users' AND COLUMN_NAME='totp_secret')>0,
  'ALTER TABLE users MODIFY COLUMN totp_secret VARCHAR(64) NOT NULL DEFAULT '''' COMMENT ''TOTP Base32 密钥（仅管理员）''', 'SELECT 1');
PREPARE st FROM @sql; EXECUTE st; DEALLOCATE PREPARE st;
SET @sql = IF((SELECT COUNT(*) FROM information_schema.COLUMNS WHERE TABLE_SCHEMA=DATABASE() AND TABLE_NAME='users' AND COLUMN_NAME='totp_enabled')>0,
  'ALTER TABLE users MODIFY COLUMN totp_enabled TINYINT NOT NULL DEFAULT 0 COMMENT ''是否已启用 TOTP''', 'SELECT 1');
PREPARE st FROM @sql; EXECUTE st; DEALLOCATE PREPARE st;
SET @sql = IF((SELECT COUNT(*) FROM information_schema.COLUMNS WHERE TABLE_SCHEMA=DATABASE() AND TABLE_NAME='users' AND COLUMN_NAME='last_login_ip')>0,
  'ALTER TABLE users MODIFY COLUMN last_login_ip VARCHAR(64) NOT NULL DEFAULT '''' COMMENT ''最近登录 IP''', 'SELECT 1');
PREPARE st FROM @sql; EXECUTE st; DEALLOCATE PREPARE st;
SET @sql = IF((SELECT COUNT(*) FROM information_schema.COLUMNS WHERE TABLE_SCHEMA=DATABASE() AND TABLE_NAME='users' AND COLUMN_NAME='last_seen_at')>0,
  'ALTER TABLE users MODIFY COLUMN last_seen_at VARCHAR(32) NOT NULL DEFAULT '''' COMMENT ''最近活跃时间 RFC3339''', 'SELECT 1');
PREPARE st FROM @sql; EXECUTE st; DEALLOCATE PREPARE st;
SET @sql = IF((SELECT COUNT(*) FROM information_schema.COLUMNS WHERE TABLE_SCHEMA=DATABASE() AND TABLE_NAME='users' AND COLUMN_NAME='ai_banned')>0,
  'ALTER TABLE users MODIFY COLUMN ai_banned TINYINT NOT NULL DEFAULT 0 COMMENT ''禁止使用 AI''', 'SELECT 1');
PREPARE st FROM @sql; EXECUTE st; DEALLOCATE PREPARE st;
SET @sql = IF((SELECT COUNT(*) FROM information_schema.COLUMNS WHERE TABLE_SCHEMA=DATABASE() AND TABLE_NAME='users' AND COLUMN_NAME='disabled')>0,
  'ALTER TABLE users MODIFY COLUMN disabled TINYINT NOT NULL DEFAULT 0 COMMENT ''禁用账号''', 'SELECT 1');
PREPARE st FROM @sql; EXECUTE st; DEALLOCATE PREPARE st;
SET @sql = IF((SELECT COUNT(*) FROM information_schema.COLUMNS WHERE TABLE_SCHEMA=DATABASE() AND TABLE_NAME='users' AND COLUMN_NAME='created_at')>0,
  'ALTER TABLE users MODIFY COLUMN created_at VARCHAR(32) NOT NULL COMMENT ''注册时间（RFC3339）''', 'SELECT 1');
PREPARE st FROM @sql; EXECUTE st; DEALLOCATE PREPARE st;

-- -------------------- sync_todos --------------------
ALTER TABLE sync_todos COMMENT='待办同步表';
SET @sql = IF((SELECT COUNT(*) FROM information_schema.COLUMNS WHERE TABLE_SCHEMA=DATABASE() AND TABLE_NAME='sync_todos' AND COLUMN_NAME='user_id')>0,
  'ALTER TABLE sync_todos MODIFY COLUMN user_id BIGINT NOT NULL COMMENT ''所属用户ID''', 'SELECT 1');
PREPARE st FROM @sql; EXECUTE st; DEALLOCATE PREPARE st;
SET @sql = IF((SELECT COUNT(*) FROM information_schema.COLUMNS WHERE TABLE_SCHEMA=DATABASE() AND TABLE_NAME='sync_todos' AND COLUMN_NAME='uuid')>0,
  'ALTER TABLE sync_todos MODIFY COLUMN uuid CHAR(36) NOT NULL COMMENT ''客户端生成的全局唯一ID''', 'SELECT 1');
PREPARE st FROM @sql; EXECUTE st; DEALLOCATE PREPARE st;
SET @sql = IF((SELECT COUNT(*) FROM information_schema.COLUMNS WHERE TABLE_SCHEMA=DATABASE() AND TABLE_NAME='sync_todos' AND COLUMN_NAME='title')>0,
  'ALTER TABLE sync_todos MODIFY COLUMN title TEXT NOT NULL COMMENT ''标题''', 'SELECT 1');
PREPARE st FROM @sql; EXECUTE st; DEALLOCATE PREPARE st;
SET @sql = IF((SELECT COUNT(*) FROM information_schema.COLUMNS WHERE TABLE_SCHEMA=DATABASE() AND TABLE_NAME='sync_todos' AND COLUMN_NAME='content')>0,
  'ALTER TABLE sync_todos MODIFY COLUMN content MEDIUMTEXT NOT NULL COMMENT ''正文（Markdown，可含内嵌图片）''', 'SELECT 1');
PREPARE st FROM @sql; EXECUTE st; DEALLOCATE PREPARE st;
SET @sql = IF((SELECT COUNT(*) FROM information_schema.COLUMNS WHERE TABLE_SCHEMA=DATABASE() AND TABLE_NAME='sync_todos' AND COLUMN_NAME='project_name')>0,
  'ALTER TABLE sync_todos MODIFY COLUMN project_name VARCHAR(255) NOT NULL DEFAULT '''' COMMENT ''关联项目名（展示用）''', 'SELECT 1');
PREPARE st FROM @sql; EXECUTE st; DEALLOCATE PREPARE st;
SET @sql = IF((SELECT COUNT(*) FROM information_schema.COLUMNS WHERE TABLE_SCHEMA=DATABASE() AND TABLE_NAME='sync_todos' AND COLUMN_NAME='due_at')>0,
  'ALTER TABLE sync_todos MODIFY COLUMN due_at VARCHAR(32) NOT NULL DEFAULT '''' COMMENT ''截止时间''', 'SELECT 1');
PREPARE st FROM @sql; EXECUTE st; DEALLOCATE PREPARE st;
SET @sql = IF((SELECT COUNT(*) FROM information_schema.COLUMNS WHERE TABLE_SCHEMA=DATABASE() AND TABLE_NAME='sync_todos' AND COLUMN_NAME='priority')>0,
  'ALTER TABLE sync_todos MODIFY COLUMN priority VARCHAR(16) NOT NULL DEFAULT ''medium'' COMMENT ''优先级：low/medium/high''', 'SELECT 1');
PREPARE st FROM @sql; EXECUTE st; DEALLOCATE PREPARE st;
SET @sql = IF((SELECT COUNT(*) FROM information_schema.COLUMNS WHERE TABLE_SCHEMA=DATABASE() AND TABLE_NAME='sync_todos' AND COLUMN_NAME='status')>0,
  'ALTER TABLE sync_todos MODIFY COLUMN status VARCHAR(16) NOT NULL DEFAULT ''open'' COMMENT ''状态：open/doing/done/cancelled''', 'SELECT 1');
PREPARE st FROM @sql; EXECUTE st; DEALLOCATE PREPARE st;
SET @sql = IF((SELECT COUNT(*) FROM information_schema.COLUMNS WHERE TABLE_SCHEMA=DATABASE() AND TABLE_NAME='sync_todos' AND COLUMN_NAME='history')>0,
  'ALTER TABLE sync_todos MODIFY COLUMN history MEDIUMTEXT NOT NULL COMMENT ''生命周期轨迹 JSON''', 'SELECT 1');
PREPARE st FROM @sql; EXECUTE st; DEALLOCATE PREPARE st;
SET @sql = IF((SELECT COUNT(*) FROM information_schema.COLUMNS WHERE TABLE_SCHEMA=DATABASE() AND TABLE_NAME='sync_todos' AND COLUMN_NAME='team_id')>0,
  'ALTER TABLE sync_todos MODIFY COLUMN team_id BIGINT NOT NULL DEFAULT 0 COMMENT ''共享团队ID，0=私密''', 'SELECT 1');
PREPARE st FROM @sql; EXECUTE st; DEALLOCATE PREPARE st;
SET @sql = IF((SELECT COUNT(*) FROM information_schema.COLUMNS WHERE TABLE_SCHEMA=DATABASE() AND TABLE_NAME='sync_todos' AND COLUMN_NAME='created_at')>0,
  'ALTER TABLE sync_todos MODIFY COLUMN created_at VARCHAR(32) NOT NULL DEFAULT '''' COMMENT ''创建时间''', 'SELECT 1');
PREPARE st FROM @sql; EXECUTE st; DEALLOCATE PREPARE st;
SET @sql = IF((SELECT COUNT(*) FROM information_schema.COLUMNS WHERE TABLE_SCHEMA=DATABASE() AND TABLE_NAME='sync_todos' AND COLUMN_NAME='updated_at')>0,
  'ALTER TABLE sync_todos MODIFY COLUMN updated_at VARCHAR(32) NOT NULL COMMENT ''最后更新时间（LWW）''', 'SELECT 1');
PREPARE st FROM @sql; EXECUTE st; DEALLOCATE PREPARE st;
SET @sql = IF((SELECT COUNT(*) FROM information_schema.COLUMNS WHERE TABLE_SCHEMA=DATABASE() AND TABLE_NAME='sync_todos' AND COLUMN_NAME='deleted')>0,
  'ALTER TABLE sync_todos MODIFY COLUMN deleted TINYINT NOT NULL DEFAULT 0 COMMENT ''软删除标记：1=已删''', 'SELECT 1');
PREPARE st FROM @sql; EXECUTE st; DEALLOCATE PREPARE st;

-- -------------------- sync_tickets --------------------
ALTER TABLE sync_tickets COMMENT='工单同步表';
SET @sql = IF((SELECT COUNT(*) FROM information_schema.COLUMNS WHERE TABLE_SCHEMA=DATABASE() AND TABLE_NAME='sync_tickets' AND COLUMN_NAME='user_id')>0,
  'ALTER TABLE sync_tickets MODIFY COLUMN user_id BIGINT NOT NULL COMMENT ''所属用户ID''', 'SELECT 1');
PREPARE st FROM @sql; EXECUTE st; DEALLOCATE PREPARE st;
SET @sql = IF((SELECT COUNT(*) FROM information_schema.COLUMNS WHERE TABLE_SCHEMA=DATABASE() AND TABLE_NAME='sync_tickets' AND COLUMN_NAME='uuid')>0,
  'ALTER TABLE sync_tickets MODIFY COLUMN uuid CHAR(36) NOT NULL COMMENT ''客户端生成的全局唯一ID''', 'SELECT 1');
PREPARE st FROM @sql; EXECUTE st; DEALLOCATE PREPARE st;
SET @sql = IF((SELECT COUNT(*) FROM information_schema.COLUMNS WHERE TABLE_SCHEMA=DATABASE() AND TABLE_NAME='sync_tickets' AND COLUMN_NAME='title')>0,
  'ALTER TABLE sync_tickets MODIFY COLUMN title TEXT NOT NULL COMMENT ''标题''', 'SELECT 1');
PREPARE st FROM @sql; EXECUTE st; DEALLOCATE PREPARE st;
SET @sql = IF((SELECT COUNT(*) FROM information_schema.COLUMNS WHERE TABLE_SCHEMA=DATABASE() AND TABLE_NAME='sync_tickets' AND COLUMN_NAME='description')>0,
  'ALTER TABLE sync_tickets MODIFY COLUMN description MEDIUMTEXT NOT NULL COMMENT ''描述（Markdown）''', 'SELECT 1');
PREPARE st FROM @sql; EXECUTE st; DEALLOCATE PREPARE st;
SET @sql = IF((SELECT COUNT(*) FROM information_schema.COLUMNS WHERE TABLE_SCHEMA=DATABASE() AND TABLE_NAME='sync_tickets' AND COLUMN_NAME='type')>0,
  'ALTER TABLE sync_tickets MODIFY COLUMN type VARCHAR(16) NOT NULL DEFAULT ''task'' COMMENT ''类型：task/bug/feature 等''', 'SELECT 1');
PREPARE st FROM @sql; EXECUTE st; DEALLOCATE PREPARE st;
SET @sql = IF((SELECT COUNT(*) FROM information_schema.COLUMNS WHERE TABLE_SCHEMA=DATABASE() AND TABLE_NAME='sync_tickets' AND COLUMN_NAME='project_name')>0,
  'ALTER TABLE sync_tickets MODIFY COLUMN project_name VARCHAR(255) NOT NULL DEFAULT '''' COMMENT ''关联项目名''', 'SELECT 1');
PREPARE st FROM @sql; EXECUTE st; DEALLOCATE PREPARE st;
SET @sql = IF((SELECT COUNT(*) FROM information_schema.COLUMNS WHERE TABLE_SCHEMA=DATABASE() AND TABLE_NAME='sync_tickets' AND COLUMN_NAME='start_at')>0,
  'ALTER TABLE sync_tickets MODIFY COLUMN start_at VARCHAR(32) NOT NULL DEFAULT '''' COMMENT ''开始时间''', 'SELECT 1');
PREPARE st FROM @sql; EXECUTE st; DEALLOCATE PREPARE st;
SET @sql = IF((SELECT COUNT(*) FROM information_schema.COLUMNS WHERE TABLE_SCHEMA=DATABASE() AND TABLE_NAME='sync_tickets' AND COLUMN_NAME='due_at')>0,
  'ALTER TABLE sync_tickets MODIFY COLUMN due_at VARCHAR(32) NOT NULL DEFAULT '''' COMMENT ''截止时间''', 'SELECT 1');
PREPARE st FROM @sql; EXECUTE st; DEALLOCATE PREPARE st;
SET @sql = IF((SELECT COUNT(*) FROM information_schema.COLUMNS WHERE TABLE_SCHEMA=DATABASE() AND TABLE_NAME='sync_tickets' AND COLUMN_NAME='status')>0,
  'ALTER TABLE sync_tickets MODIFY COLUMN status VARCHAR(16) NOT NULL DEFAULT ''open'' COMMENT ''状态''', 'SELECT 1');
PREPARE st FROM @sql; EXECUTE st; DEALLOCATE PREPARE st;
SET @sql = IF((SELECT COUNT(*) FROM information_schema.COLUMNS WHERE TABLE_SCHEMA=DATABASE() AND TABLE_NAME='sync_tickets' AND COLUMN_NAME='priority')>0,
  'ALTER TABLE sync_tickets MODIFY COLUMN priority VARCHAR(16) NOT NULL DEFAULT ''medium'' COMMENT ''优先级''', 'SELECT 1');
PREPARE st FROM @sql; EXECUTE st; DEALLOCATE PREPARE st;
SET @sql = IF((SELECT COUNT(*) FROM information_schema.COLUMNS WHERE TABLE_SCHEMA=DATABASE() AND TABLE_NAME='sync_tickets' AND COLUMN_NAME='history')>0,
  'ALTER TABLE sync_tickets MODIFY COLUMN history MEDIUMTEXT NOT NULL COMMENT ''生命周期轨迹 JSON''', 'SELECT 1');
PREPARE st FROM @sql; EXECUTE st; DEALLOCATE PREPARE st;
SET @sql = IF((SELECT COUNT(*) FROM information_schema.COLUMNS WHERE TABLE_SCHEMA=DATABASE() AND TABLE_NAME='sync_tickets' AND COLUMN_NAME='team_id')>0,
  'ALTER TABLE sync_tickets MODIFY COLUMN team_id BIGINT NOT NULL DEFAULT 0 COMMENT ''共享团队ID，0=私密''', 'SELECT 1');
PREPARE st FROM @sql; EXECUTE st; DEALLOCATE PREPARE st;
SET @sql = IF((SELECT COUNT(*) FROM information_schema.COLUMNS WHERE TABLE_SCHEMA=DATABASE() AND TABLE_NAME='sync_tickets' AND COLUMN_NAME='created_at')>0,
  'ALTER TABLE sync_tickets MODIFY COLUMN created_at VARCHAR(32) NOT NULL DEFAULT '''' COMMENT ''创建时间''', 'SELECT 1');
PREPARE st FROM @sql; EXECUTE st; DEALLOCATE PREPARE st;
SET @sql = IF((SELECT COUNT(*) FROM information_schema.COLUMNS WHERE TABLE_SCHEMA=DATABASE() AND TABLE_NAME='sync_tickets' AND COLUMN_NAME='updated_at')>0,
  'ALTER TABLE sync_tickets MODIFY COLUMN updated_at VARCHAR(32) NOT NULL COMMENT ''最后更新时间（LWW）''', 'SELECT 1');
PREPARE st FROM @sql; EXECUTE st; DEALLOCATE PREPARE st;
SET @sql = IF((SELECT COUNT(*) FROM information_schema.COLUMNS WHERE TABLE_SCHEMA=DATABASE() AND TABLE_NAME='sync_tickets' AND COLUMN_NAME='deleted')>0,
  'ALTER TABLE sync_tickets MODIFY COLUMN deleted TINYINT NOT NULL DEFAULT 0 COMMENT ''软删除标记''', 'SELECT 1');
PREPARE st FROM @sql; EXECUTE st; DEALLOCATE PREPARE st;

-- -------------------- sync_notes --------------------
ALTER TABLE sync_notes COMMENT='记事本同步表';
SET @sql = IF((SELECT COUNT(*) FROM information_schema.COLUMNS WHERE TABLE_SCHEMA=DATABASE() AND TABLE_NAME='sync_notes' AND COLUMN_NAME='user_id')>0,
  'ALTER TABLE sync_notes MODIFY COLUMN user_id BIGINT NOT NULL COMMENT ''所属用户ID''', 'SELECT 1');
PREPARE st FROM @sql; EXECUTE st; DEALLOCATE PREPARE st;
SET @sql = IF((SELECT COUNT(*) FROM information_schema.COLUMNS WHERE TABLE_SCHEMA=DATABASE() AND TABLE_NAME='sync_notes' AND COLUMN_NAME='uuid')>0,
  'ALTER TABLE sync_notes MODIFY COLUMN uuid CHAR(36) NOT NULL COMMENT ''客户端生成的全局唯一ID''', 'SELECT 1');
PREPARE st FROM @sql; EXECUTE st; DEALLOCATE PREPARE st;
SET @sql = IF((SELECT COUNT(*) FROM information_schema.COLUMNS WHERE TABLE_SCHEMA=DATABASE() AND TABLE_NAME='sync_notes' AND COLUMN_NAME='content')>0,
  'ALTER TABLE sync_notes MODIFY COLUMN content MEDIUMTEXT NOT NULL COMMENT ''记事本正文''', 'SELECT 1');
PREPARE st FROM @sql; EXECUTE st; DEALLOCATE PREPARE st;
SET @sql = IF((SELECT COUNT(*) FROM information_schema.COLUMNS WHERE TABLE_SCHEMA=DATABASE() AND TABLE_NAME='sync_notes' AND COLUMN_NAME='updated_at')>0,
  'ALTER TABLE sync_notes MODIFY COLUMN updated_at VARCHAR(32) NOT NULL COMMENT ''最后更新时间（LWW）''', 'SELECT 1');
PREPARE st FROM @sql; EXECUTE st; DEALLOCATE PREPARE st;
SET @sql = IF((SELECT COUNT(*) FROM information_schema.COLUMNS WHERE TABLE_SCHEMA=DATABASE() AND TABLE_NAME='sync_notes' AND COLUMN_NAME='deleted')>0,
  'ALTER TABLE sync_notes MODIFY COLUMN deleted TINYINT NOT NULL DEFAULT 0 COMMENT ''软删除标记''', 'SELECT 1');
PREPARE st FROM @sql; EXECUTE st; DEALLOCATE PREPARE st;

-- -------------------- sync_settings --------------------
ALTER TABLE sync_settings COMMENT='用户同步设置键值表';
SET @sql = IF((SELECT COUNT(*) FROM information_schema.COLUMNS WHERE TABLE_SCHEMA=DATABASE() AND TABLE_NAME='sync_settings' AND COLUMN_NAME='user_id')>0,
  'ALTER TABLE sync_settings MODIFY COLUMN user_id BIGINT NOT NULL COMMENT ''所属用户ID（全局资源挂在管理员 id=1）''', 'SELECT 1');
PREPARE st FROM @sql; EXECUTE st; DEALLOCATE PREPARE st;
SET @sql = IF((SELECT COUNT(*) FROM information_schema.COLUMNS WHERE TABLE_SCHEMA=DATABASE() AND TABLE_NAME='sync_settings' AND COLUMN_NAME='name')>0,
  'ALTER TABLE sync_settings MODIFY COLUMN name VARCHAR(64) NOT NULL COMMENT ''设置键名''', 'SELECT 1');
PREPARE st FROM @sql; EXECUTE st; DEALLOCATE PREPARE st;
SET @sql = IF((SELECT COUNT(*) FROM information_schema.COLUMNS WHERE TABLE_SCHEMA=DATABASE() AND TABLE_NAME='sync_settings' AND COLUMN_NAME='value')>0,
  'ALTER TABLE sync_settings MODIFY COLUMN value MEDIUMTEXT NOT NULL COMMENT ''设置值（明文或密文）''', 'SELECT 1');
PREPARE st FROM @sql; EXECUTE st; DEALLOCATE PREPARE st;
SET @sql = IF((SELECT COUNT(*) FROM information_schema.COLUMNS WHERE TABLE_SCHEMA=DATABASE() AND TABLE_NAME='sync_settings' AND COLUMN_NAME='updated_at')>0,
  'ALTER TABLE sync_settings MODIFY COLUMN updated_at VARCHAR(32) NOT NULL COMMENT ''最后更新时间''', 'SELECT 1');
PREPARE st FROM @sql; EXECUTE st; DEALLOCATE PREPARE st;

-- -------------------- user_profiles --------------------
ALTER TABLE user_profiles COMMENT='用户公开资料';
SET @sql = IF((SELECT COUNT(*) FROM information_schema.COLUMNS WHERE TABLE_SCHEMA=DATABASE() AND TABLE_NAME='user_profiles' AND COLUMN_NAME='user_id')>0,
  'ALTER TABLE user_profiles MODIFY COLUMN user_id BIGINT NOT NULL COMMENT ''对应用户ID''', 'SELECT 1');
PREPARE st FROM @sql; EXECUTE st; DEALLOCATE PREPARE st;
SET @sql = IF((SELECT COUNT(*) FROM information_schema.COLUMNS WHERE TABLE_SCHEMA=DATABASE() AND TABLE_NAME='user_profiles' AND COLUMN_NAME='nickname')>0,
  'ALTER TABLE user_profiles MODIFY COLUMN nickname VARCHAR(64) NOT NULL DEFAULT '''' COMMENT ''昵称''', 'SELECT 1');
PREPARE st FROM @sql; EXECUTE st; DEALLOCATE PREPARE st;
SET @sql = IF((SELECT COUNT(*) FROM information_schema.COLUMNS WHERE TABLE_SCHEMA=DATABASE() AND TABLE_NAME='user_profiles' AND COLUMN_NAME='title')>0,
  'ALTER TABLE user_profiles MODIFY COLUMN title VARCHAR(64) NOT NULL DEFAULT '''' COMMENT ''头衔/职位''', 'SELECT 1');
PREPARE st FROM @sql; EXECUTE st; DEALLOCATE PREPARE st;
SET @sql = IF((SELECT COUNT(*) FROM information_schema.COLUMNS WHERE TABLE_SCHEMA=DATABASE() AND TABLE_NAME='user_profiles' AND COLUMN_NAME='email')>0,
  'ALTER TABLE user_profiles MODIFY COLUMN email VARCHAR(128) NOT NULL DEFAULT '''' COMMENT ''公开邮箱''', 'SELECT 1');
PREPARE st FROM @sql; EXECUTE st; DEALLOCATE PREPARE st;
SET @sql = IF((SELECT COUNT(*) FROM information_schema.COLUMNS WHERE TABLE_SCHEMA=DATABASE() AND TABLE_NAME='user_profiles' AND COLUMN_NAME='bio')>0,
  'ALTER TABLE user_profiles MODIFY COLUMN bio VARCHAR(500) NOT NULL DEFAULT '''' COMMENT ''个人简介''', 'SELECT 1');
PREPARE st FROM @sql; EXECUTE st; DEALLOCATE PREPARE st;
SET @sql = IF((SELECT COUNT(*) FROM information_schema.COLUMNS WHERE TABLE_SCHEMA=DATABASE() AND TABLE_NAME='user_profiles' AND COLUMN_NAME='tech_tags')>0,
  'ALTER TABLE user_profiles MODIFY COLUMN tech_tags VARCHAR(1000) NOT NULL DEFAULT ''[]'' COMMENT ''技术栈标签 JSON 数组''', 'SELECT 1');
PREPARE st FROM @sql; EXECUTE st; DEALLOCATE PREPARE st;
SET @sql = IF((SELECT COUNT(*) FROM information_schema.COLUMNS WHERE TABLE_SCHEMA=DATABASE() AND TABLE_NAME='user_profiles' AND COLUMN_NAME='avatar_thumb')>0,
  'ALTER TABLE user_profiles MODIFY COLUMN avatar_thumb MEDIUMTEXT NOT NULL COMMENT ''头像缩略图（dataURL 或 URL）''', 'SELECT 1');
PREPARE st FROM @sql; EXECUTE st; DEALLOCATE PREPARE st;
SET @sql = IF((SELECT COUNT(*) FROM information_schema.COLUMNS WHERE TABLE_SCHEMA=DATABASE() AND TABLE_NAME='user_profiles' AND COLUMN_NAME='updated_at')>0,
  'ALTER TABLE user_profiles MODIFY COLUMN updated_at VARCHAR(32) NOT NULL COMMENT ''最后更新时间''', 'SELECT 1');
PREPARE st FROM @sql; EXECUTE st; DEALLOCATE PREPARE st;

-- -------------------- user_avatar_history --------------------
ALTER TABLE user_avatar_history COMMENT='用户头像历史';
SET @sql = IF((SELECT COUNT(*) FROM information_schema.COLUMNS WHERE TABLE_SCHEMA=DATABASE() AND TABLE_NAME='user_avatar_history' AND COLUMN_NAME='id')>0,
  'ALTER TABLE user_avatar_history MODIFY COLUMN id BIGINT NOT NULL AUTO_INCREMENT COMMENT ''历史记录ID''', 'SELECT 1');
PREPARE st FROM @sql; EXECUTE st; DEALLOCATE PREPARE st;
SET @sql = IF((SELECT COUNT(*) FROM information_schema.COLUMNS WHERE TABLE_SCHEMA=DATABASE() AND TABLE_NAME='user_avatar_history' AND COLUMN_NAME='user_id')>0,
  'ALTER TABLE user_avatar_history MODIFY COLUMN user_id BIGINT NOT NULL COMMENT ''所属用户ID''', 'SELECT 1');
PREPARE st FROM @sql; EXECUTE st; DEALLOCATE PREPARE st;
SET @sql = IF((SELECT COUNT(*) FROM information_schema.COLUMNS WHERE TABLE_SCHEMA=DATABASE() AND TABLE_NAME='user_avatar_history' AND COLUMN_NAME='mode')>0,
  'ALTER TABLE user_avatar_history MODIFY COLUMN mode VARCHAR(16) NOT NULL DEFAULT ''url'' COMMENT ''存储模式：url | base64''', 'SELECT 1');
PREPARE st FROM @sql; EXECUTE st; DEALLOCATE PREPARE st;
SET @sql = IF((SELECT COUNT(*) FROM information_schema.COLUMNS WHERE TABLE_SCHEMA=DATABASE() AND TABLE_NAME='user_avatar_history' AND COLUMN_NAME='value')>0,
  'ALTER TABLE user_avatar_history MODIFY COLUMN value MEDIUMTEXT NOT NULL COMMENT ''头像内容（URL 或 dataURL）''', 'SELECT 1');
PREPARE st FROM @sql; EXECUTE st; DEALLOCATE PREPARE st;
SET @sql = IF((SELECT COUNT(*) FROM information_schema.COLUMNS WHERE TABLE_SCHEMA=DATABASE() AND TABLE_NAME='user_avatar_history' AND COLUMN_NAME='created_at')>0,
  'ALTER TABLE user_avatar_history MODIFY COLUMN created_at VARCHAR(32) NOT NULL COMMENT ''写入时间（RFC3339）''', 'SELECT 1');
PREPARE st FROM @sql; EXECUTE st; DEALLOCATE PREPARE st;

-- -------------------- teams --------------------
ALTER TABLE teams COMMENT='团队';
SET @sql = IF((SELECT COUNT(*) FROM information_schema.COLUMNS WHERE TABLE_SCHEMA=DATABASE() AND TABLE_NAME='teams' AND COLUMN_NAME='id')>0,
  'ALTER TABLE teams MODIFY COLUMN id BIGINT NOT NULL AUTO_INCREMENT COMMENT ''团队ID''', 'SELECT 1');
PREPARE st FROM @sql; EXECUTE st; DEALLOCATE PREPARE st;
SET @sql = IF((SELECT COUNT(*) FROM information_schema.COLUMNS WHERE TABLE_SCHEMA=DATABASE() AND TABLE_NAME='teams' AND COLUMN_NAME='name')>0,
  'ALTER TABLE teams MODIFY COLUMN name VARCHAR(64) NOT NULL COMMENT ''团队名称''', 'SELECT 1');
PREPARE st FROM @sql; EXECUTE st; DEALLOCATE PREPARE st;
SET @sql = IF((SELECT COUNT(*) FROM information_schema.COLUMNS WHERE TABLE_SCHEMA=DATABASE() AND TABLE_NAME='teams' AND COLUMN_NAME='owner_id')>0,
  'ALTER TABLE teams MODIFY COLUMN owner_id BIGINT NOT NULL COMMENT ''创建者用户ID''', 'SELECT 1');
PREPARE st FROM @sql; EXECUTE st; DEALLOCATE PREPARE st;
SET @sql = IF((SELECT COUNT(*) FROM information_schema.COLUMNS WHERE TABLE_SCHEMA=DATABASE() AND TABLE_NAME='teams' AND COLUMN_NAME='digest_time')>0,
  'ALTER TABLE teams MODIFY COLUMN digest_time VARCHAR(8) NOT NULL DEFAULT ''21:00'' COMMENT ''日报 AI 摘要自动生成时间 HH:MM''', 'SELECT 1');
PREPARE st FROM @sql; EXECUTE st; DEALLOCATE PREPARE st;
SET @sql = IF((SELECT COUNT(*) FROM information_schema.COLUMNS WHERE TABLE_SCHEMA=DATABASE() AND TABLE_NAME='teams' AND COLUMN_NAME='ai_banned')>0,
  'ALTER TABLE teams MODIFY COLUMN ai_banned TINYINT NOT NULL DEFAULT 0 COMMENT ''禁止团队使用 AI''', 'SELECT 1');
PREPARE st FROM @sql; EXECUTE st; DEALLOCATE PREPARE st;
SET @sql = IF((SELECT COUNT(*) FROM information_schema.COLUMNS WHERE TABLE_SCHEMA=DATABASE() AND TABLE_NAME='teams' AND COLUMN_NAME='created_at')>0,
  'ALTER TABLE teams MODIFY COLUMN created_at VARCHAR(32) NOT NULL COMMENT ''创建时间''', 'SELECT 1');
PREPARE st FROM @sql; EXECUTE st; DEALLOCATE PREPARE st;

-- -------------------- team_members --------------------
ALTER TABLE team_members COMMENT='团队成员';
SET @sql = IF((SELECT COUNT(*) FROM information_schema.COLUMNS WHERE TABLE_SCHEMA=DATABASE() AND TABLE_NAME='team_members' AND COLUMN_NAME='team_id')>0,
  'ALTER TABLE team_members MODIFY COLUMN team_id BIGINT NOT NULL COMMENT ''团队ID''', 'SELECT 1');
PREPARE st FROM @sql; EXECUTE st; DEALLOCATE PREPARE st;
SET @sql = IF((SELECT COUNT(*) FROM information_schema.COLUMNS WHERE TABLE_SCHEMA=DATABASE() AND TABLE_NAME='team_members' AND COLUMN_NAME='user_id')>0,
  'ALTER TABLE team_members MODIFY COLUMN user_id BIGINT NOT NULL COMMENT ''成员用户ID''', 'SELECT 1');
PREPARE st FROM @sql; EXECUTE st; DEALLOCATE PREPARE st;
SET @sql = IF((SELECT COUNT(*) FROM information_schema.COLUMNS WHERE TABLE_SCHEMA=DATABASE() AND TABLE_NAME='team_members' AND COLUMN_NAME='role')>0,
  'ALTER TABLE team_members MODIFY COLUMN role VARCHAR(16) NOT NULL DEFAULT ''member'' COMMENT ''角色：owner/admin/member''', 'SELECT 1');
PREPARE st FROM @sql; EXECUTE st; DEALLOCATE PREPARE st;
SET @sql = IF((SELECT COUNT(*) FROM information_schema.COLUMNS WHERE TABLE_SCHEMA=DATABASE() AND TABLE_NAME='team_members' AND COLUMN_NAME='joined_at')>0,
  'ALTER TABLE team_members MODIFY COLUMN joined_at VARCHAR(32) NOT NULL COMMENT ''加入时间''', 'SELECT 1');
PREPARE st FROM @sql; EXECUTE st; DEALLOCATE PREPARE st;

-- -------------------- team_tasks --------------------
ALTER TABLE team_tasks COMMENT='团队任务/工单';
SET @sql = IF((SELECT COUNT(*) FROM information_schema.COLUMNS WHERE TABLE_SCHEMA=DATABASE() AND TABLE_NAME='team_tasks' AND COLUMN_NAME='id')>0,
  'ALTER TABLE team_tasks MODIFY COLUMN id BIGINT NOT NULL AUTO_INCREMENT COMMENT ''任务ID''', 'SELECT 1');
PREPARE st FROM @sql; EXECUTE st; DEALLOCATE PREPARE st;
SET @sql = IF((SELECT COUNT(*) FROM information_schema.COLUMNS WHERE TABLE_SCHEMA=DATABASE() AND TABLE_NAME='team_tasks' AND COLUMN_NAME='team_id')>0,
  'ALTER TABLE team_tasks MODIFY COLUMN team_id BIGINT NOT NULL COMMENT ''所属团队ID''', 'SELECT 1');
PREPARE st FROM @sql; EXECUTE st; DEALLOCATE PREPARE st;
SET @sql = IF((SELECT COUNT(*) FROM information_schema.COLUMNS WHERE TABLE_SCHEMA=DATABASE() AND TABLE_NAME='team_tasks' AND COLUMN_NAME='kind')>0,
  'ALTER TABLE team_tasks MODIFY COLUMN kind VARCHAR(16) NOT NULL DEFAULT ''todo'' COMMENT ''种类：todo/ticket''', 'SELECT 1');
PREPARE st FROM @sql; EXECUTE st; DEALLOCATE PREPARE st;
SET @sql = IF((SELECT COUNT(*) FROM information_schema.COLUMNS WHERE TABLE_SCHEMA=DATABASE() AND TABLE_NAME='team_tasks' AND COLUMN_NAME='title')>0,
  'ALTER TABLE team_tasks MODIFY COLUMN title TEXT NOT NULL COMMENT ''标题''', 'SELECT 1');
PREPARE st FROM @sql; EXECUTE st; DEALLOCATE PREPARE st;
SET @sql = IF((SELECT COUNT(*) FROM information_schema.COLUMNS WHERE TABLE_SCHEMA=DATABASE() AND TABLE_NAME='team_tasks' AND COLUMN_NAME='description')>0,
  'ALTER TABLE team_tasks MODIFY COLUMN description MEDIUMTEXT NOT NULL COMMENT ''描述''', 'SELECT 1');
PREPARE st FROM @sql; EXECUTE st; DEALLOCATE PREPARE st;
SET @sql = IF((SELECT COUNT(*) FROM information_schema.COLUMNS WHERE TABLE_SCHEMA=DATABASE() AND TABLE_NAME='team_tasks' AND COLUMN_NAME='priority')>0,
  'ALTER TABLE team_tasks MODIFY COLUMN priority VARCHAR(16) NOT NULL DEFAULT ''medium'' COMMENT ''优先级''', 'SELECT 1');
PREPARE st FROM @sql; EXECUTE st; DEALLOCATE PREPARE st;
SET @sql = IF((SELECT COUNT(*) FROM information_schema.COLUMNS WHERE TABLE_SCHEMA=DATABASE() AND TABLE_NAME='team_tasks' AND COLUMN_NAME='status')>0,
  'ALTER TABLE team_tasks MODIFY COLUMN status VARCHAR(16) NOT NULL DEFAULT ''open'' COMMENT ''状态''', 'SELECT 1');
PREPARE st FROM @sql; EXECUTE st; DEALLOCATE PREPARE st;
SET @sql = IF((SELECT COUNT(*) FROM information_schema.COLUMNS WHERE TABLE_SCHEMA=DATABASE() AND TABLE_NAME='team_tasks' AND COLUMN_NAME='creator_id')>0,
  'ALTER TABLE team_tasks MODIFY COLUMN creator_id BIGINT NOT NULL COMMENT ''创建者用户ID''', 'SELECT 1');
PREPARE st FROM @sql; EXECUTE st; DEALLOCATE PREPARE st;
SET @sql = IF((SELECT COUNT(*) FROM information_schema.COLUMNS WHERE TABLE_SCHEMA=DATABASE() AND TABLE_NAME='team_tasks' AND COLUMN_NAME='assignee_id')>0,
  'ALTER TABLE team_tasks MODIFY COLUMN assignee_id BIGINT NOT NULL DEFAULT 0 COMMENT ''指派人用户ID，0=未指派''', 'SELECT 1');
PREPARE st FROM @sql; EXECUTE st; DEALLOCATE PREPARE st;
SET @sql = IF((SELECT COUNT(*) FROM information_schema.COLUMNS WHERE TABLE_SCHEMA=DATABASE() AND TABLE_NAME='team_tasks' AND COLUMN_NAME='start_at')>0,
  'ALTER TABLE team_tasks MODIFY COLUMN start_at VARCHAR(32) NOT NULL DEFAULT '''' COMMENT ''开始时间''', 'SELECT 1');
PREPARE st FROM @sql; EXECUTE st; DEALLOCATE PREPARE st;
SET @sql = IF((SELECT COUNT(*) FROM information_schema.COLUMNS WHERE TABLE_SCHEMA=DATABASE() AND TABLE_NAME='team_tasks' AND COLUMN_NAME='due_at')>0,
  'ALTER TABLE team_tasks MODIFY COLUMN due_at VARCHAR(32) NOT NULL DEFAULT '''' COMMENT ''截止时间''', 'SELECT 1');
PREPARE st FROM @sql; EXECUTE st; DEALLOCATE PREPARE st;
SET @sql = IF((SELECT COUNT(*) FROM information_schema.COLUMNS WHERE TABLE_SCHEMA=DATABASE() AND TABLE_NAME='team_tasks' AND COLUMN_NAME='urged_at')>0,
  'ALTER TABLE team_tasks MODIFY COLUMN urged_at VARCHAR(32) NOT NULL DEFAULT '''' COMMENT ''最近催办时间''', 'SELECT 1');
PREPARE st FROM @sql; EXECUTE st; DEALLOCATE PREPARE st;
SET @sql = IF((SELECT COUNT(*) FROM information_schema.COLUMNS WHERE TABLE_SCHEMA=DATABASE() AND TABLE_NAME='team_tasks' AND COLUMN_NAME='history')>0,
  'ALTER TABLE team_tasks MODIFY COLUMN history MEDIUMTEXT NOT NULL COMMENT ''生命周期轨迹 JSON''', 'SELECT 1');
PREPARE st FROM @sql; EXECUTE st; DEALLOCATE PREPARE st;
SET @sql = IF((SELECT COUNT(*) FROM information_schema.COLUMNS WHERE TABLE_SCHEMA=DATABASE() AND TABLE_NAME='team_tasks' AND COLUMN_NAME='updated_at')>0,
  'ALTER TABLE team_tasks MODIFY COLUMN updated_at VARCHAR(32) NOT NULL COMMENT ''最后更新时间''', 'SELECT 1');
PREPARE st FROM @sql; EXECUTE st; DEALLOCATE PREPARE st;
SET @sql = IF((SELECT COUNT(*) FROM information_schema.COLUMNS WHERE TABLE_SCHEMA=DATABASE() AND TABLE_NAME='team_tasks' AND COLUMN_NAME='deleted')>0,
  'ALTER TABLE team_tasks MODIFY COLUMN deleted TINYINT NOT NULL DEFAULT 0 COMMENT ''软删除标记''', 'SELECT 1');
PREPARE st FROM @sql; EXECUTE st; DEALLOCATE PREPARE st;

-- -------------------- team_reports --------------------
ALTER TABLE team_reports COMMENT='团队日报';
SET @sql = IF((SELECT COUNT(*) FROM information_schema.COLUMNS WHERE TABLE_SCHEMA=DATABASE() AND TABLE_NAME='team_reports' AND COLUMN_NAME='team_id')>0,
  'ALTER TABLE team_reports MODIFY COLUMN team_id BIGINT NOT NULL COMMENT ''团队ID''', 'SELECT 1');
PREPARE st FROM @sql; EXECUTE st; DEALLOCATE PREPARE st;
SET @sql = IF((SELECT COUNT(*) FROM information_schema.COLUMNS WHERE TABLE_SCHEMA=DATABASE() AND TABLE_NAME='team_reports' AND COLUMN_NAME='user_id')>0,
  'ALTER TABLE team_reports MODIFY COLUMN user_id BIGINT NOT NULL COMMENT ''提交人用户ID''', 'SELECT 1');
PREPARE st FROM @sql; EXECUTE st; DEALLOCATE PREPARE st;
SET @sql = IF((SELECT COUNT(*) FROM information_schema.COLUMNS WHERE TABLE_SCHEMA=DATABASE() AND TABLE_NAME='team_reports' AND COLUMN_NAME='date')>0,
  'ALTER TABLE team_reports MODIFY COLUMN date CHAR(10) NOT NULL COMMENT ''日报日期 YYYY-MM-DD''', 'SELECT 1');
PREPARE st FROM @sql; EXECUTE st; DEALLOCATE PREPARE st;
SET @sql = IF((SELECT COUNT(*) FROM information_schema.COLUMNS WHERE TABLE_SCHEMA=DATABASE() AND TABLE_NAME='team_reports' AND COLUMN_NAME='content')>0,
  'ALTER TABLE team_reports MODIFY COLUMN content MEDIUMTEXT NOT NULL COMMENT ''日报正文（Markdown）''', 'SELECT 1');
PREPARE st FROM @sql; EXECUTE st; DEALLOCATE PREPARE st;
SET @sql = IF((SELECT COUNT(*) FROM information_schema.COLUMNS WHERE TABLE_SCHEMA=DATABASE() AND TABLE_NAME='team_reports' AND COLUMN_NAME='submitted_at')>0,
  'ALTER TABLE team_reports MODIFY COLUMN submitted_at VARCHAR(32) NOT NULL COMMENT ''提交/更新时间''', 'SELECT 1');
PREPARE st FROM @sql; EXECUTE st; DEALLOCATE PREPARE st;

-- -------------------- team_digests --------------------
ALTER TABLE team_digests COMMENT='团队日报 AI 摘要';
SET @sql = IF((SELECT COUNT(*) FROM information_schema.COLUMNS WHERE TABLE_SCHEMA=DATABASE() AND TABLE_NAME='team_digests' AND COLUMN_NAME='team_id')>0,
  'ALTER TABLE team_digests MODIFY COLUMN team_id BIGINT NOT NULL COMMENT ''团队ID''', 'SELECT 1');
PREPARE st FROM @sql; EXECUTE st; DEALLOCATE PREPARE st;
SET @sql = IF((SELECT COUNT(*) FROM information_schema.COLUMNS WHERE TABLE_SCHEMA=DATABASE() AND TABLE_NAME='team_digests' AND COLUMN_NAME='date')>0,
  'ALTER TABLE team_digests MODIFY COLUMN date CHAR(10) NOT NULL COMMENT ''摘要对应日期 YYYY-MM-DD''', 'SELECT 1');
PREPARE st FROM @sql; EXECUTE st; DEALLOCATE PREPARE st;
SET @sql = IF((SELECT COUNT(*) FROM information_schema.COLUMNS WHERE TABLE_SCHEMA=DATABASE() AND TABLE_NAME='team_digests' AND COLUMN_NAME='content')>0,
  'ALTER TABLE team_digests MODIFY COLUMN content MEDIUMTEXT NOT NULL COMMENT ''AI 摘要正文（Markdown）''', 'SELECT 1');
PREPARE st FROM @sql; EXECUTE st; DEALLOCATE PREPARE st;
SET @sql = IF((SELECT COUNT(*) FROM information_schema.COLUMNS WHERE TABLE_SCHEMA=DATABASE() AND TABLE_NAME='team_digests' AND COLUMN_NAME='provider')>0,
  'ALTER TABLE team_digests MODIFY COLUMN provider VARCHAR(32) NOT NULL DEFAULT '''' COMMENT ''生成所用 AI 提供商''', 'SELECT 1');
PREPARE st FROM @sql; EXECUTE st; DEALLOCATE PREPARE st;
SET @sql = IF((SELECT COUNT(*) FROM information_schema.COLUMNS WHERE TABLE_SCHEMA=DATABASE() AND TABLE_NAME='team_digests' AND COLUMN_NAME='generated_at')>0,
  'ALTER TABLE team_digests MODIFY COLUMN generated_at VARCHAR(32) NOT NULL COMMENT ''生成时间''', 'SELECT 1');
PREPARE st FROM @sql; EXECUTE st; DEALLOCATE PREPARE st;

-- -------------------- team_notices --------------------
ALTER TABLE team_notices COMMENT='团队通知';
SET @sql = IF((SELECT COUNT(*) FROM information_schema.COLUMNS WHERE TABLE_SCHEMA=DATABASE() AND TABLE_NAME='team_notices' AND COLUMN_NAME='id')>0,
  'ALTER TABLE team_notices MODIFY COLUMN id BIGINT NOT NULL AUTO_INCREMENT COMMENT ''通知ID''', 'SELECT 1');
PREPARE st FROM @sql; EXECUTE st; DEALLOCATE PREPARE st;
SET @sql = IF((SELECT COUNT(*) FROM information_schema.COLUMNS WHERE TABLE_SCHEMA=DATABASE() AND TABLE_NAME='team_notices' AND COLUMN_NAME='team_id')>0,
  'ALTER TABLE team_notices MODIFY COLUMN team_id BIGINT NOT NULL COMMENT ''团队ID''', 'SELECT 1');
PREPARE st FROM @sql; EXECUTE st; DEALLOCATE PREPARE st;
SET @sql = IF((SELECT COUNT(*) FROM information_schema.COLUMNS WHERE TABLE_SCHEMA=DATABASE() AND TABLE_NAME='team_notices' AND COLUMN_NAME='to_user')>0,
  'ALTER TABLE team_notices MODIFY COLUMN to_user BIGINT NOT NULL COMMENT ''接收用户ID''', 'SELECT 1');
PREPARE st FROM @sql; EXECUTE st; DEALLOCATE PREPARE st;
SET @sql = IF((SELECT COUNT(*) FROM information_schema.COLUMNS WHERE TABLE_SCHEMA=DATABASE() AND TABLE_NAME='team_notices' AND COLUMN_NAME='from_user')>0,
  'ALTER TABLE team_notices MODIFY COLUMN from_user BIGINT NOT NULL COMMENT ''发送用户ID''', 'SELECT 1');
PREPARE st FROM @sql; EXECUTE st; DEALLOCATE PREPARE st;
SET @sql = IF((SELECT COUNT(*) FROM information_schema.COLUMNS WHERE TABLE_SCHEMA=DATABASE() AND TABLE_NAME='team_notices' AND COLUMN_NAME='kind')>0,
  'ALTER TABLE team_notices MODIFY COLUMN kind VARCHAR(16) NOT NULL COMMENT ''通知类型''', 'SELECT 1');
PREPARE st FROM @sql; EXECUTE st; DEALLOCATE PREPARE st;
SET @sql = IF((SELECT COUNT(*) FROM information_schema.COLUMNS WHERE TABLE_SCHEMA=DATABASE() AND TABLE_NAME='team_notices' AND COLUMN_NAME='ref_id')>0,
  'ALTER TABLE team_notices MODIFY COLUMN ref_id VARCHAR(64) NOT NULL DEFAULT '''' COMMENT ''关联对象ID''', 'SELECT 1');
PREPARE st FROM @sql; EXECUTE st; DEALLOCATE PREPARE st;
SET @sql = IF((SELECT COUNT(*) FROM information_schema.COLUMNS WHERE TABLE_SCHEMA=DATABASE() AND TABLE_NAME='team_notices' AND COLUMN_NAME='content')>0,
  'ALTER TABLE team_notices MODIFY COLUMN content TEXT NOT NULL COMMENT ''通知正文''', 'SELECT 1');
PREPARE st FROM @sql; EXECUTE st; DEALLOCATE PREPARE st;
SET @sql = IF((SELECT COUNT(*) FROM information_schema.COLUMNS WHERE TABLE_SCHEMA=DATABASE() AND TABLE_NAME='team_notices' AND COLUMN_NAME='created_at')>0,
  'ALTER TABLE team_notices MODIFY COLUMN created_at VARCHAR(32) NOT NULL COMMENT ''创建时间''', 'SELECT 1');
PREPARE st FROM @sql; EXECUTE st; DEALLOCATE PREPARE st;

-- -------------------- pms_files（原先 CREATE 多为行尾注释，列 COMMENT 常缺失） --------------------
ALTER TABLE pms_files COMMENT='已上传文件元数据';
SET @sql = IF((SELECT COUNT(*) FROM information_schema.COLUMNS WHERE TABLE_SCHEMA=DATABASE() AND TABLE_NAME='pms_files' AND COLUMN_NAME='id')>0,
  'ALTER TABLE pms_files MODIFY COLUMN id BIGINT NOT NULL AUTO_INCREMENT COMMENT ''文件ID''', 'SELECT 1');
PREPARE st FROM @sql; EXECUTE st; DEALLOCATE PREPARE st;
SET @sql = IF((SELECT COUNT(*) FROM information_schema.COLUMNS WHERE TABLE_SCHEMA=DATABASE() AND TABLE_NAME='pms_files' AND COLUMN_NAME='name')>0,
  'ALTER TABLE pms_files MODIFY COLUMN name VARCHAR(191) NOT NULL COMMENT ''存储相对路径，如 2026/08/13/<hex>.jpg''', 'SELECT 1');
PREPARE st FROM @sql; EXECUTE st; DEALLOCATE PREPARE st;
SET @sql = IF((SELECT COUNT(*) FROM information_schema.COLUMNS WHERE TABLE_SCHEMA=DATABASE() AND TABLE_NAME='pms_files' AND COLUMN_NAME='original')>0,
  'ALTER TABLE pms_files MODIFY COLUMN original VARCHAR(255) NOT NULL DEFAULT '''' COMMENT ''原始文件名（仅备查）''', 'SELECT 1');
PREPARE st FROM @sql; EXECUTE st; DEALLOCATE PREPARE st;
SET @sql = IF((SELECT COUNT(*) FROM information_schema.COLUMNS WHERE TABLE_SCHEMA=DATABASE() AND TABLE_NAME='pms_files' AND COLUMN_NAME='mime')>0,
  'ALTER TABLE pms_files MODIFY COLUMN mime VARCHAR(64) NOT NULL DEFAULT '''' COMMENT ''MIME 类型''', 'SELECT 1');
PREPARE st FROM @sql; EXECUTE st; DEALLOCATE PREPARE st;
SET @sql = IF((SELECT COUNT(*) FROM information_schema.COLUMNS WHERE TABLE_SCHEMA=DATABASE() AND TABLE_NAME='pms_files' AND COLUMN_NAME='size')>0,
  'ALTER TABLE pms_files MODIFY COLUMN size BIGINT NOT NULL DEFAULT 0 COMMENT ''文件字节大小''', 'SELECT 1');
PREPARE st FROM @sql; EXECUTE st; DEALLOCATE PREPARE st;
SET @sql = IF((SELECT COUNT(*) FROM information_schema.COLUMNS WHERE TABLE_SCHEMA=DATABASE() AND TABLE_NAME='pms_files' AND COLUMN_NAME='sha256')>0,
  'ALTER TABLE pms_files MODIFY COLUMN sha256 CHAR(64) NOT NULL DEFAULT '''' COMMENT ''内容摘要，同归属秒传去重''', 'SELECT 1');
PREPARE st FROM @sql; EXECUTE st; DEALLOCATE PREPARE st;
SET @sql = IF((SELECT COUNT(*) FROM information_schema.COLUMNS WHERE TABLE_SCHEMA=DATABASE() AND TABLE_NAME='pms_files' AND COLUMN_NAME='user_id')>0,
  'ALTER TABLE pms_files MODIFY COLUMN user_id BIGINT NOT NULL DEFAULT 0 COMMENT ''上传者用户ID，0=未知''', 'SELECT 1');
PREPARE st FROM @sql; EXECUTE st; DEALLOCATE PREPARE st;
SET @sql = IF((SELECT COUNT(*) FROM information_schema.COLUMNS WHERE TABLE_SCHEMA=DATABASE() AND TABLE_NAME='pms_files' AND COLUMN_NAME='team_id')>0,
  'ALTER TABLE pms_files MODIFY COLUMN team_id BIGINT NOT NULL DEFAULT 0 COMMENT ''上传时所在团队ID，0=个人''', 'SELECT 1');
PREPARE st FROM @sql; EXECUTE st; DEALLOCATE PREPARE st;
SET @sql = IF((SELECT COUNT(*) FROM information_schema.COLUMNS WHERE TABLE_SCHEMA=DATABASE() AND TABLE_NAME='pms_files' AND COLUMN_NAME='kind')>0,
  'ALTER TABLE pms_files MODIFY COLUMN kind VARCHAR(16) NOT NULL DEFAULT '''' COMMENT ''用途：avatar | content''', 'SELECT 1');
PREPARE st FROM @sql; EXECUTE st; DEALLOCATE PREPARE st;
SET @sql = IF((SELECT COUNT(*) FROM information_schema.COLUMNS WHERE TABLE_SCHEMA=DATABASE() AND TABLE_NAME='pms_files' AND COLUMN_NAME='created_at')>0,
  'ALTER TABLE pms_files MODIFY COLUMN created_at VARCHAR(32) NOT NULL DEFAULT '''' COMMENT ''上传时间（RFC3339）''', 'SELECT 1');
PREPARE st FROM @sql; EXECUTE st; DEALLOCATE PREPARE st;

-- -------------------- user_daily_active --------------------
SET @sql = IF((SELECT COUNT(*) FROM information_schema.TABLES WHERE TABLE_SCHEMA=DATABASE() AND TABLE_NAME='user_daily_active')>0,
  'ALTER TABLE user_daily_active COMMENT=''用户日活''', 'SELECT 1');
PREPARE st FROM @sql; EXECUTE st; DEALLOCATE PREPARE st;
SET @sql = IF((SELECT COUNT(*) FROM information_schema.COLUMNS WHERE TABLE_SCHEMA=DATABASE() AND TABLE_NAME='user_daily_active' AND COLUMN_NAME='user_id')>0,
  'ALTER TABLE user_daily_active MODIFY COLUMN user_id BIGINT NOT NULL COMMENT ''用户ID''', 'SELECT 1');
PREPARE st FROM @sql; EXECUTE st; DEALLOCATE PREPARE st;
SET @sql = IF((SELECT COUNT(*) FROM information_schema.COLUMNS WHERE TABLE_SCHEMA=DATABASE() AND TABLE_NAME='user_daily_active' AND COLUMN_NAME='active_date')>0,
  'ALTER TABLE user_daily_active MODIFY COLUMN active_date CHAR(10) NOT NULL COMMENT ''活跃日期 YYYY-MM-DD''', 'SELECT 1');
PREPARE st FROM @sql; EXECUTE st; DEALLOCATE PREPARE st;
SET @sql = IF((SELECT COUNT(*) FROM information_schema.COLUMNS WHERE TABLE_SCHEMA=DATABASE() AND TABLE_NAME='user_daily_active' AND COLUMN_NAME='last_ip')>0,
  'ALTER TABLE user_daily_active MODIFY COLUMN last_ip VARCHAR(64) NOT NULL DEFAULT '''' COMMENT ''当日最近 IP''', 'SELECT 1');
PREPARE st FROM @sql; EXECUTE st; DEALLOCATE PREPARE st;
SET @sql = IF((SELECT COUNT(*) FROM information_schema.COLUMNS WHERE TABLE_SCHEMA=DATABASE() AND TABLE_NAME='user_daily_active' AND COLUMN_NAME='last_seen_at')>0,
  'ALTER TABLE user_daily_active MODIFY COLUMN last_seen_at VARCHAR(32) NOT NULL DEFAULT '''' COMMENT ''当日最近活跃时间''', 'SELECT 1');
PREPARE st FROM @sql; EXECUTE st; DEALLOCATE PREPARE st;

-- -------------------- ai_usage_daily --------------------
SET @sql = IF((SELECT COUNT(*) FROM information_schema.TABLES WHERE TABLE_SCHEMA=DATABASE() AND TABLE_NAME='ai_usage_daily')>0,
  'ALTER TABLE ai_usage_daily COMMENT=''AI Token 日汇总''', 'SELECT 1');
PREPARE st FROM @sql; EXECUTE st; DEALLOCATE PREPARE st;
SET @sql = IF((SELECT COUNT(*) FROM information_schema.COLUMNS WHERE TABLE_SCHEMA=DATABASE() AND TABLE_NAME='ai_usage_daily' AND COLUMN_NAME='user_id')>0,
  'ALTER TABLE ai_usage_daily MODIFY COLUMN user_id BIGINT NOT NULL COMMENT ''用户ID''', 'SELECT 1');
PREPARE st FROM @sql; EXECUTE st; DEALLOCATE PREPARE st;
SET @sql = IF((SELECT COUNT(*) FROM information_schema.COLUMNS WHERE TABLE_SCHEMA=DATABASE() AND TABLE_NAME='ai_usage_daily' AND COLUMN_NAME='team_id')>0,
  'ALTER TABLE ai_usage_daily MODIFY COLUMN team_id BIGINT NOT NULL DEFAULT 0 COMMENT ''团队ID，0=个人''', 'SELECT 1');
PREPARE st FROM @sql; EXECUTE st; DEALLOCATE PREPARE st;
SET @sql = IF((SELECT COUNT(*) FROM information_schema.COLUMNS WHERE TABLE_SCHEMA=DATABASE() AND TABLE_NAME='ai_usage_daily' AND COLUMN_NAME='usage_date')>0,
  'ALTER TABLE ai_usage_daily MODIFY COLUMN usage_date CHAR(10) NOT NULL COMMENT ''用量日期 YYYY-MM-DD''', 'SELECT 1');
PREPARE st FROM @sql; EXECUTE st; DEALLOCATE PREPARE st;
SET @sql = IF((SELECT COUNT(*) FROM information_schema.COLUMNS WHERE TABLE_SCHEMA=DATABASE() AND TABLE_NAME='ai_usage_daily' AND COLUMN_NAME='provider')>0,
  'ALTER TABLE ai_usage_daily MODIFY COLUMN provider VARCHAR(32) NOT NULL DEFAULT '''' COMMENT ''AI 提供商''', 'SELECT 1');
PREPARE st FROM @sql; EXECUTE st; DEALLOCATE PREPARE st;
SET @sql = IF((SELECT COUNT(*) FROM information_schema.COLUMNS WHERE TABLE_SCHEMA=DATABASE() AND TABLE_NAME='ai_usage_daily' AND COLUMN_NAME='prompt_tokens')>0,
  'ALTER TABLE ai_usage_daily MODIFY COLUMN prompt_tokens BIGINT NOT NULL DEFAULT 0 COMMENT ''提示 token''', 'SELECT 1');
PREPARE st FROM @sql; EXECUTE st; DEALLOCATE PREPARE st;
SET @sql = IF((SELECT COUNT(*) FROM information_schema.COLUMNS WHERE TABLE_SCHEMA=DATABASE() AND TABLE_NAME='ai_usage_daily' AND COLUMN_NAME='completion_tokens')>0,
  'ALTER TABLE ai_usage_daily MODIFY COLUMN completion_tokens BIGINT NOT NULL DEFAULT 0 COMMENT ''补全 token''', 'SELECT 1');
PREPARE st FROM @sql; EXECUTE st; DEALLOCATE PREPARE st;
SET @sql = IF((SELECT COUNT(*) FROM information_schema.COLUMNS WHERE TABLE_SCHEMA=DATABASE() AND TABLE_NAME='ai_usage_daily' AND COLUMN_NAME='calls')>0,
  'ALTER TABLE ai_usage_daily MODIFY COLUMN calls INT NOT NULL DEFAULT 0 COMMENT ''调用次数''', 'SELECT 1');
PREPARE st FROM @sql; EXECUTE st; DEALLOCATE PREPARE st;
SET @sql = IF((SELECT COUNT(*) FROM information_schema.COLUMNS WHERE TABLE_SCHEMA=DATABASE() AND TABLE_NAME='ai_usage_daily' AND COLUMN_NAME='estimated')>0,
  'ALTER TABLE ai_usage_daily MODIFY COLUMN estimated TINYINT NOT NULL DEFAULT 0 COMMENT ''是否含估算数据''', 'SELECT 1');
PREPARE st FROM @sql; EXECUTE st; DEALLOCATE PREPARE st;

-- -------------------- app_releases --------------------
SET @sql = IF((SELECT COUNT(*) FROM information_schema.TABLES WHERE TABLE_SCHEMA=DATABASE() AND TABLE_NAME='app_releases')>0,
  'ALTER TABLE app_releases COMMENT=''客户端发版''', 'SELECT 1');
PREPARE st FROM @sql; EXECUTE st; DEALLOCATE PREPARE st;
SET @sql = IF((SELECT COUNT(*) FROM information_schema.COLUMNS WHERE TABLE_SCHEMA=DATABASE() AND TABLE_NAME='app_releases' AND COLUMN_NAME='id')>0,
  'ALTER TABLE app_releases MODIFY COLUMN id BIGINT NOT NULL AUTO_INCREMENT COMMENT ''发版ID''', 'SELECT 1');
PREPARE st FROM @sql; EXECUTE st; DEALLOCATE PREPARE st;
SET @sql = IF((SELECT COUNT(*) FROM information_schema.COLUMNS WHERE TABLE_SCHEMA=DATABASE() AND TABLE_NAME='app_releases' AND COLUMN_NAME='version')>0,
  'ALTER TABLE app_releases MODIFY COLUMN version VARCHAR(32) NOT NULL COMMENT ''版本号 semver''', 'SELECT 1');
PREPARE st FROM @sql; EXECUTE st; DEALLOCATE PREPARE st;
SET @sql = IF((SELECT COUNT(*) FROM information_schema.COLUMNS WHERE TABLE_SCHEMA=DATABASE() AND TABLE_NAME='app_releases' AND COLUMN_NAME='channel')>0,
  'ALTER TABLE app_releases MODIFY COLUMN channel VARCHAR(16) NOT NULL DEFAULT ''stable'' COMMENT ''渠道''', 'SELECT 1');
PREPARE st FROM @sql; EXECUTE st; DEALLOCATE PREPARE st;
SET @sql = IF((SELECT COUNT(*) FROM information_schema.COLUMNS WHERE TABLE_SCHEMA=DATABASE() AND TABLE_NAME='app_releases' AND COLUMN_NAME='filename')>0,
  'ALTER TABLE app_releases MODIFY COLUMN filename VARCHAR(255) NOT NULL COMMENT ''存储相对路径''', 'SELECT 1');
PREPARE st FROM @sql; EXECUTE st; DEALLOCATE PREPARE st;
SET @sql = IF((SELECT COUNT(*) FROM information_schema.COLUMNS WHERE TABLE_SCHEMA=DATABASE() AND TABLE_NAME='app_releases' AND COLUMN_NAME='sha256')>0,
  'ALTER TABLE app_releases MODIFY COLUMN sha256 CHAR(64) NOT NULL DEFAULT '''' COMMENT ''文件 SHA256''', 'SELECT 1');
PREPARE st FROM @sql; EXECUTE st; DEALLOCATE PREPARE st;
SET @sql = IF((SELECT COUNT(*) FROM information_schema.COLUMNS WHERE TABLE_SCHEMA=DATABASE() AND TABLE_NAME='app_releases' AND COLUMN_NAME='size_bytes')>0,
  'ALTER TABLE app_releases MODIFY COLUMN size_bytes BIGINT NOT NULL DEFAULT 0 COMMENT ''字节大小''', 'SELECT 1');
PREPARE st FROM @sql; EXECUTE st; DEALLOCATE PREPARE st;
SET @sql = IF((SELECT COUNT(*) FROM information_schema.COLUMNS WHERE TABLE_SCHEMA=DATABASE() AND TABLE_NAME='app_releases' AND COLUMN_NAME='changelog')>0,
  'ALTER TABLE app_releases MODIFY COLUMN changelog MEDIUMTEXT NOT NULL COMMENT ''更新说明''', 'SELECT 1');
PREPARE st FROM @sql; EXECUTE st; DEALLOCATE PREPARE st;
SET @sql = IF((SELECT COUNT(*) FROM information_schema.COLUMNS WHERE TABLE_SCHEMA=DATABASE() AND TABLE_NAME='app_releases' AND COLUMN_NAME='created_at')>0,
  'ALTER TABLE app_releases MODIFY COLUMN created_at VARCHAR(32) NOT NULL COMMENT ''上传时间''', 'SELECT 1');
PREPARE st FROM @sql; EXECUTE st; DEALLOCATE PREPARE st;
SET @sql = IF((SELECT COUNT(*) FROM information_schema.COLUMNS WHERE TABLE_SCHEMA=DATABASE() AND TABLE_NAME='app_releases' AND COLUMN_NAME='is_latest')>0,
  'ALTER TABLE app_releases MODIFY COLUMN is_latest TINYINT NOT NULL DEFAULT 0 COMMENT ''是否当前最新''', 'SELECT 1');
PREPARE st FROM @sql; EXECUTE st; DEALLOCATE PREPARE st;

-- -------------------- admin_stepup --------------------
SET @sql = IF((SELECT COUNT(*) FROM information_schema.TABLES WHERE TABLE_SCHEMA=DATABASE() AND TABLE_NAME='admin_stepup')>0,
  'ALTER TABLE admin_stepup COMMENT=''管理员敏感操作二次验证''', 'SELECT 1');
PREPARE st FROM @sql; EXECUTE st; DEALLOCATE PREPARE st;
SET @sql = IF((SELECT COUNT(*) FROM information_schema.COLUMNS WHERE TABLE_SCHEMA=DATABASE() AND TABLE_NAME='admin_stepup' AND COLUMN_NAME='user_id')>0,
  'ALTER TABLE admin_stepup MODIFY COLUMN user_id BIGINT NOT NULL COMMENT ''管理员用户ID''', 'SELECT 1');
PREPARE st FROM @sql; EXECUTE st; DEALLOCATE PREPARE st;
SET @sql = IF((SELECT COUNT(*) FROM information_schema.COLUMNS WHERE TABLE_SCHEMA=DATABASE() AND TABLE_NAME='admin_stepup' AND COLUMN_NAME='token_hash')>0,
  'ALTER TABLE admin_stepup MODIFY COLUMN token_hash CHAR(64) NOT NULL COMMENT ''stepup token SHA256''', 'SELECT 1');
PREPARE st FROM @sql; EXECUTE st; DEALLOCATE PREPARE st;
SET @sql = IF((SELECT COUNT(*) FROM information_schema.COLUMNS WHERE TABLE_SCHEMA=DATABASE() AND TABLE_NAME='admin_stepup' AND COLUMN_NAME='client_ip')>0,
  'ALTER TABLE admin_stepup MODIFY COLUMN client_ip VARCHAR(64) NOT NULL DEFAULT '''' COMMENT ''签发时 IP''', 'SELECT 1');
PREPARE st FROM @sql; EXECUTE st; DEALLOCATE PREPARE st;
SET @sql = IF((SELECT COUNT(*) FROM information_schema.COLUMNS WHERE TABLE_SCHEMA=DATABASE() AND TABLE_NAME='admin_stepup' AND COLUMN_NAME='expires_at')>0,
  'ALTER TABLE admin_stepup MODIFY COLUMN expires_at VARCHAR(32) NOT NULL COMMENT ''过期时间 RFC3339''', 'SELECT 1');
PREPARE st FROM @sql; EXECUTE st; DEALLOCATE PREPARE st;

-- 抽查：仍为空注释的列（执行完应为 0 行，或仅含未建表跳过的情况）
-- SELECT TABLE_NAME, COLUMN_NAME, COLUMN_COMMENT
-- FROM information_schema.COLUMNS
-- WHERE TABLE_SCHEMA = DATABASE()
--   AND TABLE_NAME IN (
--     'users','sync_todos','sync_tickets','sync_notes','sync_settings',
--     'user_profiles','user_avatar_history','teams','team_members','team_tasks',
--     'team_reports','team_digests','team_notices','pms_files',
--     'user_daily_active','ai_usage_daily','app_releases','admin_stepup'
--   )
--   AND (COLUMN_COMMENT IS NULL OR COLUMN_COMMENT = '')
-- ORDER BY TABLE_NAME, ORDINAL_POSITION;
