You can not select more than 25 topics Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.

266 lines
9.6 KiB

3 years ago
2 years ago
3 years ago
3 years ago
3 years ago
2 years ago
3 years ago
2 years ago
3 years ago
2 years ago
3 years ago
2 years ago
3 years ago
2 years ago
3 years ago
2 years ago
3 years ago
2 years ago
3 years ago
2 years ago
3 years ago
2 years ago
3 years ago
2 years ago
3 years ago
2 years ago
3 years ago
2 years ago
3 years ago
2 years ago
3 years ago
2 years ago
3 years ago
2 years ago
3 years ago
3 years ago
2 years ago
3 years ago
2 years ago
3 years ago
3 years ago
2 years ago
3 years ago
2 years ago
3 years ago
3 years ago
2 years ago
3 years ago
3 years ago
2 years ago
3 years ago
3 years ago
2 years ago
3 years ago
3 years ago
3 years ago
2 years ago
3 years ago
3 years ago
2 years ago
2 years ago
3 years ago
2 years ago
3 years ago
3 years ago
3 years ago
3 years ago
3 years ago
3 years ago
3 years ago
3 years ago
3 years ago
3 years ago
3 years ago
3 years ago
3 years ago
3 years ago
3 years ago
3 years ago
3 years ago
3 years ago
3 years ago
2 years ago
3 years ago
2 years ago
3 years ago
3 years ago
3 years ago
3 years ago
2 years ago
3 years ago
3 years ago
3 years ago
2 years ago
3 years ago
3 years ago
3 years ago
3 years ago
3 years ago
3 years ago
3 years ago
3 years ago
3 years ago
3 years ago
3 years ago
2 years ago
3 years ago
3 years ago
3 years ago
3 years ago
3 years ago
2 years ago
3 years ago
3 years ago
2 years ago
3 years ago
3 years ago
2 years ago
3 years ago
2 years ago
3 years ago
3 years ago
2 years ago
3 years ago
3 years ago
3 years ago
3 years ago
3 years ago
3 years ago
2 years ago
3 years ago
2 years ago
3 years ago
3 years ago
2 years ago
3 years ago
2 years ago
  1. <template>
  2. <section class="padding">
  3. <el-row :class="{'row-box':true,'cfg':isRptCfg}">
  4. <div class="rpt-title">{{ rawDatas.name }}</div>
  5. <el-input class="input" v-model="rawDatas.name" placeholder="计划名称"/>
  6. </el-row>
  7. <el-row :class="{'row-box':true,'cfg':isRptCfg}">
  8. <div class="title">{{ title?title:'报告概览' }}</div>
  9. <el-input class="input" v-model="title" placeholder="报告概览"/>
  10. </el-row>
  11. <el-row ref="table">
  12. <el-row class="box">
  13. <el-col :span="6" class="box-red">
  14. <div class="box-info">
  15. <div class="num">{{rawDatas.totalCases?rawDatas.totalCases:'0'}}</div>
  16. <div class="label">用例数</div>
  17. </div>
  18. </el-col>
  19. <el-col :span="6" class="box-blue">
  20. <div class="box-info">
  21. <div class="num">{{caseFuGaiLv}}%</div>
  22. <div class="label">用例覆盖率</div>
  23. </div>
  24. </el-col>
  25. <el-col :span="6" class="box-green">
  26. <div class="box-info">
  27. <div class="num">{{caseTongGuoLv}}%</div>
  28. <div class="label">用例通过率</div>
  29. </div>
  30. </el-col>
  31. <el-col :span="6" class="box-orange">
  32. <div class="box-info">
  33. <div class="num">{{rawDatas.bugCnt?rawDatas.bugCnt:0}}</div>
  34. <div class="label">缺陷数</div>
  35. </div>
  36. </el-col>
  37. </el-row>
  38. <!--编辑界面 XmTestPlan 测试计划-->
  39. <el-form :model="rawDatas" label-width="120px" :rules="rawDatasRules" ref="rawDatasRef" label-position="left">
  40. <el-row class="padding">
  41. <el-col :span="8">
  42. <mdp-select-user show-style="x" size="medium" label="负责人" v-model="rawDatas.cuserid" :init-name="rawDatas.cusername"></mdp-select-user>
  43. </el-col>
  44. <el-col :span="8">
  45. <mdp-select show-style="x" size="medium" label="状态" item-code="testPlanStatus" v-model="rawDatas.status"></mdp-select>
  46. </el-col>
  47. <el-col :span="8">
  48. <mdp-select show-style="x" size="medium" label="测试结果" item-code="testPlanTcode" v-model="rawDatas.tcode"></mdp-select>
  49. </el-col>
  50. </el-row>
  51. <el-form-item label="归属测试库" prop="casedbName">
  52. {{rawDatas.casedbName}}
  53. </el-form-item>
  54. <el-form-item label="归属项目" prop="projectId">
  55. <span v-if="opType=='add'">
  56. <xm-project-select v-if="!selProject || !selProject.id" ref="xmProjectSelect" :link-product-id="xmTestCasedb? xmTestCasedb.productId:null" @row-click="onPorjectConfirm" :auto-select="false">
  57. <span slot="title">选择项目</span>
  58. </xm-project-select>
  59. <div v-else>{{rawDatas.projectName}}</div>
  60. </span>
  61. <div v-else>{{rawDatas.projectName}}</div>
  62. </el-form-item>
  63. <el-form-item label="归属产品" prop="productName">
  64. {{rawDatas.productName}}
  65. </el-form-item>
  66. <el-form-item label="起止时间" prop="stime">
  67. <mdp-date-range :auto-default="false" placeholder="选择日期" v-model="rawDatas" start-key="stime" end-key="etime" value-format="yyyy-MM-dd HH:mm:ss" format="yyyy-MM-dd" ></mdp-date-range>
  68. </el-form-item>
  69. </el-form>
  70. </el-row>
  71. <el-row class="padding-bottom">
  72. <span>报告总结</span>
  73. </el-row>
  74. <el-row>
  75. <el-input type="textarea" :rows="8" v-model="rawDatas.summaryRemark"></el-input>
  76. </el-row>
  77. <el-row v-if="rawDatas.summaryRemark!==rawDatasBak.summaryRemark" >
  78. <span style="float:right;">
  79. <el-button type="primary" @click.native="editSomeFields(rawDatas,'summaryRemark',rawDatas.summaryRemark)">提交</el-button>
  80. </span>
  81. </el-row>
  82. </section>
  83. </template>
  84. <script>
  85. import util from '@/common/js/util';//全局公共库
  86. import config from "@/common/config"; //全局公共库import
  87. import { initDicts, addXmTestPlan,editXmTestPlan,editSomeFieldsXmTestPlan } from '@/api/xm/core/xmTestPlan';
  88. import { mapGetters } from 'vuex'
  89. import XmProjectSelect from '@/views/xm/core/components/XmProjectSelect';
  90. export default {
  91. name:'xmTestPlanEdit',
  92. components: {
  93. XmProjectSelect,
  94. },
  95. computed: {
  96. ...mapGetters([ 'userInfo' ]),
  97. caseFuGaiLv(){
  98. if(!this.rawDatas.totalCases){
  99. return 0
  100. }
  101. var okCases=parseInt(this.rawDatas.okCases>0?this.rawDatas.okCases:0)
  102. var errCases=parseInt(this.rawDatas.errCases>0?this.rawDatas.errCases:0)
  103. var igCases=parseInt(this.rawDatas.igCases>0?this.rawDatas.igCases:0)
  104. var blCases=parseInt(this.rawDatas.blCases>0?this.rawDatas.blCases:0)
  105. var totalExecs=okCases+errCases+igCases+blCases
  106. var rate=parseInt(totalExecs/this.rawDatas.totalCases*100)
  107. return rate;
  108. },
  109. caseTongGuoLv(){
  110. if(!this.rawDatas.totalCases){
  111. return 0
  112. }
  113. var okCases=parseInt(this.rawDatas.okCases>0?this.rawDatas.okCases:0)
  114. var errCases=parseInt(this.rawDatas.errCases>0?this.rawDatas.errCases:0)
  115. var igCases=parseInt(this.rawDatas.igCases>0?this.rawDatas.igCases:0)
  116. var blCases=parseInt(this.rawDatas.blCases>0?this.rawDatas.blCases:0)
  117. var totalExecs=okCases+igCases
  118. var rate=parseInt(totalExecs/this.rawDatas.totalCases*100)
  119. return rate;
  120. }
  121. },
  122. props:['xmTestPlan','visible','opType','selProject','xmTestCasedb','rptDatas','isRptCfg'],
  123. watch: {
  124. 'xmTestPlan':function( xmTestPlan ) {
  125. if(xmTestPlan){
  126. this.rawDatas = {...xmTestPlan};
  127. }
  128. },
  129. 'visible':function(visible) {
  130. if(visible==true){
  131. this.initData()
  132. }
  133. }
  134. },
  135. data() {
  136. return {
  137. title:'',
  138. remark:'',
  139. currOpType:'add',//add/edit
  140. load:{ list: false, edit: false, del: false, add: false },//查询中...
  141. dicts:{
  142. testPlanStatus:[],
  143. testPlanTcode:[],
  144. },//下拉选择框的所有静态数据 params={categoryId:'all',itemCodes:['sex']} 返回结果 {sex: [{id:'1',name:'男'},{id:'2',name:'女'}]}
  145. rawDatasRules: {
  146. },
  147. rawDatas: {
  148. id:'',name:'',casedbId:'',casedbName:'',projectId:'',projectName:'',cuserid:'',cusername:'',ctime:'',stime:'',etime:'',status:'',tcode:'',totalCases:'',okCases:'',errCases:'',igCases:'',blCases:'',productId:'',productName:'',flowState:'',summaryRemark:''
  149. },
  150. rawDatasBak: {
  151. id:'',name:'',casedbId:'',casedbName:'',projectId:'',projectName:'',cuserid:'',cusername:'',ctime:'',stime:'',etime:'',status:'',tcode:'',totalCases:'',okCases:'',errCases:'',igCases:'',blCases:'',productId:'',productName:'',flowState:'',summaryRemark:''
  152. },
  153. maxTableHeight:300,
  154. summaryRemarkEditVisible:false,
  155. }//end return
  156. },//end data
  157. methods: {
  158. ...util,
  159. // 取消按钮点击 父组件监听@cancel="rawDatasVisible=false" 监听
  160. handleCancel:function(){
  161. this.$refs['rawDatasRef'].resetFields();
  162. this.$emit('cancel');
  163. },
  164. //新增、编辑提交XmTestPlan 测试计划父组件监听@submit="afterEditSubmit"
  165. saveSubmit: function () {
  166. this.$refs.rawDatasRef.validate((valid) => {
  167. if (valid) {
  168. this.$confirm('确认提交吗?', '提示', {}).then(() => {
  169. this.load.edit=true
  170. let params = Object.assign({}, this.rawDatas);
  171. var func=addXmTestPlan
  172. if(this.currOpType=='edit'){
  173. func=editXmTestPlan
  174. }
  175. func(params).then((res) => {
  176. this.load.edit=false
  177. var tips=res.data.tips;
  178. if(tips.isOk){
  179. this.rawDatas=res.data.data
  180. this.initData()
  181. this.currOpType="edit";
  182. this.$emit('submit');// @submit="afterAddSubmit"
  183. }
  184. this.$notify({ position:'bottom-left',showClose:true, message: tips.msg, type: tips.isOk?'success':'error' });
  185. }).catch( err =>this.load.edit=false);
  186. });
  187. }else{
  188. this.$notify({ showClose:true, message: "表单验证不通过,请修改表单数据再提交", type: 'error' });
  189. }
  190. });
  191. },
  192. initData: function(){
  193. if(this.xmTestPlan){
  194. this.rawDatas = Object.assign({},this.xmTestPlan);
  195. }
  196. if(this.rptDatas){
  197. this.rawDatas=Object.assign({},this.rptDatas)
  198. }
  199. this.rawDatasBak={...this.rawDatas}
  200. },
  201. editSomeFields(row,fieldName,$event){
  202. if(this.opType=='add'){
  203. return;
  204. }
  205. let params={};
  206. params['ids']=[row].map(i=>i.id)
  207. if(fieldName=='stime'){
  208. params[fieldName]=$event.stime
  209. params.etime=$event.etime
  210. }else if(fieldName=='cuserid'){
  211. params[fieldName]=$event.userid
  212. params.cusername=$event.username
  213. }else{
  214. params[fieldName]=$event
  215. }
  216. var func = editSomeFieldsXmTestPlan
  217. func(params).then(res=>{
  218. let tips = res.data.tips;
  219. if(tips.isOk){
  220. this.rawDatasBak=[...this.rawDatas]
  221. this.$emit('edit-fields',params)
  222. }else{
  223. Object.assign(this.rawDatas,this.rawDatasBak)
  224. this.$notify({position:'bottom-left',showClose:true,message:tips.msg,type:tips.isOk?'success':'error'})
  225. }
  226. }).catch((e)=>Object.assign(this.rawDatas,this.rawDatasBak))
  227. },
  228. onPorjectConfirm(row){
  229. this.rawDatas.projectId=row.id
  230. this.rawDatas.projectName=row.name
  231. this.rawDatas.name=this.rawDatas.projectName+'-测试计划-V1.0'
  232. },
  233. sizeAutoChange(){
  234. }
  235. },//end method
  236. mounted() {
  237. this.$nextTick(() => {
  238. initDicts(this);
  239. this.initData()
  240. this.maxTableHeight = util.calcTableMaxHeight(this.$refs.table.$el)
  241. });
  242. }
  243. }
  244. </script>
  245. <style lang="scss" scoped>
  246. @import url('../index/overview.scss');
  247. </style>