refactor(frontend): split large reimbursement and audit modules
This commit is contained in:
@@ -87,12 +87,17 @@
|
||||
<strong>{{ message.role === 'assistant' ? (message.assistantName || ASSISTANT_DISPLAY_NAME) : '我' }}</strong>
|
||||
<time>{{ message.time }}</time>
|
||||
</header>
|
||||
<p
|
||||
v-if="message.text && (message.role !== 'assistant' || message.reviewPayload)"
|
||||
:class="{ 'review-summary': message.role === 'assistant' && message.reviewPayload }"
|
||||
>
|
||||
{{ message.text }}
|
||||
</p>
|
||||
<div
|
||||
v-if="message.text && message.role === 'assistant' && message.reviewPayload"
|
||||
class="review-summary message-answer-content message-answer-markdown"
|
||||
v-html="renderMarkdown(message.text)"
|
||||
></div>
|
||||
|
||||
<div
|
||||
v-else-if="message.text && message.role !== 'assistant'"
|
||||
class="message-answer-content message-answer-markdown message-rich-text"
|
||||
v-html="renderMarkdown(message.text)"
|
||||
></div>
|
||||
|
||||
<div
|
||||
v-else-if="message.text && message.role === 'assistant'"
|
||||
@@ -288,88 +293,49 @@
|
||||
</div>
|
||||
|
||||
<div v-if="message.role === 'assistant' && message.reviewPayload" class="message-detail-block review-message-block">
|
||||
<div class="review-card-shell">
|
||||
<div class="review-card-head">
|
||||
<div class="review-card-head-main">
|
||||
<span class="review-card-icon">
|
||||
<i class="mdi mdi-shield-alert-outline"></i>
|
||||
</span>
|
||||
<div class="review-card-head-copy">
|
||||
<strong>{{ buildReviewHeadline(message.reviewPayload, message.draftPayload) }}</strong>
|
||||
<p>{{ buildReviewSubline(message.reviewPayload, message.draftPayload) }}</p>
|
||||
</div>
|
||||
</div>
|
||||
<span class="review-card-state" :class="buildReviewStateTone(message.reviewPayload, message.draftPayload)">
|
||||
{{ buildReviewStateLabel(message.reviewPayload, message.draftPayload) }}
|
||||
</span>
|
||||
</div>
|
||||
|
||||
<details
|
||||
class="review-followup-panel"
|
||||
:class="buildReviewStateTone(message.reviewPayload, message.draftPayload)"
|
||||
:open="shouldOpenReviewDisclosure(message.reviewPayload)"
|
||||
<div class="review-plain-followup">
|
||||
<template
|
||||
v-for="followup in [buildReviewPlainFollowupCopy(message.reviewPayload)]"
|
||||
:key="`${message.id}-review-followup`"
|
||||
>
|
||||
<summary class="review-followup-head">
|
||||
<div class="review-followup-head-main">
|
||||
<span class="review-followup-mark">
|
||||
<i :class="buildReviewStateTone(message.reviewPayload, message.draftPayload) === 'ready' ? 'mdi mdi-clipboard-check-outline' : 'mdi mdi-clipboard-text-clock-outline'"></i>
|
||||
</span>
|
||||
<div class="review-followup-title-copy">
|
||||
<strong>{{ buildReviewTodoSectionTitle(message.reviewPayload) }}</strong>
|
||||
<p>{{ buildReviewDisclosureHint(message.reviewPayload) }}</p>
|
||||
<div class="review-followup-preview">
|
||||
<span
|
||||
v-for="item in buildReviewTodoItems(message.reviewPayload).slice(0, 2)"
|
||||
:key="`${message.id}-preview-${item.key}`"
|
||||
>
|
||||
{{ item.title }}
|
||||
</span>
|
||||
<span v-if="buildReviewTodoItems(message.reviewPayload).length > 2">
|
||||
+{{ buildReviewTodoItems(message.reviewPayload).length - 2 }}
|
||||
</span>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
<div class="review-followup-side">
|
||||
<span class="review-followup-count">{{ buildReviewTodoSectionMeta(message.reviewPayload) }}</span>
|
||||
<span class="review-followup-chevron">
|
||||
<i class="mdi mdi-chevron-down"></i>
|
||||
</span>
|
||||
</div>
|
||||
</summary>
|
||||
|
||||
<div class="review-followup-body">
|
||||
<div class="review-followup-list">
|
||||
<article
|
||||
v-for="item in buildReviewTodoItems(message.reviewPayload)"
|
||||
:key="`${message.id}-${item.key}`"
|
||||
class="review-followup-item"
|
||||
:class="item.tone"
|
||||
>
|
||||
<span class="review-followup-icon">
|
||||
<i :class="item.icon"></i>
|
||||
</span>
|
||||
<div class="review-followup-copy">
|
||||
<strong>{{ item.title }}</strong>
|
||||
<p>{{ item.hint }}</p>
|
||||
</div>
|
||||
<span class="review-followup-status">{{ item.status }}</span>
|
||||
</article>
|
||||
</div>
|
||||
|
||||
<p v-if="buildReviewDecisionHint(message.reviewPayload)" class="review-followup-helper">
|
||||
{{ buildReviewDecisionHint(message.reviewPayload) }}
|
||||
</p>
|
||||
</div>
|
||||
</details>
|
||||
<p class="review-plain-lead">{{ followup.lead }}</p>
|
||||
<ul v-if="followup.items.length" class="review-plain-list">
|
||||
<li
|
||||
v-for="item in followup.items"
|
||||
:key="`${message.id}-${item.key}`"
|
||||
>
|
||||
<span class="review-plain-label">{{ item.label }}:</span>
|
||||
<span>{{ item.text }}</span>
|
||||
</li>
|
||||
</ul>
|
||||
<p
|
||||
v-for="line in followup.notes"
|
||||
:key="`${message.id}-note-${line}`"
|
||||
class="review-plain-note"
|
||||
>
|
||||
{{ line }}
|
||||
</p>
|
||||
<p v-if="canUseInlineSaveDraft(message)" class="review-inline-save-copy">
|
||||
请核查上面的关键信息。您也可以暂时不处理上述的这些内容,我可以帮你先保存为
|
||||
<button
|
||||
type="button"
|
||||
class="review-inline-draft-link"
|
||||
:disabled="submitting || reviewActionBusy || sessionSwitchBusy"
|
||||
@click="handleInlineSaveDraft(message)"
|
||||
>
|
||||
草稿
|
||||
</button>
|
||||
。
|
||||
</p>
|
||||
</template>
|
||||
|
||||
<div
|
||||
v-if="resolveReviewSubmitActions(message.reviewPayload).length || resolveReviewEditAction(message.reviewPayload) || message.draftPayload?.claim_no"
|
||||
v-if="resolveReviewFooterActions(message.reviewPayload).length"
|
||||
class="review-footer-actions"
|
||||
>
|
||||
<div class="review-footer-btn-row">
|
||||
<button
|
||||
v-for="action in resolveReviewSubmitActions(message.reviewPayload)"
|
||||
v-for="action in resolveReviewFooterActions(message.reviewPayload)"
|
||||
:key="`${message.id}-${action.action_type}`"
|
||||
type="button"
|
||||
:class="['review-footer-btn', action.emphasis === 'primary' ? 'primary' : '']"
|
||||
@@ -378,26 +344,6 @@
|
||||
>
|
||||
{{ action.label || buildReviewPrimaryButtonLabel(message.reviewPayload, message.draftPayload) }}
|
||||
</button>
|
||||
|
||||
<button
|
||||
v-if="resolveReviewEditAction(message.reviewPayload)"
|
||||
type="button"
|
||||
:class="['review-footer-btn', resolveReviewEditAction(message.reviewPayload)?.emphasis === 'primary' ? 'primary' : '']"
|
||||
:disabled="submitting || reviewActionBusy || sessionSwitchBusy"
|
||||
@click="handleReviewAction(message, resolveReviewEditAction(message.reviewPayload))"
|
||||
>
|
||||
{{ resolveReviewEditAction(message.reviewPayload)?.label || '修改识别信息' }}
|
||||
</button>
|
||||
|
||||
<button
|
||||
v-if="shouldShowReviewUploadButton(message.reviewPayload)"
|
||||
type="button"
|
||||
class="review-footer-btn"
|
||||
:disabled="submitting || reviewActionBusy"
|
||||
@click="triggerFileUpload(message.reviewPayload.document_cards?.length ? 'composer-continue' : 'composer')"
|
||||
>
|
||||
{{ message.reviewPayload.document_cards?.length ? '继续上传票据' : '上传票据' }}
|
||||
</button>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
@@ -1328,22 +1274,6 @@
|
||||
@confirm="confirmDeleteCurrentSession"
|
||||
/>
|
||||
|
||||
<ConfirmDialog
|
||||
:open="reviewCancelDialogOpen"
|
||||
badge="取消核对"
|
||||
badge-tone="warning"
|
||||
title="确认放弃本次识别结果?"
|
||||
description="关闭后将退出当前核对窗口,本次尚未确认的修改不会继续保留。"
|
||||
cancel-text="返回继续核对"
|
||||
confirm-text="确认取消"
|
||||
busy-text="处理中..."
|
||||
confirm-tone="danger"
|
||||
confirm-icon="mdi mdi-close-circle-outline"
|
||||
:busy="reviewActionBusy"
|
||||
@close="closeCancelReviewDialog"
|
||||
@confirm="confirmCancelReview"
|
||||
/>
|
||||
|
||||
<Transition name="assistant-modal">
|
||||
<div v-if="uploadDecisionDialogOpen" class="assistant-overlay review-overlay">
|
||||
<section class="review-confirm-modal review-upload-decision-modal">
|
||||
@@ -1404,57 +1334,12 @@
|
||||
</div>
|
||||
</Transition>
|
||||
|
||||
<Transition name="assistant-modal">
|
||||
<div v-if="reviewEditDialogOpen" class="assistant-overlay review-overlay">
|
||||
<section class="review-edit-modal">
|
||||
<header class="review-edit-head">
|
||||
<div>
|
||||
<span class="assistant-badge">修改识别信息</span>
|
||||
<h3>请按当前识别结果逐项修改</h3>
|
||||
<p>修改会先保存到右侧核对信息,提交下一步时再进行 AI 预审。</p>
|
||||
</div>
|
||||
<button class="close-btn" type="button" aria-label="关闭修改面板" :disabled="reviewActionBusy" @click="closeEditReviewDialog">
|
||||
<i class="mdi mdi-close"></i>
|
||||
</button>
|
||||
</header>
|
||||
|
||||
<div class="review-edit-form">
|
||||
<label
|
||||
v-for="item in reviewEditFields"
|
||||
:key="item.key"
|
||||
class="review-edit-field"
|
||||
:class="item.group"
|
||||
>
|
||||
<span>{{ item.label }}<em v-if="item.required">*</em></span>
|
||||
<textarea
|
||||
v-if="item.field_type === 'textarea'"
|
||||
v-model="item.value"
|
||||
rows="3"
|
||||
:placeholder="item.placeholder"
|
||||
:disabled="reviewActionBusy"
|
||||
></textarea>
|
||||
<input
|
||||
v-else
|
||||
v-model="item.value"
|
||||
type="text"
|
||||
:placeholder="item.placeholder"
|
||||
:disabled="reviewActionBusy"
|
||||
/>
|
||||
</label>
|
||||
</div>
|
||||
|
||||
<div class="review-edit-actions">
|
||||
<button type="button" class="secondary-dialog-btn" :disabled="reviewActionBusy" @click="closeEditReviewDialog">取消</button>
|
||||
<button type="button" class="primary-dialog-btn" :disabled="reviewActionBusy" @click="applyEditedReview">
|
||||
{{ reviewActionBusy ? '保存中...' : '确认修改' }}
|
||||
</button>
|
||||
</div>
|
||||
</section>
|
||||
</div>
|
||||
</Transition>
|
||||
</Teleport>
|
||||
</template>
|
||||
|
||||
<script src="./scripts/TravelReimbursementCreateView.js"></script>
|
||||
|
||||
<style scoped src="../assets/styles/views/travel-reimbursement-create-view.css"></style>
|
||||
<style scoped src="../assets/styles/views/travel-reimbursement-create-view-part2.css"></style>
|
||||
<style scoped src="../assets/styles/views/travel-reimbursement-create-view-part3.css"></style>
|
||||
<style scoped src="../assets/styles/views/travel-reimbursement-create-view-part4.css"></style>
|
||||
|
||||
Reference in New Issue
Block a user