64 lines
3.5 KiB
MySQL
64 lines
3.5 KiB
MySQL
|
|
-- Tenant/user hierarchy alignment. Additive and safe to run repeatedly.
|
||
|
|
-- New business flows use tenant_members, platform_role, tenant_id and
|
||
|
|
-- created_by. Legacy role/project fields remain for compatibility only.
|
||
|
|
|
||
|
|
ALTER TABLE users ADD COLUMN IF NOT EXISTS platform_role TEXT NOT NULL DEFAULT 'platform_user';
|
||
|
|
UPDATE users
|
||
|
|
SET platform_role = CASE
|
||
|
|
WHEN role = 'admin' OR COALESCE(protected, 0) = 1 THEN 'platform_admin'
|
||
|
|
ELSE 'platform_user'
|
||
|
|
END
|
||
|
|
WHERE platform_role IS NULL OR platform_role NOT IN ('platform_admin', 'platform_user');
|
||
|
|
CREATE INDEX IF NOT EXISTS idx_users_platform_role ON users(platform_role, status, deleted_at);
|
||
|
|
|
||
|
|
ALTER TABLE fine_tune_tasks ADD COLUMN IF NOT EXISTS tenant_id TEXT NOT NULL DEFAULT 'default';
|
||
|
|
ALTER TABLE fine_tune_tasks ADD COLUMN IF NOT EXISTS created_by TEXT;
|
||
|
|
ALTER TABLE fine_tune_tasks ADD COLUMN IF NOT EXISTS deleted_at TEXT;
|
||
|
|
ALTER TABLE fine_tune_tasks ADD COLUMN IF NOT EXISTS deleted_by TEXT;
|
||
|
|
UPDATE fine_tune_tasks
|
||
|
|
SET tenant_id = COALESCE(NULLIF(tenant_id, ''), payload::json->>'tenant_id', 'default'),
|
||
|
|
created_by = COALESCE(NULLIF(created_by, ''), payload::json->>'created_by')
|
||
|
|
WHERE tenant_id IS NULL OR tenant_id = '' OR created_by IS NULL OR created_by = '';
|
||
|
|
CREATE INDEX IF NOT EXISTS idx_fine_tune_tasks_tenant_active
|
||
|
|
ON fine_tune_tasks(tenant_id, status, deleted_at, create_time DESC);
|
||
|
|
CREATE INDEX IF NOT EXISTS idx_fine_tune_tasks_creator
|
||
|
|
ON fine_tune_tasks(created_by, deleted_at, create_time DESC);
|
||
|
|
|
||
|
|
INSERT INTO tenants (id, name, code, status, quota, create_time)
|
||
|
|
VALUES ('default', '默认租户', 'default', 'active', '{}', NOW()::text)
|
||
|
|
ON CONFLICT (id) DO UPDATE
|
||
|
|
SET status = CASE WHEN COALESCE(tenants.status, 'active') = 'deleted' THEN 'active' ELSE tenants.status END,
|
||
|
|
deleted_at = CASE WHEN COALESCE(tenants.status, 'active') = 'deleted' THEN NULL ELSE tenants.deleted_at END,
|
||
|
|
deleted_by = CASE WHEN COALESCE(tenants.status, 'active') = 'deleted' THEN NULL ELSE tenants.deleted_by END;
|
||
|
|
|
||
|
|
-- Make the tenant owner relationship explicit and repair older tenant rows.
|
||
|
|
INSERT INTO tenant_members (tenant_id, user_id, role, status, joined_at)
|
||
|
|
SELECT t.id, t.owner_user_id, 'owner', 'active', COALESCE(t.create_time, NOW()::text)
|
||
|
|
FROM tenants t
|
||
|
|
JOIN users u ON u.id = t.owner_user_id
|
||
|
|
WHERE t.owner_user_id IS NOT NULL
|
||
|
|
AND COALESCE(t.status, 'active') = 'active'
|
||
|
|
ON CONFLICT (tenant_id, user_id) DO UPDATE
|
||
|
|
SET role = 'owner', status = 'active';
|
||
|
|
|
||
|
|
-- Existing account creation used admin as a tenant owner. Platform role and
|
||
|
|
-- tenant role are separate, so keep only explicit tenant owners as owners.
|
||
|
|
UPDATE tenant_members tm
|
||
|
|
SET role = 'member'
|
||
|
|
FROM users u
|
||
|
|
WHERE tm.user_id = u.id
|
||
|
|
AND tm.role = 'owner'
|
||
|
|
AND (u.role <> 'admin' AND COALESCE(u.protected, 0) = 0)
|
||
|
|
AND NOT EXISTS (
|
||
|
|
SELECT 1 FROM tenants t
|
||
|
|
WHERE t.id = tm.tenant_id AND t.owner_user_id = tm.user_id
|
||
|
|
);
|
||
|
|
|
||
|
|
-- Project is no longer a business isolation boundary. Keep historical columns
|
||
|
|
-- readable, but make tenant-scoped queries the only supported new path.
|
||
|
|
CREATE INDEX IF NOT EXISTS idx_datasets_tenant_active ON datasets(tenant_id, deleted_at, create_time DESC);
|
||
|
|
CREATE INDEX IF NOT EXISTS idx_models_tenant_active ON models(tenant_id, deleted_at, create_time DESC);
|
||
|
|
CREATE INDEX IF NOT EXISTS idx_trained_models_tenant_active ON trained_models(tenant_id, deleted_at, create_time DESC);
|
||
|
|
CREATE INDEX IF NOT EXISTS idx_eval_tasks_tenant_active ON eval_tasks(tenant_id, deleted_at, create_time DESC);
|
||
|
|
CREATE INDEX IF NOT EXISTS idx_compare_tasks_tenant_active ON compare_tasks(tenant_id, deleted_at, create_time DESC);
|