187 lines
7.9 KiB
XML
187 lines
7.9 KiB
XML
<?xml version="1.0" encoding="UTF-8" ?>
|
|
<!DOCTYPE mapper
|
|
PUBLIC "-//mybatis.org//DTD Mapper 3.0//EN"
|
|
"http://mybatis.org/dtd/mybatis-3-mapper.dtd">
|
|
<mapper namespace="com.bms.receivable.mapper.ArBillGenerateTaskMapper">
|
|
<!-- 生成任务表是异步任务的持久化队列;状态更新均带前置状态条件,保证多节点抢占幂等。 -->
|
|
<resultMap id="ArBillGenerateTaskResult" type="ArBillGenerateTask">
|
|
<id property="taskId" column="task_id"/>
|
|
<result property="taskNo" column="task_no"/>
|
|
<result property="arBillId" column="ar_bill_id"/>
|
|
<result property="selectionMode" column="selection_mode"/>
|
|
<result property="requestPayload" column="request_payload"/>
|
|
<result property="snapshotCreateTime" column="snapshot_create_time"/>
|
|
<result property="lastSourceBillId" column="last_source_bill_id"/>
|
|
<result property="totalCount" column="total_count"/>
|
|
<result property="processedCount" column="processed_count"/>
|
|
<result property="successCount" column="success_count"/>
|
|
<result property="totalAmount" column="total_amount"/>
|
|
<result property="status" column="status"/>
|
|
<result property="errorMessage" column="error_message"/>
|
|
<result property="requestToken" column="request_token"/>
|
|
<result property="createBy" column="create_by"/>
|
|
<result property="createUserId" column="create_user_id"/>
|
|
<result property="createTime" column="create_time"/>
|
|
<result property="startedAt" column="started_at"/>
|
|
<result property="heartbeatTime" column="heartbeat_time"/>
|
|
<result property="finishedAt" column="finished_at"/>
|
|
</resultMap>
|
|
|
|
<sql id="columns">
|
|
select task_id,
|
|
task_no,
|
|
ar_bill_id,
|
|
selection_mode,
|
|
request_payload,
|
|
snapshot_create_time,
|
|
last_source_bill_id,
|
|
total_count,
|
|
processed_count,
|
|
success_count,
|
|
total_amount,
|
|
status,
|
|
error_message,
|
|
request_token,
|
|
create_by,
|
|
create_user_id,
|
|
create_time,
|
|
started_at,
|
|
heartbeat_time,
|
|
finished_at
|
|
from ar_bill_generate_task
|
|
</sql>
|
|
|
|
<select id="selectById" parameterType="long" resultMap="ArBillGenerateTaskResult">
|
|
<include refid="columns"/>
|
|
where task_id = #{taskId}
|
|
</select>
|
|
|
|
<select id="selectByRequestToken" parameterType="string" resultMap="ArBillGenerateTaskResult">
|
|
<include refid="columns"/>
|
|
where request_token = #{requestToken}
|
|
</select>
|
|
|
|
<!-- 前端恢复页面时查询当前用户仍需展示的任务。 -->
|
|
<select id="selectActiveByCreateBy" resultMap="ArBillGenerateTaskResult">
|
|
<include refid="columns"/>
|
|
where create_by = #{createBy}
|
|
and status in ('WAITING', 'RUNNING', 'CANCEL_REQUESTED')
|
|
order by create_time desc, task_id desc
|
|
</select>
|
|
|
|
<select id="selectActiveByCreateByScoped" resultMap="ArBillGenerateTaskResult">
|
|
<include refid="columns"/>
|
|
where create_by = #{createBy}
|
|
and status in ('WAITING', 'RUNNING', 'CANCEL_REQUESTED')
|
|
AND EXISTS (SELECT 1 FROM ar_bill b WHERE b.ar_bill_id = ar_bill_generate_task.ar_bill_id
|
|
<include refid="com.bms.receivable.mapper.ArBillScopeMapper.billScope"/>)
|
|
order by create_time desc, task_id desc
|
|
</select>
|
|
|
|
<!-- 定时调度器按创建时间顺序取待处理任务。 -->
|
|
<select id="selectWaiting" resultMap="ArBillGenerateTaskResult">
|
|
<include refid="columns"/>
|
|
where status = 'WAITING'
|
|
order by create_time asc, task_id asc
|
|
limit #{limit}
|
|
</select>
|
|
|
|
<insert id="insert" parameterType="ArBillGenerateTask" useGeneratedKeys="true" keyProperty="taskId">
|
|
insert into ar_bill_generate_task (task_no, ar_bill_id, selection_mode, request_payload, snapshot_create_time,
|
|
last_source_bill_id, total_count, processed_count, success_count,
|
|
total_amount,
|
|
status, error_message, request_token, create_by, create_user_id, create_time, started_at,
|
|
heartbeat_time, finished_at)
|
|
values (#{taskNo}, #{arBillId}, #{selectionMode}, #{requestPayload}, #{snapshotCreateTime},
|
|
#{lastSourceBillId}, #{totalCount}, #{processedCount}, #{successCount}, #{totalAmount},
|
|
#{status}, #{errorMessage}, #{requestToken}, #{createBy}, #{createUserId}, sysdate(), #{startedAt},
|
|
#{heartbeatTime}, #{finishedAt})
|
|
</insert>
|
|
|
|
<!-- 条件更新抢占任务;返回 1 才表示当前节点真正拿到执行权。 -->
|
|
<update id="markRunning">
|
|
update ar_bill_generate_task
|
|
set status = 'RUNNING',
|
|
started_at = coalesce(started_at, #{startedAt}),
|
|
heartbeat_time = #{startedAt}
|
|
where task_id = #{taskId}
|
|
and status = 'WAITING'
|
|
</update>
|
|
|
|
<update id="updateTotalCount">
|
|
update ar_bill_generate_task
|
|
set total_count = #{totalCount},
|
|
heartbeat_time = sysdate()
|
|
where task_id = #{taskId}
|
|
and status = 'RUNNING'
|
|
</update>
|
|
|
|
<!-- 每批成功后写入游标、计数和心跳;游标用于故障恢复后继续扫描。 -->
|
|
<update id="updateProgress">
|
|
update ar_bill_generate_task
|
|
set last_source_bill_id = #{lastSourceBillId},
|
|
processed_count = #{processedCount},
|
|
success_count = #{successCount},
|
|
total_amount = #{totalAmount},
|
|
heartbeat_time = #{heartbeatTime}
|
|
where task_id = #{taskId}
|
|
and status = 'RUNNING'
|
|
</update>
|
|
|
|
<update id="markSuccess">
|
|
update ar_bill_generate_task
|
|
set status = 'SUCCESS',
|
|
finished_at = #{finishedAt},
|
|
heartbeat_time = #{finishedAt}
|
|
where task_id = #{taskId}
|
|
and status = 'RUNNING'
|
|
</update>
|
|
|
|
<update id="markFailed">
|
|
update ar_bill_generate_task
|
|
set status = 'FAILED',
|
|
error_message = #{errorMessage},
|
|
finished_at = #{finishedAt},
|
|
heartbeat_time = #{finishedAt}
|
|
where task_id = #{taskId}
|
|
and status in ('WAITING', 'RUNNING', 'CANCEL_REQUESTED')
|
|
</update>
|
|
|
|
<update id="markCancelRequested">
|
|
update ar_bill_generate_task
|
|
set status = 'CANCEL_REQUESTED',
|
|
heartbeat_time = sysdate()
|
|
where task_id = #{taskId}
|
|
and status in ('WAITING', 'RUNNING')
|
|
</update>
|
|
|
|
<update id="markCanceled">
|
|
update ar_bill_generate_task
|
|
set status = 'CANCELED',
|
|
error_message = '用户取消账单生成',
|
|
finished_at = #{finishedAt},
|
|
heartbeat_time = #{finishedAt}
|
|
where task_id = #{taskId}
|
|
and status in ('WAITING', 'RUNNING', 'CANCEL_REQUESTED')
|
|
</update>
|
|
|
|
<!-- 执行节点宕机时恢复无心跳的 RUNNING 任务,供调度器重新投递。 -->
|
|
<update id="resetExpiredRunning">
|
|
update ar_bill_generate_task
|
|
set status = 'WAITING',
|
|
error_message = '任务执行节点已重启,已自动恢复等待处理',
|
|
heartbeat_time = null
|
|
where status = 'RUNNING'
|
|
and heartbeat_time < #{expiredBefore}
|
|
</update>
|
|
|
|
<!-- 取消请求长时间未完成时由补偿任务取出并执行数据清理。 -->
|
|
<select id="selectCancelRequestedBefore" resultMap="ArBillGenerateTaskResult">
|
|
<include refid="columns"/>
|
|
where status = 'CANCEL_REQUESTED'
|
|
and coalesce(heartbeat_time, create_time) < #{expiredBefore}
|
|
order by create_time asc, task_id asc
|
|
limit #{limit}
|
|
</select>
|
|
</mapper>
|