import { createTaskEvent } from '../../../repositories/task-event-repo.js' import { updateTask } from '../../../repositories/task-repo.js' import { TASK_STATUS, isKuaishouCloudRoleConfirmSettledStatus, } from '../../../domain/task-status.js' import { createHttpError } from '../../../utils/http.js' import { nowIso } from '../../../utils/time.js' import type { TaskRow } from '../../../types/repository/rows.js' import { assertBoundUidMatchesExpected, assertClaimExpectedUidReady, } from '../../claim/claim-identity.js' import { isKuaishouCloudTask, normalizeKuaishouCloudFlow, type JsonObject } from './domain.js' import { isKuaishouCloudMockContext, isKuaishouCloudMockTask } from './mock-helpers.js' import { refreshKuaishouCloudTaskRoleInfo } from './refresh-role-info.js' import { normalizeActor, parseTaskContext } from './task-context.js' export type ConfirmKuaishouCloudRoleResult = { task: TaskRow alreadySettled: boolean } /** * lewan 确认角色用例:刷新角色 → UID 闸门 → ROLE_CONFIRMED。 * 一键兑换路径里 WAITING_BINDING 的自动晋升在 redeem 内完成,不必先调本函数。 */ export async function confirmKuaishouCloudTaskRole( task: TaskRow, options: JsonObject = {}, ): Promise { if (!isKuaishouCloudTask(task)) { throw createHttpError('当前任务不是 kuaishou-lewan 履约任务', { statusCode: 409, errorCode: 'kuaishou_cloud_task_invalid', }) } const now = String(options.now || '').trim() || nowIso() const source = String(options.source || 'system_confirm_role').trim() || 'system_confirm_role' const actor = normalizeActor(options.actor) const errorCodePrefix = String(options.errorCodePrefix || 'kuaishou_cloud_confirm').trim() || 'kuaishou_cloud_confirm' if (isKuaishouCloudRoleConfirmSettledStatus(task.task_status)) { return { task, alreadySettled: true } } const expectedUid = assertClaimExpectedUidReady(task) const mockMode = isKuaishouCloudMockTask(task) || isKuaishouCloudMockContext(parseTaskContext(task)) const refreshed = mockMode ? { task } : await refreshKuaishouCloudTaskRoleInfo(task, { source, actor, recordEvent: options.recordEvent === true, forceProbe: options.forceProbe !== false, }) const flow = normalizeKuaishouCloudFlow( parseTaskContext(refreshed.task).kuaishouCloudFulfillment, ) if (!flow.binding.vnPhone || !flow.binding.roleName || !flow.binding.roleId) { throw createHttpError('角色信息还未刷新到系统,请完成绑定后稍等片刻再试', { statusCode: 409, errorCode: `${errorCodePrefix}_role_not_ready`, }) } if (!mockMode) { assertBoundUidMatchesExpected(refreshed.task, flow, { errorCodePrefix, }) } const updatedTask = (await updateTask(task.id, { task_status: TASK_STATUS.ROLE_CONFIRMED, role_id: flow.binding.roleId, role_name: flow.binding.roleName, user_action_status: TASK_STATUS.ROLE_CONFIRMED, role_confirmed_at: now, last_error: '', updated_at: now, })) || refreshed.task || task await createTaskEvent( task.id, 'kuaishou_cloud_role_confirmed', { expectedUid, vnPhone: flow.binding.vnPhone, roleName: flow.binding.roleName, roleId: flow.binding.roleId, source, actor, }, now, ) return { task: updatedTask, alreadySettled: false } }