调研表历史日志预览
continuous-integration/drone/push Build is passing Details

uat_us^2
wangxiaoshuang 2026-08-12 14:28:19 +08:00
parent 0bbb93d663
commit 967688e94e
5 changed files with 197 additions and 181 deletions

View File

@ -228,6 +228,12 @@ export const constantRoutes = [
component: () => import('@/views/research/form'), component: () => import('@/views/research/form'),
hidden: true hidden: true
}, },
{
path: '/researchLog',
name: 'researchLog',
component: () => import('@/views/research/form'),
hidden: true
},
{ {
path: '/researchLogin_m', path: '/researchLogin_m',
name: 'researchLogin_m', name: 'researchLogin_m',

View File

@ -1,2 +1,2 @@
const WHITELIST = ['/', "/curriculumVitae", 'researchDetail_m', '/researchForm', '/ReviewersResearch', '/login', '/link_expired', '/error', '/resetpassword', '/recompose', '/email-recompose', '/trialStats', '/showdicom', '/imagesShare', '/audit', '/preview', '/researchLogin', '/researchLogin_m', '/blindResumeInfo', '/trialsResume', '/joinVerify', '/showNoneDicoms', '/noneDicomReading', '/clinicalData', '/readingDicoms', '/readingPage', '/visitDicomReview', '/visitNondicomReview', '/globalReview', '/adReview', '/oncologyReview', '/nonedicoms', '/ecrfList'] const WHITELIST = ['/', "/curriculumVitae", 'researchDetail_m', '/researchForm', '/ReviewersResearch', '/login', '/link_expired', '/error', '/resetpassword', '/recompose', '/email-recompose', '/trialStats', '/showdicom', '/imagesShare', '/audit', '/preview', '/researchLogin', '/researchLogin_m', '/blindResumeInfo', '/trialsResume', '/joinVerify', '/showNoneDicoms', '/noneDicomReading', '/clinicalData', '/readingDicoms', '/readingPage', '/visitDicomReview', '/visitNondicomReview', '/globalReview', '/adReview', '/oncologyReview', '/nonedicoms', '/ecrfList', '/researchLog']
export default WHITELIST export default WHITELIST

View File

@ -1,65 +1,29 @@
<template> <template>
<div class="log-list"> <div class="log-list">
<el-table <el-table v-loading="loading" :data="tableData" v-adaptive="{ bottomOffset: 40 }" height="100" style="width: 100%">
v-loading="loading" <el-table-column prop="CreateTime" :label="时间" min-width="120" show-overflow-tooltip>
:data="tableData"
v-adaptive="{ bottomOffset: 40 }"
height="100"
style="width: 100%"
>
<el-table-column
prop="CreateTime"
label="时间"
min-width="120"
show-overflow-tooltip
>
<template slot-scope="scope"> <template slot-scope="scope">
{{ scope.row.CreateTime ? moment(scope.row.CreateTime).format('YYYY-MM-DD HH:MM:SS') : '' }} {{ scope.row.CreateTime ? moment(scope.row.CreateTime).format('YYYY-MM-DD HH:MM:SS') : '' }}
</template> </template>
</el-table-column> </el-table-column>
<el-table-column <el-table-column prop="Name" label="姓名" min-width="100" show-overflow-tooltip>
prop="Name"
label="姓名"
min-width="100"
show-overflow-tooltip
>
</el-table-column> </el-table-column>
<el-table-column <el-table-column prop="UserType" label="角色" min-width="100" show-overflow-tooltip>
prop="UserType"
label="角色"
min-width="100"
show-overflow-tooltip
>
<template slot-scope="scope"> <template slot-scope="scope">
{{ $fd('UserType', scope.row.IsJoin) }} {{ $fd('UserType', scope.row.IsJoin) }}
</template> </template>
</el-table-column> </el-table-column>
<el-table-column <el-table-column prop="OptType" label="操作" min-width="100" show-overflow-tooltip>
prop="OptType"
label="操作"
min-width="100"
show-overflow-tooltip
>
<template slot-scope="scope"> <template slot-scope="scope">
{{ $fd('SiteSurveyOptTyp', scope.row.IsJoin) }} {{ $fd('SiteSurveyOptTyp', scope.row.IsJoin) }}
</template> </template>
</el-table-column> </el-table-column>
<el-table-column <el-table-column prop="Json" label="详情" min-width="100" show-overflow-tooltip>
prop="Json"
label="详情"
min-width="100"
show-overflow-tooltip
>
<template slot-scope="scope"> <template slot-scope="scope">
<el-button v-if="scope.row.Json" type="text"></el-button> <el-button v-if="scope.row.Json" type="text" @click="openLog(scope.row)"></el-button>
</template> </template>
</el-table-column> </el-table-column>
<el-table-column <el-table-column prop="Reason" label="备注" min-width="140" show-overflow-tooltip>
prop="Reason"
label="备注"
min-width="140"
show-overflow-tooltip
>
</el-table-column> </el-table-column>
</el-table> </el-table>
</div> </div>
@ -67,6 +31,7 @@
<script> <script>
import { getSiteSurveyLogList } from '@/api/research' import { getSiteSurveyLogList } from '@/api/research'
import moment from 'moment' import moment from 'moment'
import { getToken } from '@/utils/auth'
export default { export default {
name: 'LogList', name: 'LogList',
props: { props: {
@ -79,7 +44,8 @@ export default {
return { return {
loading: false, loading: false,
tableData: [], tableData: [],
moment moment,
openWindow: null
} }
}, },
mounted() { mounted() {
@ -93,11 +59,20 @@ export default {
if (res.IsSuccess) { if (res.IsSuccess) {
this.tableData = res.Result this.tableData = res.Result
} }
} catch(e) { } catch (e) {
console.log(e) console.log(e)
} finally { } finally {
this.loading = false this.loading = false
} }
},
openLog(row) {
if (this.openWindow) {
this.openWindow.close()
}
var token = getToken()
var path = `/researchLog?trialId=${this.$route.query.trialId}&trialSiteSurveyId=${this.trialSiteSurveyId}&logId=${row.Id}&TokenKey=${token}`
this.openWindow = window.open(path, '_blank')
} }
} }
} }

View File

@ -36,7 +36,7 @@
{{ $t('trials:researchForm:button:historicalRecord') }} {{ $t('trials:researchForm:button:historicalRecord') }}
</el-button> </el-button>
<!-- 操作日志 --> <!-- 操作日志 -->
<el-button type="primary" size="small" @click="viewLog"> <el-button type="primary" size="small" v-if="!isLog" @click="viewLog">
{{ $t('trials:researchForm:button:log') }} {{ $t('trials:researchForm:button:log') }}
</el-button> </el-button>
<!-- 退出 --> <!-- 退出 -->
@ -166,8 +166,8 @@
</div> </div>
</template> </template>
<script> <script>
import { getSiteSurveyInfo, trialSurveySubmit, submissionRejection } from '@/api/research' import { getSiteSurveyInfo, trialSurveySubmit, submissionRejection, getSiteSurveyLogList } from '@/api/research'
import { getQueryString } from '@/utils/history.js' import { getQueryString, changeURLStatic } from '@/utils/history.js'
import BaseInfo from './components/BaseInfo' import BaseInfo from './components/BaseInfo'
import HistoricalParticipant from './components/HistoricalParticipant' import HistoricalParticipant from './components/HistoricalParticipant'
import ParticipantList from './components/ParticipantList' import ParticipantList from './components/ParticipantList'
@ -176,6 +176,7 @@ import { mapMutations } from 'vuex'
import TopLang from './topLang' import TopLang from './topLang'
import HistoricalRecord from './components/HistoricalRecord' import HistoricalRecord from './components/HistoricalRecord'
import LogList from './components/LogList' import LogList from './components/LogList'
import store from '@/store'
export default { export default {
name: 'QuestionForm', name: 'QuestionForm',
components: { BaseInfo, HistoricalParticipant, ParticipantList, EquipmentList, TopLang, HistoricalRecord, LogList }, components: { BaseInfo, HistoricalParticipant, ParticipantList, EquipmentList, TopLang, HistoricalRecord, LogList },
@ -202,7 +203,9 @@ export default {
siteSurveyNoteInfo: {}, siteSurveyNoteInfo: {},
IsSupportUploadFile: false, IsSupportUploadFile: false,
IsOnlyUploadFile: false, IsOnlyUploadFile: false,
logVisible: false logVisible: false,
isLog: false,
logId: null
} }
}, },
mounted() { mounted() {
@ -218,6 +221,12 @@ export default {
this.setLanguage(lang) this.setLanguage(lang)
this.$updateDictionary() this.$updateDictionary()
this.trialSiteSurveyId = getQueryString('trialSiteSurveyId') this.trialSiteSurveyId = getQueryString('trialSiteSurveyId')
this.logId = getQueryString('logId')
if (this.logId) this.isLog = true
if (this.$router.currentRoute.query.TokenKey) {
store.dispatch('user/setToken', this.$router.currentRoute.query.TokenKey)
changeURLStatic('TokenKey', '')
}
this.initPage() this.initPage()
if (zzSessionStorage.getItem('userTypeEnumInt')) { if (zzSessionStorage.getItem('userTypeEnumInt')) {
this.userTypeEnumInt = zzSessionStorage.getItem('userTypeEnumInt') * 1 this.userTypeEnumInt = zzSessionStorage.getItem('userTypeEnumInt') * 1
@ -233,6 +242,43 @@ export default {
// //
initPage() { initPage() {
this.loading = true this.loading = true
if (this.isLog) {
getSiteSurveyLogList({ trialSiteSurveyId: this.trialSiteSurveyId, Id: this.logId }).then(r => {
if (r.Result && r.Result[0].Json) {
let res = {
Result: JSON.parse(r.Result[0].Json)
}
if (res.Result) {
// this.trialSiteSurveyEquipmentType = res.Result.TrialInfo.TrialSiteSurveyEquipmentType
// this.trialSiteSurveyUserRoles = res.Result.TrialInfo.TrialSiteSurveyUserRoles
if (res.Result.SiteSurveyFiledConfig && res.Result.SiteSurveyFiledConfig.ModifyFiledList.length > 0) {
this.siteSurveyNoteInfo = res.Result.SiteSurveyFiledConfig.ModifyFiledList.find(i => i.NeedModifyFiled === 'SiteSurveyNote')
}
this.IsSupportUploadFile = res.Result.SiteSurveyFiledConfig.IsSupportUploadFile
this.IsOnlyUploadFile = res.Result.SiteSurveyFiledConfig.IsOnlyUploadFile
this.siteSurveyNoteInfo.IsCloseEquipmentSurvey = res.Result.SiteSurveyFiledConfig.IsCloseEquipmentSurvey
this.state = 3
this.siteId = res.Result.TrialSiteSurvey.TrialSiteId
this.$refs['baseResearchInfo'].initForm(res.Result.TrialInfo, res.Result.TrialSiteSurvey, res.Result.SiteSurveyFiledConfig ? res.Result.SiteSurveyFiledConfig.NotShowFieldList : null)
var historicalArr = []
var newArr = []
res.Result.TrialSiteUserSurveyList.map(i => {
if (i.IsHistoryUser) {
historicalArr.push(i)
} else {
newArr.push(i)
}
})
this.$refs['historicalParticipant'].initList(historicalArr, res.Result.TrialSiteSurvey)
this.$refs['researchParticipants'].initList(newArr, res.Result.TrialSiteSurvey)
this.$refs['researchEquipments'].initList(res.Result.TrialSiteEquipmentSurveyList, res.Result.TrialSiteSurvey, res.Result.SiteSurveyFiledConfig.EquipmentControlFieldList)
this.isExistIncorrect = res.Result.TrialSiteUserSurveyList.every(item => item.IsCorrect === false)
}
this.loading = false
}
}).catch((err) => { console.log(err); this.loading = false })
} else {
getSiteSurveyInfo(this.trialId, this.trialSiteSurveyId).then(res => { getSiteSurveyInfo(this.trialId, this.trialSiteSurveyId).then(res => {
if (res.Result) { if (res.Result) {
// this.trialSiteSurveyEquipmentType = res.Result.TrialInfo.TrialSiteSurveyEquipmentType // this.trialSiteSurveyEquipmentType = res.Result.TrialInfo.TrialSiteSurveyEquipmentType
@ -263,6 +309,8 @@ export default {
} }
this.loading = false this.loading = false
}).catch(() => { this.loading = false }) }).catch(() => { this.loading = false })
}
}, },
// //
handleSubmit(type) { handleSubmit(type) {

View File

@ -1,39 +1,22 @@
<template> <template>
<BaseContainer> <BaseContainer>
<div class="step-wrapper"> <div class="step-wrapper">
<el-steps <el-steps :active="activeStatus" align-center :space="300">
:active="activeStatus"
align-center
:space="300"
>
<!-- 中心填写 --> <!-- 中心填写 -->
<el-step <el-step :title="$t('trials:siteResearch:timeline:step1')" class="click_cursor"
:title="$t('trials:siteResearch:timeline:step1')" @click.native="handleClick(0)" />
class="click_cursor"
@click.native="handleClick(0)"
/>
<!-- SPM审核 --> <!-- SPM审核 -->
<el-step <el-step v-if="isSPMJoin" :title="$t('trials:siteResearch:timeline:step2')" class="click_cursor"
v-show="isSPMJoin" @click.native="handleClick(1)" />
:title="$t('trials:siteResearch:timeline:step2')"
class="click_cursor"
@click.native="handleClick(1)"
/>
<!-- PM审核 --> <!-- PM审核 -->
<el-step <el-step :title="$t('trials:siteResearch:timeline:step3')" class="click_cursor"
:title="$t('trials:siteResearch:timeline:step3')" @click.native="handleClick(2)" />
class="click_cursor"
@click.native="handleClick(2)"
/>
<!-- 审核完毕 --> <!-- 审核完毕 -->
<el-step <el-step :title="$t('trials:siteResearch:timeline:step14')" class="click_cursor"
:title="$t('trials:siteResearch:timeline:step14')" @click.native="handleClick(3)" />
class="click_cursor"
@click.native="handleClick(3)"
/>
</el-steps> </el-steps>
<div class="step-content"> <div class="step-content">
<ResearchList ref="researchList"/> <ResearchList ref="researchList" />
</div> </div>
</div> </div>
</BaseContainer> </BaseContainer>
@ -59,7 +42,7 @@ export default {
deep: true, deep: true,
immediate: true, immediate: true,
handler(v) { handler(v) {
this.$nextTick(() =>{ this.$nextTick(() => {
this.$refs['researchList'].searchData.State = v this.$refs['researchList'].searchData.State = v
this.$refs['researchList'].getList() this.$refs['researchList'].getList()
}) })
@ -69,15 +52,17 @@ export default {
}, },
mounted() { mounted() {
this.getTrialIsSPMJoin() this.getTrialIsSPMJoin()
if (this.hasPermi(['role:pm'])) this.activeStatus = 2
if (this.hasPermi(['role:spm'])) this.activeStatus = 1
}, },
methods: { methods: {
async getTrialIsSPMJoin() { async getTrialIsSPMJoin() {
try { try {
let trialId = this.$route.query.trialId let trialId = this.$route.query.trialId
if (!trialId) return if (!trialId) return
let res = await getTrialIsSPMJoin( trialId ) let res = await getTrialIsSPMJoin(trialId)
this.isSPMJoin = res.Result this.isSPMJoin = res.Result
} catch(e) { } catch (e) {
console.log(e) console.log(e)
} }
@ -90,7 +75,7 @@ export default {
} }
</script> </script>
<style lang="scss" scoped> <style lang="scss" scoped>
.step-wrapper { .step-wrapper {
height: 100%; height: 100%;
flex: 1; flex: 1;
display: flex; display: flex;
@ -98,53 +83,55 @@ export default {
padding: 0; padding: 0;
margin: 0; margin: 0;
background-color: #fff; background-color: #fff;
} }
.el-steps {
.el-steps {
height: 80px; height: 80px;
justify-content: center; justify-content: center;
} }
.step-content {
flex: 1;
}
// .underline {
// // .el-step__title {
// // text-decoration: underline
// // }
// .el-step__title,
// .el-step__title.is-process,
// .el-step__title.is-finish {
// text-decoration: underline;
// }
// }
// .noneUnderline {
// .el-step__title {
// text-decoration: none;
// }
// }
// .el-step__head.is-process,
// .el-step__title.is-process,
// .el-step__description.is-process {
// color: #428bca;
// border-color: #428bca;
// }
// .el-step__head.is-process .el-step__line {
// background-color: #428bca;
// }
// .el-step__head.is-finish,
// .el-step__title.is-finish,
// .el-step__description.is-finish {
// color: #303133;
// border-color: #303133;
// }
// .el-step__title.is-process,
// .el-step__title.is-finish {
// text-decoration: none;
// }
// .el-step__head.is-finish .el-step__line {
// background-color: #303133;
// }
.click_cursor {
cursor: pointer;
}
.step-content {
flex: 1;
}
// .underline {
// // .el-step__title {
// // text-decoration: underline
// // }
// .el-step__title,
// .el-step__title.is-process,
// .el-step__title.is-finish {
// text-decoration: underline;
// }
// }
// .noneUnderline {
// .el-step__title {
// text-decoration: none;
// }
// }
// .el-step__head.is-process,
// .el-step__title.is-process,
// .el-step__description.is-process {
// color: #428bca;
// border-color: #428bca;
// }
// .el-step__head.is-process .el-step__line {
// background-color: #428bca;
// }
// .el-step__head.is-finish,
// .el-step__title.is-finish,
// .el-step__description.is-finish {
// color: #303133;
// border-color: #303133;
// }
// .el-step__title.is-process,
// .el-step__title.is-finish {
// text-decoration: none;
// }
// .el-step__head.is-finish .el-step__line {
// background-color: #303133;
// }
.click_cursor {
cursor: pointer;
}
</style> </style>