批量推送代码

Co-Authored-By: Claude <noreply@anthropic.com>
This commit is contained in:
郭庆泰
2026-08-29 17:52:05 +08:00
co-authored by Claude
parent 36528b6e0c
commit e47f76478b
130 changed files with 3972 additions and 2546 deletions
@@ -15,6 +15,7 @@
<result property="titleCertUrl" column="title_cert_url" />
<result property="bankCard" column="bank_card" />
<result property="bankName" column="bank_name" />
<result property="bankBranch" column="bank_branch" />
<result property="bankRegion" column="bank_region" />
<result property="bankAddress" column="bank_address" />
<result property="idCardAttachments" column="id_card_attachments" />
@@ -27,7 +28,7 @@
<result property="updateTime" column="update_time" />
</resultMap>
<sql id="selectFields">
select expert_id, user_id, name, phone, region, id_card, work_unit, department, title, practice_cert_url, title_cert_url, bank_card, bank_name, bank_region, bank_address, id_card_attachments, audit_status, audit_by, audit_time, status, create_by, create_time, update_by, update_time
select expert_id, user_id, name, phone, region, id_card, work_unit, department, title, practice_cert_url, title_cert_url, bank_card, bank_name, bank_branch, bank_region, bank_address, id_card_attachments, audit_status, audit_by, audit_time, status, create_by, create_time, update_by, update_time
from biz_expert
</sql>
<select id="selectByUserId" resultMap="BizExpertResult" parameterType="Long">
@@ -68,6 +69,7 @@
<if test="titleCertUrl != null">title_cert_url,</if>
<if test="bankCard != null">bank_card,</if>
<if test="bankName != null">bank_name,</if>
<if test="bankBranch != null">bank_branch,</if>
<if test="bankRegion != null">bank_region,</if>
<if test="bankAddress != null">bank_address,</if>
<if test="auditStatus != null">audit_status,</if>
@@ -94,6 +96,7 @@
<if test="titleCertUrl != null">#{titleCertUrl},</if>
<if test="bankCard != null">#{bankCard},</if>
<if test="bankName != null">#{bankName},</if>
<if test="bankBranch != null">#{bankBranch},</if>
<if test="bankRegion != null">#{bankRegion},</if>
<if test="bankAddress != null">#{bankAddress},</if>
<if test="auditStatus != null">#{auditStatus},</if>
@@ -118,6 +121,7 @@
<if test="idCard != null">id_card = #{idCard},</if>
<if test="bankCard != null">bank_card = #{bankCard},</if>
<if test="bankName != null">bank_name = #{bankName},</if>
<if test="bankBranch != null">bank_branch = #{bankBranch},</if>
<if test="bankRegion != null">bank_region = #{bankRegion},</if>
<if test="bankAddress != null">bank_address = #{bankAddress},</if>
<if test="idCardAttachments != null">id_card_attachments = #{idCardAttachments},</if>
@@ -144,6 +148,7 @@
<if test="idCard != null">id_card,</if>
<if test="bankCard != null">bank_card,</if>
<if test="bankName != null">bank_name,</if>
<if test="bankBranch != null">bank_branch,</if>
<if test="bankRegion != null">bank_region,</if>
<if test="bankAddress != null">bank_address,</if>
<if test="idCardAttachments != null">id_card_attachments,</if>
@@ -162,6 +167,7 @@
<if test="idCard != null">#{idCard},</if>
<if test="bankCard != null">#{bankCard},</if>
<if test="bankName != null">#{bankName},</if>
<if test="bankBranch != null">#{bankBranch},</if>
<if test="bankRegion != null">#{bankRegion},</if>
<if test="bankAddress != null">#{bankAddress},</if>
<if test="idCardAttachments != null">#{idCardAttachments},</if>
@@ -178,6 +184,7 @@
<if test="idCard != null and idCard != ''">id_card = #{idCard},</if>
<if test="bankCard != null and bankCard != ''">bank_card = #{bankCard},</if>
<if test="bankName != null and bankName != ''">bank_name = #{bankName},</if>
<if test="bankBranch != null and bankBranch != ''">bank_branch = #{bankBranch},</if>
<if test="bankRegion != null and bankRegion != ''">bank_region = #{bankRegion},</if>
<if test="bankAddress != null and bankAddress != ''">bank_address = #{bankAddress},</if>
<if test="idCardAttachments != null and idCardAttachments != ''">id_card_attachments = #{idCardAttachments},</if>
@@ -201,7 +208,7 @@
(expert_id, user_id, name, phone, region, id_card,
work_unit, department, title,
practice_cert_url, title_cert_url,
bank_card, bank_name, bank_region, bank_address,
bank_card, bank_name, bank_branch, bank_region, bank_address,
id_card_attachments,
audit_status, audit_by, audit_time, status,
create_by, create_time)
@@ -210,7 +217,7 @@
(#{e.expertId}, #{e.userId}, #{e.name}, #{e.phone}, #{e.region}, #{e.idCard},
#{e.workUnit}, #{e.department}, #{e.title},
#{e.practiceCertUrl}, #{e.titleCertUrl},
#{e.bankCard}, #{e.bankName}, #{e.bankRegion}, #{e.bankAddress},
#{e.bankCard}, #{e.bankName}, #{e.bankBranch}, #{e.bankRegion}, #{e.bankAddress},
#{e.idCardAttachments},
#{e.auditStatus}, #{e.auditBy}, #{e.auditTime}, #{e.status},
#{e.createBy}, sysdate())
@@ -41,6 +41,7 @@
<result property="isDeleted" column="is_deleted" />
<result property="isEsigned" column="is_esigned" />
<result property="isInvited" column="is_invited" />
<result property="hasIntent" column="has_intent" />
</resultMap>
<insert id="insert" parameterType="BizMeetingAttendee">
insert into biz_meeting_attendee(id, meeting_id, user_id, create_by, create_time)
@@ -152,7 +153,12 @@
delete from biz_meeting_attendee where meeting_id = #{meetingId} and user_id = #{userId}
</delete>
<select id="selectByMeetingId" resultMap="BizMeetingAttendeeResult" parameterType="Long">
select id, meeting_id, user_id, name, phone, work_unit, department, title, id_card, bank_card, bank_name, bank_branch, bank_region, bank_address, account_name, id_card_attachments, labor_form, fee_pre_tax, tax, fee, vat_and_surcharge, summary, on_site_photos, signed_at, signed_ip, handsign, labor_protocol, labor_protocol_masked, create_by, create_time, is_deleted, is_esigned, is_invited
select id, meeting_id, user_id, name, phone, work_unit, department, title, id_card, bank_card, bank_name, bank_branch, bank_region, bank_address, account_name, id_card_attachments, labor_form, fee_pre_tax, tax, fee, vat_and_surcharge, summary, on_site_photos, signed_at, signed_ip, handsign, labor_protocol, labor_protocol_masked, create_by, create_time, is_deleted, is_esigned, is_invited,
(select if(exists(
select 1 from biz_execution_intent e
where e.user_id = biz_meeting_attendee.user_id
and e.project_no collate utf8mb4_unicode_ci = (select p.project_no collate utf8mb4_unicode_ci from biz_meeting m join biz_project p on m.project_id = p.project_id where m.meeting_id = #{meetingId})
), 1, 0)) as has_intent
from biz_meeting_attendee where meeting_id = #{meetingId} and is_deleted = 0
order by id
</select>
@@ -11,6 +11,7 @@
<result property="meetingName" column="meeting_name" />
<result property="periodNo" column="period_no" />
<result property="totalPeriods" column="total_periods" />
<result property="assignedSessions" column="assigned_sessions" />
<result property="projectForm" column="project_form" />
<result property="startTime" column="start_time" />
<result property="endTime" column="end_time" />
@@ -62,12 +63,14 @@
from biz_meeting
where meeting_id = #{meetingId} and is_deleted = 0
</select>
<select id="selectList" resultMap="BizMeetingResult" parameterType="BizMeeting">
select
<if test="userId != null">(select a.id from biz_meeting_attendee a where a.meeting_id = biz_meeting.meeting_id and a.user_id = #{userId} and a.is_deleted = 0 limit 1) as attendee_id,</if>
<if test="userId != null">(select a.labor_protocol from biz_meeting_attendee a where a.meeting_id = biz_meeting.meeting_id and a.user_id = #{userId} and a.is_deleted = 0 limit 1) as attendee_labor_protocol,</if>
(select o.org_name from biz_project p join biz_org o on o.org_id = p.sponsor_org_id where p.project_id = biz_meeting.project_id limit 1) as org_name,
(select p.invitation_url from biz_project p where p.project_id = biz_meeting.project_id limit 1) as project_invitation_url,
<if test="params.assignedExecutorUserId != null">(select coalesce(sum(a.sessions), 0) from biz_project_assign a where a.project_id = biz_meeting.project_id and a.is_deleted = 0 and a.execution_unit_id = (select org_id from biz_org where user_id = #{params.assignedExecutorUserId} and org_type = 'executor')) as assigned_sessions,</if>
<include refid="selectFields"/>
from biz_meeting
<where>
@@ -78,15 +81,15 @@
<if test="periodNo != null">and period_no = #{periodNo}</if>
<if test="projectForm != null and projectForm != ''">and project_form = #{projectForm}</if>
<if test="currentStage != null and currentStage != ''">and current_stage = #{currentStage}</if>
<if test="currentStageNotIn != null and currentStageNotIn != ''">
and current_stage not in
<foreach collection="currentStageNotIn.split(',')" item="s" open="(" separator="," close=")">#{s}</foreach>
</if>
<if test="startTime != null">and start_time &gt;= #{startTime}</if>
<if test="endTime != null">and end_time &lt;= #{endTime}</if>
<!-- doctor 角色按 user_id 过滤 (走 biz_meeting_attendee 中间表, 同时 attendee 也需 is_deleted=0) -->
<if test="userId != null">and exists (select 1 from biz_meeting_attendee a where a.meeting_id = biz_meeting.meeting_id and a.user_id = #{userId} and a.is_deleted = 0)</if>
<!-- sponsor 数据权限: 只看"我的项目"下的会议 (project_id ∈ 我的项目). MAIN 走 sponsor_org_id (经 user_id 反查 org_id), SUB 走 sponsor_assign.monitor_user_id.
刻意不带 biz_publicity_support_intent 关联 (与项目列表 selectSponsorList 的区别点) -->
<if test="params.sponsorAdminUserId != null">and project_id in (select project_id from biz_project where sponsor_org_id = (select org_id from biz_org where user_id = #{params.sponsorAdminUserId} and org_type = 'sponsor') and is_deleted = 0)</if>
<if test="params.monitorUserId != null">and project_id in (select distinct project_id from biz_project_sponsor_assign where monitor_user_id = #{params.monitorUserId} and is_deleted = 0)</if>
<!-- 结题且未开通的项目, sponsor 会议不可见 (与项目列表 selectSponsorList 同口径) -->
<if test="params.sponsorAdminUserId != null or params.monitorUserId != null">
and not exists (
select 1 from biz_project p2
@@ -95,20 +98,39 @@
and p2.is_finished = '1' and p2.open_status = 'N'
)
</if>
<!-- executor 数据权限: MAIN 看本执行单位项目下的会议 (biz_project_assign.execution_unit_id), SUB(执行人) 只看本人创建的会议 (create_by) -->
<if test="params.executorUserId != null">and project_id in (
select distinct a.project_id from biz_project_assign a
where a.is_deleted = 0
and a.execution_unit_id = (select org_id from biz_org where user_id = #{params.executorUserId} and org_type = 'executor')
)</if>
<if test="params.executorCreatorUsername != null and params.executorCreatorUsername != ''">and create_by = #{params.executorCreatorUsername}</if>
<!-- 合规人员(manager) 数据权限: 只看本人创建项目的会议 -->
<if test="params.managerCreateUserId != null">and project_id in (
select project_id from biz_project where create_user_id = #{params.managerCreateUserId} and is_deleted = 0
)</if>
</where>
order by meeting_id desc
</select>
<!-- 会议阶段统计 (仅 sponsor/Home KPI 用): 按 current_stage 分组计数, 只套 sponsor 数据权限 (其他角色单独修, 不在此复用多角色过滤) -->
<select id="selectStageStats" resultType="java.util.HashMap" parameterType="BizMeeting">
select current_stage as currentStage, count(*) as cnt
from biz_meeting
<where>
is_deleted = 0
<if test="params.sponsorAdminUserId != null">and project_id in (select project_id from biz_project where sponsor_org_id = (select org_id from biz_org where user_id = #{params.sponsorAdminUserId} and org_type = 'sponsor') and is_deleted = 0)</if>
<if test="params.monitorUserId != null">and project_id in (select distinct project_id from biz_project_sponsor_assign where monitor_user_id = #{params.monitorUserId} and is_deleted = 0)</if>
<if test="params.sponsorAdminUserId != null or params.monitorUserId != null">
and not exists (
select 1 from biz_project p2
where p2.project_id = biz_meeting.project_id
and p2.is_deleted = 0
and p2.is_finished = '1' and p2.open_status = 'N'
)
</if>
</where>
group by current_stage
</select>
<insert id="insert" parameterType="BizMeeting">
insert into biz_meeting
<trim prefix="(" suffix=")" suffixOverrides=",">
@@ -250,7 +272,27 @@
and execution_unit_id = #{executionUnitId}
and period_no = #{periodNo}
</select>
<!-- 自动流转 (MeetingStageScheduler 每分钟调): start_time 已过 且 material 未提交 且未执行的会议 → is_executed=1 + RUNNING. 已软删/已冻结/已提交材料的不动. -->
<!-- 修改校验用 (执行方隔离): 同上, 但排除指定 meetingId (修改自身会议不触发相同期数误报) -->
<select id="countByProjectIdExecutionUnitPeriodExclude" resultType="int">
select count(*) from biz_meeting where project_id = #{projectId} and is_deleted = 0
and execution_unit_id = #{executionUnitId}
and period_no = #{periodNo}
and meeting_id != #{excludeMeetingId}
</select>
<!-- 自动流转 (MeetingStageScheduler 每分钟调): start_time 已过 且 end_time 未到 且 material 未提交 且未执行的会议 → current_stage = IN_PROGRESS (执行中). 已软删/已冻结/已执行的不动. -->
<update id="markInProgress">
update biz_meeting
set current_stage = 'IN_PROGRESS'
where is_deleted = 0
and is_executed = 0
and is_frozen = 0
and start_time is not null
and start_time &lt;= NOW()
and end_time &gt; NOW()
and labor_audit_stage = 'NOT_SUBMITTED'
and service_audit_stage = 'NOT_SUBMITTED'
</update>
<!-- 自动流转 (MeetingStageScheduler 每分钟调): end_time 已过 且 material 未提交 且未执行的会议 → is_executed=1 + RUNNING (已执行). 已软删/已冻结/已提交材料的不动. -->
<update id="markExecuted">
update biz_meeting
set is_executed = 1,
@@ -259,8 +301,8 @@
where is_deleted = 0
and is_executed = 0
and is_frozen = 0
and start_time is not null
and start_time &lt;= NOW()
and end_time is not null
and end_time &lt;= NOW()
and labor_audit_stage = 'NOT_SUBMITTED'
and service_audit_stage = 'NOT_SUBMITTED'
</update>
@@ -282,9 +324,9 @@
<select id="selectPendingFeeCalcIds" resultType="Long">
select meeting_id from biz_meeting where fee_calc_status = 0 and is_deleted = 0
</select>
<!-- 置未汇总 (人员/材料变化触发, 幂等) -->
<update id="markFeeCalcPending" parameterType="Long">
update biz_meeting set fee_calc_status = 0 where meeting_id = #{meetingId}
<!-- 费用重算状态机: 直接置 fee_calc_status (-1 计算中 / 0 待算兜底); 成功(1) 由 updateFeeSummary 一并写入 -->
<update id="updateFeeCalcStatus">
update biz_meeting set fee_calc_status = #{status} where meeting_id = #{meetingId}
</update>
<!-- 汇总回写 3 个费用字段 + 置已汇总 -->
<update id="updateFeeSummary">
@@ -295,4 +337,11 @@
fee_calc_status = 1
where meeting_id = #{meetingId}
</update>
<!-- 同步重算劳务费 (参会人增删改后立即调用): 只回写 labor_fee + total_fee, 不动 meeting_fee / fee_calc_status -->
<update id="updateLaborFee">
update biz_meeting
set labor_fee = #{laborFee},
total_fee = #{totalFee}
where meeting_id = #{meetingId}
</update>
</mapper>
@@ -21,9 +21,11 @@
<sql id="selectFields">
select m.msg_id, m.receiver_user_id, m.msg_type, m.title, m.content, m.biz_type, m.biz_id,
m.is_read, m.read_time, m.create_by, m.create_time, m.update_by, m.update_time,
u.user_name as receiver_name
COALESCE(NULLIF(bp.name, ''), NULLIF(be.name, ''), u.nick_name) as receiver_name
from biz_message m
left join sys_user u on u.user_id = m.receiver_user_id
left join biz_person bp on bp.user_id = m.receiver_user_id
left join biz_expert be on be.user_id = m.receiver_user_id
</sql>
<select id="selectByPrimaryKey" resultMap="BizMessageResult" parameterType="Long">
@@ -49,9 +51,23 @@
m.receiver_user_id = #{receiverUserId}
</where>
order by m.is_read asc, m.msg_id desc
<if test="params.limit != null">
limit #{params.limit}
</if>
<!-- 分页: params.offset 有值时用 offset,limit; 否则只用 limit (嵌入式列表) -->
<choose>
<when test="params.offset != null">
limit #{params.offset}, #{params.limit}
</when>
<otherwise>
<if test="params.limit != null">
limit #{params.limit}
</if>
</otherwise>
</choose>
</select>
<!-- 某用户的全部消息总数 (分页 total 用, 与 countUnread 解耦) -->
<select id="countMy" resultType="int" parameterType="Long">
select count(*) from biz_message
where receiver_user_id = #{receiverUserId}
</select>
<select id="countUnread" resultType="int" parameterType="Long">
@@ -120,7 +120,7 @@
<if test="orgId != null">and o.org_id = #{orgId}</if>
<if test="orgName != null and orgName != ''">and o.org_name like concat('%', #{orgName}, '%')</if>
order by o.org_id desc
LIMIT 5
LIMIT 10
</select>
<!--
@@ -146,7 +146,7 @@
<if test="orgId != null">and o.org_id = #{orgId}</if>
<if test="orgName != null and orgName != ''">and o.org_name like concat('%', #{orgName}, '%')</if>
order by o.org_id desc
LIMIT 5
LIMIT 10
</select>
<!--
@@ -198,4 +198,12 @@
(select org_id from biz_person where user_id = #{userId} limit 1)
)
</select>
<!-- 单位名称查重 (新增/改名前): 同 orgType 下 org_name 精确匹配 (trim 后) 的条数; orgId 传非空则排除自身 (改名用) -->
<select id="countByOrgName" parameterType="BizOrg" resultType="int">
select count(*) from biz_org
where org_type = #{orgType}
and trim(org_name) = #{orgName}
<if test="orgId != null"> and org_id != #{orgId}</if>
</select>
</mapper>
@@ -11,6 +11,7 @@
<result property="department" column="department" />
<result property="position" column="position" />
<result property="userId" column="user_id" />
<result property="isSynced" column="is_synced" />
<result property="unitType" column="unit_type" />
<result property="accountType" column="account_type" />
<result property="parentUserId" column="parent_user_id" />
@@ -23,14 +24,14 @@
</resultMap>
<sql id="selectFields">
select person_id, name, phone, org_id, department, position, unit_type, user_id, create_by, create_time, update_by, update_time
select person_id, name, phone, org_id, department, position, unit_type, is_synced, user_id, create_by, create_time, update_by, update_time
from biz_person
</sql>
<!-- 通用列表: LEFT JOIN biz_org 取公司名/类型, LEFT JOIN sys_user 取账号状态/类型 -->
<sql id="selectFieldsWithAccount">
select p.person_id, p.name, p.phone, p.org_id, o.org_name, o.org_type,
p.department, p.position, p.unit_type, p.user_id,
p.department, p.position, p.unit_type, p.is_synced, p.user_id,
p.create_by, p.create_time, p.update_by, p.update_time,
u.account_type, u.parent_user_id, u.status, u.del_flag as user_del_flag,
u.user_name as user_name,
@@ -82,6 +83,7 @@
<if test="department != null">department,</if>
<if test="position != null">position,</if>
<if test="unitType != null">unit_type,</if>
<if test="isSynced != null">is_synced,</if>
<if test="userId != null">user_id,</if>
<if test="createBy != null and createBy != ''">create_by,</if>
create_time,
@@ -96,6 +98,7 @@
<if test="department != null">#{department},</if>
<if test="position != null">#{position},</if>
<if test="unitType != null">#{unitType},</if>
<if test="isSynced != null">#{isSynced},</if>
<if test="userId != null">#{userId},</if>
<if test="createBy != null and createBy != ''">#{createBy},</if>
sysdate(),
@@ -110,6 +113,7 @@
<if test="userId != null and userId != ''">user_id = #{userId},</if>
<if test="orgId != null">org_id = #{orgId},</if>
<if test="unitType != null and unitType != ''">unit_type = #{unitType},</if>
<if test="isSynced != null">is_synced = #{isSynced},</if>
<if test="name != null">name = #{name},</if>
<if test="phone != null">phone = #{phone},</if>
<if test="department != null">department = #{department},</if>
@@ -145,15 +149,13 @@
</foreach>
</update>
<!-- sponsor 专属: 通过 biz_person.user_id 关联 sys_user, 利用 sys_user.parent_user_id 过滤主账号归属 -->
<!-- 主账号自己 (parent_user_id=NULL) 也通过 OR u.user_id=#{sponsorOwnerUid} 一并带上 (否则主账号看不到自己) -->
<!-- sponsor 专属: SQL 硬编码 unit_type='sponsor' + 严格按 org_id 圈本机构所有用户 (含主账号自己) -->
<select id="selectSponsorList" resultMap="BizPersonResult" parameterType="BizPerson">
<include refid="selectFieldsWithAccount"/>
<where>
u.del_flag = '0'
and p.unit_type = 'sponsor'
and (u.parent_user_id = #{params.sponsorOwnerUid}
or u.user_id = #{params.sponsorOwnerUid})
and p.org_id = #{params.sponsorOrgId}
<if test="name != null and name != ''"> and p.name like concat('%', #{name}, '%')</if>
<if test="phone != null and phone != ''"> and p.phone = #{phone}</if>
<if test="orgId != null"> and p.org_id = #{orgId}</if>
@@ -165,15 +167,13 @@
order by p.person_id desc
</select>
<!-- executor 专属: 同 sponsor, SQL 硬编码 unit_type='executor' + parent_user_id=当前主账号 (前端绕不开) -->
<!-- 主账号自己 (parent_user_id=NULL) 也通过 OR u.user_id=#{executorOwnerUid} 一并带上 (否则主账号看不到自己) -->
<!-- executor 专属: SQL 硬编码 unit_type='executor' + 严格按 org_id 圈本机构所有用户 (含主账号自己) -->
<select id="selectExecutorList" resultMap="BizPersonResult" parameterType="BizPerson">
<include refid="selectFieldsWithAccount"/>
<where>
u.del_flag = '0'
and p.unit_type = 'executor'
and (u.parent_user_id = #{params.executorOwnerUid}
or u.user_id = #{params.executorOwnerUid})
and p.org_id = #{params.executorOrgId}
<if test="name != null and name != ''"> and p.name like concat('%', #{name}, '%')</if>
<if test="phone != null and phone != ''"> and p.phone = #{phone}</if>
<if test="orgId != null"> and p.org_id = #{orgId}</if>
@@ -185,4 +185,21 @@
order by p.person_id desc
</select>
<!-- 按 user_id 反查人员档案 (个人资料编辑: 拿 personId 再走 updateByPrimaryKey) -->
<select id="selectByUserId" resultMap="BizPersonResult" parameterType="Long">
<include refid="selectFields"/>
where user_id = #{userId}
limit 1
</select>
<!-- 按 org_id 反查该机构主账号 user_id: biz_person.org_id 绑定 + sys_user.account_type='MAIN', 不依赖 biz_org.user_id -->
<select id="selectMainUserIdByOrgId" resultType="java.lang.Long" parameterType="Long">
select u.user_id
from biz_person p
join sys_user u on u.user_id = p.user_id
where p.org_id = #{orgId} and u.account_type = 'MAIN' and u.del_flag = '0'
order by u.user_id
limit 1
</select>
</mapper>
@@ -35,12 +35,14 @@
<select id="selectByProjectId" resultMap="BaseResultMap">
SELECT a.*,
e.user_name AS executor_user_name,
s.user_name AS staff_user_name
COALESCE(NULLIF(ep.name, ''), e.nick_name) AS executor_user_name,
COALESCE(NULLIF(sp.name, ''), s.nick_name) AS staff_user_name
FROM biz_project_executor_assign a
LEFT JOIN biz_org o ON o.org_id = a.executor_org_id
LEFT JOIN sys_user e ON e.user_id = o.user_id
LEFT JOIN biz_person ep ON ep.user_id = o.user_id
LEFT JOIN sys_user s ON a.staff_user_id = s.user_id
LEFT JOIN biz_person sp ON sp.user_id = a.staff_user_id
WHERE a.project_id = #{projectId} and a.is_deleted = 0
ORDER BY a.create_time DESC
</select>
@@ -51,7 +51,15 @@
<result property="isDeleted" column="is_deleted" />
</resultMap>
<sql id="selectFields">
select p.project_id, p.project_no, p.project_name, p.total_sessions, p.done_sessions, p.todo_sessions, p.total_amount,
select p.project_id, p.project_no, p.project_name, p.total_sessions, p.total_amount,
<!-- 已执行会议数: stage 走过 NOT_STARTED/IN_PROGRESS 就算 (含 FROZEN 已结算异常态) -->
(select count(*) from biz_meeting m
where m.project_id = p.project_id and m.is_deleted = 0
and m.current_stage not in ('NOT_STARTED','IN_PROGRESS')) as done_sessions,
<!-- 未执行会议数: 仅 NOT_STARTED -->
(select count(*) from biz_meeting m
where m.project_id = p.project_id and m.is_deleted = 0
and m.current_stage = 'NOT_STARTED') as todo_sessions,
(select ifnull(sum(m.labor_fee), 0) from biz_meeting m where m.project_id = p.project_id and m.is_settled = 1 and m.is_deleted = 0) as paid_labor_amount,
(select ifnull(sum(m.meeting_fee), 0) from biz_meeting m where m.project_id = p.project_id and m.is_settled = 1 and m.is_deleted = 0) as paid_meeting_amount,
(p.total_amount - ifnull(p.manage_fee, 0)
@@ -59,8 +67,8 @@
- (select ifnull(sum(m.meeting_fee), 0) from biz_meeting m where m.project_id = p.project_id and m.is_settled = 1 and m.is_deleted = 0)) as available_amount,
p.manager_score, p.sponsor_score, p.project_form, p.is_finished, p.is_settled, p.is_published, p.publish_time, p.sponsor_org_id, p.lead_user_id, p.is_bid_project, p.create_by, p.create_user_id, p.create_time, p.update_by, p.update_time, p.manage_fee, p.role_labor, p.start_time, p.end_time, p.submit_deadline_days, p.support_contract_url, p.execute_contract_url, p.invitation_url, p.support_letter_url, p.publish_url, p.schedule_url, p.open_deadline, p.open_status, p.is_deleted,
o.org_name as sponsor_org_name,
su.user_name as sponsor_admin_user_name,
lu.user_name as lead_user_name,
COALESCE(NULLIF(sup.name, ''), su.nick_name) as sponsor_admin_user_name,
COALESCE(NULLIF(lup.name, ''), lu.nick_name) as lead_user_name,
bp.name as create_user_name,
(select group_concat(distinct o2.org_name separator ',')
from biz_project_assign bpa
@@ -70,13 +78,21 @@
left join biz_org o on o.org_id = p.sponsor_org_id and o.org_type = 'sponsor'
left join sys_user su on su.user_id = o.user_id
left join sys_user lu on lu.user_id = p.lead_user_id
left join biz_person sup on sup.user_id = o.user_id
left join biz_person lup on lup.user_id = p.lead_user_id
left join biz_person bp on bp.user_id = p.create_user_id
</sql>
<!-- sponsor 端专属查询: 与 selectFields 等价 (sponsor 评分改走 biz_project_rating 子表, 这里只查项目本体) -->
<sql id="selectFieldsForSponsor">
select p.project_id, p.project_no, p.project_name, p.total_sessions, p.done_sessions, p.todo_sessions,
select p.project_id, p.project_no, p.project_name, p.total_sessions,
p.total_amount,
(select count(*) from biz_meeting m
where m.project_id = p.project_id and m.is_deleted = 0
and m.current_stage not in ('NOT_STARTED','IN_PROGRESS')) as done_sessions,
(select count(*) from biz_meeting m
where m.project_id = p.project_id and m.is_deleted = 0
and m.current_stage = 'NOT_STARTED') as todo_sessions,
(select ifnull(sum(m.labor_fee), 0) from biz_meeting m where m.project_id = p.project_id and m.is_settled = 1 and m.is_deleted = 0) as paid_labor_amount,
(select ifnull(sum(m.meeting_fee), 0) from biz_meeting m where m.project_id = p.project_id and m.is_settled = 1 and m.is_deleted = 0) as paid_meeting_amount,
(p.total_amount - ifnull(p.manage_fee, 0)
@@ -89,8 +105,8 @@
p.support_contract_url, p.execute_contract_url, p.invitation_url, p.support_letter_url,
p.publish_url, p.schedule_url, p.open_deadline, p.open_status, p.is_deleted,
o.org_name as sponsor_org_name,
su.user_name as sponsor_admin_user_name,
lu.user_name as lead_user_name,
COALESCE(NULLIF(sup.name, ''), su.nick_name) as sponsor_admin_user_name,
COALESCE(NULLIF(lup.name, ''), lu.nick_name) as lead_user_name,
bp.name as create_user_name,
(select group_concat(distinct o2.org_name separator ',')
from biz_project_assign bpa
@@ -100,6 +116,8 @@
left join biz_org o on o.org_id = p.sponsor_org_id and o.org_type = 'sponsor'
left join sys_user su on su.user_id = o.user_id
left join sys_user lu on lu.user_id = p.lead_user_id
left join biz_person sup on sup.user_id = o.user_id
left join biz_person lup on lup.user_id = p.lead_user_id
left join biz_person bp on bp.user_id = p.create_user_id
</sql>
<select id="selectByPrimaryKey" resultMap="BizProjectResult" parameterType="Long">
@@ -150,6 +168,7 @@
<if test="startTime != null">and p.start_time &gt;= #{startTime}</if>
<if test="endTime != null">and p.end_time &lt;= #{endTime}</if>
<if test="isFinished != null and isFinished != ''">and p.is_finished = #{isFinished}</if>
<if test="isSettled != null and isSettled != ''">and p.is_settled = #{isSettled}</if>
</where>
order by p.project_id desc
</select>
@@ -164,10 +183,10 @@
biz_meeting.execution_unit_id = 本执行方 org 过滤, 与项目级 total_amount/available_amount 无关.
-->
<select id="selectExecutorList" resultMap="BizProjectResult" parameterType="BizProject">
select distinct p.project_id, p.project_no, p.project_name, p.total_sessions, p.done_sessions, p.todo_sessions, p.total_amount, p.manager_score, p.sponsor_score, p.project_form, p.is_finished, p.is_settled, p.is_published, p.sponsor_org_id, p.lead_user_id, p.is_bid_project, p.create_by, p.create_user_id, p.create_time, p.update_by, p.update_time, p.manage_fee, p.role_labor, p.start_time, p.end_time, p.submit_deadline_days, p.support_contract_url, p.execute_contract_url, p.invitation_url, p.support_letter_url, p.publish_url,
select distinct p.project_id, p.project_no, p.project_name, p.total_sessions, p.total_amount, p.manager_score, p.sponsor_score, p.project_form, p.is_finished, p.is_settled, p.is_published, p.sponsor_org_id, p.lead_user_id, p.is_bid_project, p.create_by, p.create_user_id, p.create_time, p.update_by, p.update_time, p.manage_fee, p.role_labor, p.start_time, p.end_time, p.submit_deadline_days, p.support_contract_url, p.execute_contract_url, p.invitation_url, p.support_letter_url, p.publish_url,
o.org_name as sponsor_org_name,
su.user_name as sponsor_admin_user_name,
lu.user_name as lead_user_name,
COALESCE(NULLIF(sup.name, ''), su.nick_name) as sponsor_admin_user_name,
COALESCE(NULLIF(lup.name, ''), lu.nick_name) as lead_user_name,
bp.name as create_user_name,
(select group_concat(distinct o2.org_name separator ',')
from biz_project_assign bpa2
@@ -213,7 +232,17 @@
and m.is_deleted = 0
and m.execution_unit_id = (select org_id from biz_org where user_id = #{params.executorUserId} and org_type = 'executor')) as available_amount,
(select count(*) from biz_meeting m where m.project_id = p.project_id and m.is_deleted = 0
and m.execution_unit_id = (select org_id from biz_org where user_id = #{params.executorUserId} and org_type = 'executor')) as meeting_count
and m.execution_unit_id = (select org_id from biz_org where user_id = #{params.executorUserId} and org_type = 'executor')) as meeting_count,
<!-- 执行方级已执行: 同上 execution_unit_id 隔离, FROZEN 算已执行 -->
(select count(*) from biz_meeting m
where m.project_id = p.project_id and m.is_deleted = 0
and m.current_stage not in ('NOT_STARTED','IN_PROGRESS')
and m.execution_unit_id = (select org_id from biz_org where user_id = #{params.executorUserId} and org_type = 'executor')) as done_sessions,
<!-- 执行方级未执行 -->
(select count(*) from biz_meeting m
where m.project_id = p.project_id and m.is_deleted = 0
and m.current_stage = 'NOT_STARTED'
and m.execution_unit_id = (select org_id from biz_org where user_id = #{params.executorUserId} and org_type = 'executor')) as todo_sessions
from biz_project p
<!-- 执行方专属 join: 把 executor 限定条件放进 ON (而不是 WHERE), 这样 join 只命中分给当前执行方的 assignment, 1 行/项目. SELECT DISTINCT 保留以防 LEFT JOIN 副作用 -->
join biz_project_assign a on a.project_id = p.project_id
@@ -222,6 +251,8 @@
left join biz_org o on o.org_id = p.sponsor_org_id and o.org_type = 'sponsor'
left join sys_user su on su.user_id = o.user_id
left join sys_user lu on lu.user_id = p.lead_user_id
left join biz_person sup on sup.user_id = o.user_id
left join biz_person lup on lup.user_id = p.lead_user_id
left join biz_person bp on bp.user_id = p.create_user_id
<where>
p.is_deleted = 0
@@ -230,6 +261,7 @@
<if test="startTime != null">and p.start_time &gt;= #{startTime}</if>
<if test="endTime != null">and p.end_time &lt;= #{endTime}</if>
<if test="isFinished != null and isFinished != ''">and p.is_finished = #{isFinished}</if>
<if test="isSettled != null and isSettled != ''">and p.is_settled = #{isSettled}</if>
</where>
order by p.project_id desc
</select>
@@ -242,10 +274,10 @@
已支付劳务/会务/可用金额同样按 biz_meeting.execution_unit_id = 本公司 org 过滤 (执行方级).
-->
<select id="selectExecutorStaffList" resultMap="BizProjectResult" parameterType="BizProject">
select p.project_id, p.project_no, p.project_name, p.total_sessions, p.done_sessions, p.todo_sessions, p.total_amount, p.manager_score, p.sponsor_score, p.project_form, p.is_finished, p.is_settled, p.is_published, p.sponsor_org_id, p.lead_user_id, p.is_bid_project, p.create_by, p.create_user_id, p.create_time, p.update_by, p.update_time, p.manage_fee, p.role_labor, p.start_time, p.end_time, p.submit_deadline_days, p.support_contract_url, p.execute_contract_url, p.invitation_url, p.support_letter_url, p.publish_url,
select p.project_id, p.project_no, p.project_name, p.total_sessions, p.total_amount, p.manager_score, p.sponsor_score, p.project_form, p.is_finished, p.is_settled, p.is_published, p.sponsor_org_id, p.lead_user_id, p.is_bid_project, p.create_by, p.create_user_id, p.create_time, p.update_by, p.update_time, p.manage_fee, p.role_labor, p.start_time, p.end_time, p.submit_deadline_days, p.support_contract_url, p.execute_contract_url, p.invitation_url, p.support_letter_url, p.publish_url,
o.org_name as sponsor_org_name,
su.user_name as sponsor_admin_user_name,
lu.user_name as lead_user_name,
COALESCE(NULLIF(sup.name, ''), su.nick_name) as sponsor_admin_user_name,
COALESCE(NULLIF(lup.name, ''), lu.nick_name) as lead_user_name,
bp.name as create_user_name,
(select group_concat(distinct o2.org_name separator ',')
from biz_project_assign bpa2
@@ -291,11 +323,22 @@
and m.is_deleted = 0
and m.execution_unit_id = (select org_id from biz_org where user_id = #{params.executorUserId} and org_type = 'executor')) as available_amount,
(select count(*) from biz_meeting m where m.project_id = p.project_id and m.is_deleted = 0
and m.execution_unit_id = (select org_id from biz_org where user_id = #{params.executorUserId} and org_type = 'executor')) as meeting_count
and m.execution_unit_id = (select org_id from biz_org where user_id = #{params.executorUserId} and org_type = 'executor')) as meeting_count,
<!-- 执行人视角: 仍按主账号 org_id 聚合 (执行人看公司数据不是个人), FROZEN 算已执行 -->
(select count(*) from biz_meeting m
where m.project_id = p.project_id and m.is_deleted = 0
and m.current_stage not in ('NOT_STARTED','IN_PROGRESS')
and m.execution_unit_id = (select org_id from biz_org where user_id = #{params.executorUserId} and org_type = 'executor')) as done_sessions,
(select count(*) from biz_meeting m
where m.project_id = p.project_id and m.is_deleted = 0
and m.current_stage = 'NOT_STARTED'
and m.execution_unit_id = (select org_id from biz_org where user_id = #{params.executorUserId} and org_type = 'executor')) as todo_sessions
from biz_project p
left join biz_org o on o.org_id = p.sponsor_org_id and o.org_type = 'sponsor'
left join sys_user su on su.user_id = o.user_id
left join sys_user lu on lu.user_id = p.lead_user_id
left join biz_person sup on sup.user_id = o.user_id
left join biz_person lup on lup.user_id = p.lead_user_id
left join biz_person bp on bp.user_id = p.create_user_id
<where>
p.is_deleted = 0
@@ -309,6 +352,7 @@
<if test="startTime != null">and p.start_time &gt;= #{startTime}</if>
<if test="endTime != null">and p.end_time &lt;= #{endTime}</if>
<if test="isFinished != null and isFinished != ''">and p.is_finished = #{isFinished}</if>
<if test="isSettled != null and isSettled != ''">and p.is_settled = #{isSettled}</if>
</where>
order by p.project_id desc
</select>
@@ -25,6 +25,7 @@
<result property="createTime" column="create_time" />
<result property="updateBy" column="update_by" />
<result property="updateTime" column="update_time" />
<result property="submitTime" column="submit_time" />
<result property="isDeleted" column="is_deleted" />
</resultMap>
<sql id="selectFields">
@@ -32,9 +33,9 @@
s.title as plan_direction_title,
p.plan_category, p.project_form, p.design_file_url, p.subject_direction, p.status, p.is_settled,
p.project_no, p.remark, p.audit_opinion, p.audit_by, p.audit_time, p.submitter_id,
COALESCE(bp.name, u.user_name) as submitter_name,
COALESCE(bp.name, u.nick_name) as submitter_name,
proj.project_name as project_name,
p.create_by, p.create_time, p.update_by, p.update_time, p.is_deleted
p.create_by, p.create_time, p.update_by, p.update_time, p.submit_time, p.is_deleted
from biz_project_plan p
left join biz_special_plan s on s.id = p.plan_direction_id
left join sys_user u on u.user_id = p.submitter_id
@@ -49,6 +50,8 @@
<include refid="selectFields"/>
<where>
p.is_deleted = 0
<!-- 管理角色 (admin/manager): 未提交草稿 status='0' 不进列表 (controller 注入 params.excludeDraft) -->
<if test="params.excludeDraft == true"> and p.status != '0'</if>
<if test="planName != null and planName != ''"> and p.plan_name like concat('%', #{planName}, '%')</if>
<if test="planDirectionId != null"> and p.plan_direction_id = #{planDirectionId}</if>
<if test="planCategory != null and planCategory != ''"> and p.plan_category = #{planCategory}</if>
@@ -57,11 +60,11 @@
<choose>
<!-- 选了具体状态: 等值匹配 -->
<when test="status != null and status != ''"> and p.status = #{status}</when>
<!-- 未选: 不加 status 过滤, 由前端按角色决定默认值 (经理侧默认查 1/2/3, 医生侧默认查全部含 0) -->
<!-- 未选: 不加 status 等值过滤; 未提交草稿 '0' 已由上方 params.excludeDraft 对管理角色排除 -->
</choose>
<if test="remark != null and remark != ''"> and p.remark like concat('%', #{remark}, '%')</if>
</where>
order by p.plan_id desc
order by (p.submit_time is null), p.submit_time desc, p.plan_id desc
</select>
<insert id="insert" parameterType="BizProjectPlan">
insert into biz_project_plan
@@ -79,6 +82,8 @@
<if test="projectNo != null and projectNo != ''">project_no,</if>
<if test="remark != null">remark,</if>
<if test="submitterId != null">submitter_id,</if>
<if test="createBy != null">create_by,</if>
<if test="createTime != null">create_time,</if>
</trim>
<trim prefix="values (" suffix=")" suffixOverrides=",">
<if test="planId != null and planId != ''">#{planId},</if>
@@ -94,6 +99,8 @@
<if test="projectNo != null and projectNo != ''">#{projectNo},</if>
<if test="remark != null">#{remark},</if>
<if test="submitterId != null">#{submitterId},</if>
<if test="createBy != null">#{createBy},</if>
<if test="createTime != null">#{createTime},</if>
</trim>
</insert>
<update id="updateByPrimaryKey" parameterType="BizProjectPlan">
@@ -114,6 +121,7 @@
<if test="status != null">status = #{status},</if>
<if test="remark != null">remark = #{remark},</if>
<if test="submitterId != null">submitter_id = #{submitterId},</if>
<if test="submitTime != null">submit_time = #{submitTime},</if>
</trim>
where plan_id = #{planId}
</update>
@@ -35,12 +35,14 @@
<select id="selectByProjectId" resultMap="BaseResultMap">
SELECT a.*,
s.user_name AS sponsor_user_name,
m.user_name AS monitor_user_name
COALESCE(NULLIF(sp.name, ''), s.nick_name) AS sponsor_user_name,
COALESCE(NULLIF(p.name, ''), m.nick_name) AS monitor_user_name
FROM biz_project_sponsor_assign a
LEFT JOIN biz_org o ON o.org_id = a.sponsor_org_id
LEFT JOIN sys_user s ON s.user_id = o.user_id
LEFT JOIN sys_user m ON a.monitor_user_id = m.user_id
LEFT JOIN biz_person sp ON sp.user_id = o.user_id
LEFT JOIN biz_person p ON p.user_id = a.monitor_user_id
INNER JOIN sys_user m ON a.monitor_user_id = m.user_id
WHERE a.project_id = #{projectId} and a.is_deleted = 0
ORDER BY a.create_time DESC
</select>