Bladeren bron

撤销+考勤记录

zhengkaixin 4 jaren geleden
bovenliggende
commit
86f9d38f11

+ 14 - 3
src/components/ExamineDetail.vue

@@ -1,5 +1,6 @@
 <template>
 		<div>
+			<loading :visible="isLoading"></loading>
 			
 				
 			<div class="mui-content-padded" v-if="examineDetail.examineList">
@@ -82,23 +83,30 @@
 
 				</template>
 				</div> 
+			
 		</div>
 </template>
 
 <script>
 		import * as API_sp from '@/apis-xsy/xsy'
+	import Loading from '$project/components/Loading.vue'
 
 	export default {
-		
+	
 		name: 'examineDetail',
 		data() {
 			return {
-		
+				isLoading:false,
 				examineDetail: {},
 				only: "test"
 
 			}
 		},
+		components: {
+		
+			Loading,
+		
+		},
 		props: {
 			id: {
 				require: true,
@@ -106,6 +114,7 @@
 			},
 		},
 		methods: {
+			
 			getClass(ac, i) {
 				var reclass = ""
 				
@@ -134,7 +143,9 @@
 			getExamineDetail() {
 				API_sp.examineDetail(this.id).then(response => {
 					this.examineDetail = response
-
+					
+					this.$emit('getOwnerSubmit', response.ownerSubmit);
+					
 					this.$emit('allowExamine', response.procinstActUserId);
 				}).catch(error => {
 

+ 14 - 0
src/projects/business/apis-xsy/xsy.js

@@ -21,6 +21,20 @@ export function examineDetail(id) {
 	return request({
 		url: '/mobile/adjustShiftApi/examineDetail',
 	
+		data: Qs.stringify(params),
+		method: 'post',
+	})
+}
+
+
+//根据id查询审核详情
+export function revoke(id) {
+	var 	params= {
+			id:id
+		}
+	return request({
+		url: '/mobile/adjustShiftApi/revoke',
+	
 		data: Qs.stringify(params),
 		method: 'post',
 	})

+ 10 - 0
src/projects/business/apis/Master/attendance.js

@@ -1,4 +1,6 @@
 import request from '$project/utils/request'
+import request2 from '$project/utils/request2'
+
 import Qs from 'qs';
 
 /**
@@ -15,6 +17,14 @@ export function pageList(params) {
 	})
 }
 
+//获取考勤记录
+export function statistics(params) {
+	return request2({
+		url: '/mobile/workAttendance/statistics',
+		data: Qs.stringify(params),
+		method: 'post',
+	})
+}
 //获取申请补卡详情
 export function getApplyInfo(params) {
 	return request({

+ 12 - 1
src/projects/business/router/master.js

@@ -824,7 +824,18 @@ const routesMaster = [
 							form: true,
 						}
 					},
-
+					//考勤统计列表
+					{
+						path: 'statistic',
+						name: 'MasterAttendanceStatistic',
+						component: () => import('../views/Master/Attendance/Statistic.vue'),
+						meta: {
+							requireAuth: true,
+							role: [],
+							title: '考勤统计(个人)',
+							mode: true,
+						}
+					},
 					//考勤统计列表
 					{
 						path: 'statisticList',

+ 33 - 6
src/projects/business/views-xsy/Approval/Info.vue

@@ -28,9 +28,15 @@
 			 <Info2 v-if="sp&&formId=='leaveCancelWork'" @getInfo="getInfo"></Info2>
 			 
 			 
-			<examineDetail @allowExamine="allowExamine" :id="id" v-if="info.sp&&info.status!=4"></examineDetail>
+			<examineDetail  @getOwnerSubmit="getOwnerSubmit" @allowExamine="allowExamine" :id="id" v-if="info.sp&&info.status!=4"></examineDetail>
+			
+		<div class="fyy-footer" >
+			
+			<div class="bindfyy-btn" v-if="myownerSubmit">
+				<button type="button" class="mui-btn mui-btn-primary " @click="doAction">撤销</button>
+			</div>
+		</div>
 			
-			 
 		</div>
 	</div>
 </template>
@@ -77,7 +83,8 @@
 				id: '',
 				info: {},
 				examineDetail: {},
-				only: "test"
+				only: "test",
+				myownerSubmit:false,
 
 			}
 		},
@@ -85,6 +92,21 @@
 			this.id = this.$route.query.id;
 		},
 		methods: {
+			getOwnerSubmit(bl){
+				this.myownerSubmit=bl
+			},
+			doAction(){
+				this.isLoading=true;
+				this.update(false);
+				API_sp.revoke(this.id).then(response => {
+					this.update(true);
+					
+				 this.isLoading=false;
+				}).catch(error => {
+				
+					mui.toast(error);
+				})
+			},
 			getInfo(op){
 				this.info=op;
 				this.info.sp=true;
@@ -95,7 +117,13 @@
 			},
 			allowExamine(op){
 				this.isLoading=false;
-				this.$emit('allowExamine',op);
+				
+				if(this.info.status==6){
+					this.$emit('allowExamine',"");
+				}else{
+					this.$emit('allowExamine',op);
+				}
+				
 				
 			},
 			getClass(ac, i) {
@@ -123,8 +151,7 @@
 				}
 				return reclass
 			},
-			
-		
+		 
 			asynCallBack() {
 
 			},

+ 1 - 1
src/projects/business/views/Master/Attendance/LeaveList.vue

@@ -15,7 +15,7 @@
 						 
 						<button class="mui-btn   mui-btn-outlined" :class="{'mui-btn-primary':mod.status==0,
 						'mui-btn-danger':mod.status==2||mod.status==3,
-						'mui-btn-success':mod.status==1||mod.status==4}"  v-text="mod.enableCancel||mod.cancelStatus!=5?mod.mergeStatusN:status[mod.status]"  ></button>
+						'mui-btn-success':mod.status==1||mod.status==4}"  v-text="mod.enableCancel||mod.cancelStatus!=5?mod.mergeStatusN:mod.statusN"  ></button>
 							
 					</li>
 

+ 250 - 0
src/projects/business/views/Master/Attendance/Statistic.vue

@@ -0,0 +1,250 @@
+<!--workStatus:1-工作,2-外出,3-出差,4-休假-->
+<!--result:0-缺卡,1-正常,2-迟到,3-早退, 4-出差,5-请假-->
+<!--type:0=设备打卡,1=外勤打卡、2=补卡-->
+<!--status:0:无操作, 1:机器打卡记录,2:请假审批详情,3:外勤打卡、补卡审批详情-->
+
+<template>
+	<div>
+		<common @asynCallBack="asynCallBack"></common>
+		<top-header :pageTitle="pageTitle"></top-header>
+		
+		<div class="mui-content vongi-admin-kqtj">
+			<ul class="mui-table-view" style="margin-bottom: 10px;"  >
+			 					<li class="mui-table-view-cell " style="text-align: center;"  >
+			 						<span class="mui-icon mui-icon mui-icon-arrowleft" @click="optMonth(0)"></span>	{{year}}.{{(month>9?"":"0")}}{{month}}	<span class="mui-icon mui-icon mui-icon-arrowright" @click="optMonth(1)"></span>
+			 					</li>
+			</ul>
+			
+			<div class="vongi-index flew-sp flew-items" style="margin-bottom: 10px;">
+				<div class="vongi-index-top">
+					<div class="mui-media-object mui-pull-left">
+						<img :src="person_data?(person_data.faceImageUrl+'?x-oss-process=image/resize,h_50,m_lfit'):''">
+					</div>
+					<div class="mui-media-body">
+						<h3 v-if="person_data">{{person_data.name}}</h3>
+ 					</div>
+				</div>
+				<div class="vongi-index-right flew-items flew-sp">
+					
+					应出勤<a class="mui-pull-right" >{{obj.attendanceDays}}</a>天 / 实出勤<a class="mui-pull-right" >{{obj.totalAttendanceDays}}</a>天
+				</div>
+			</div>
+			
+			
+			 <ul class="mui-table-view"> 
+					
+			        <li class="mui-table-view-cell mui-collapse"  v-for="(it,index) in recordList"  >
+			            <a class="mui-navigate-right" href="#">{{it.name}}
+						<span style="float: right;  margin-right: 20px; color: rgba(136, 136, 136, 100); ">{{it.list.length}}</span></a>
+			            <div class="mui-content-padded vongi-work">
+			               
+							<ul class="mui-table-view">
+								<li v-for="(item,index) in it.list" class="mui-table-view-cell">
+									{{item.recordTime}}
+									<div class="mui-media-body">
+										<button type="button" class="mui-btn mui-btn-primary" v-if="item.result=='1' && item.status=='1'" @click="goToInfo(item.supplementWorkId)">{{item.type=='1'?'已外勤打卡':'已补卡'}}</button>
+										<button type="button" class="mui-btn mui-btn-primary" v-if="item.result=='0' && item.status=='3'" @click="goToInfo(item.supplementWorkId)">已拒绝</button>
+										<button type="button" class="mui-btn mui-btn-primary" v-if="item.result=='0' && item.status=='0'" @click="goToInfo(item.supplementWorkId)">审核中</button>
+										<button type="button" class="mui-btn mui-btn-primary" v-if="item.result=='0' && item.status===null" @click="applybk(item.id,item.recordTime)">申请补卡</button>
+										<span :style="'color:'+statusColor[item.result]" v-text="status[item.result]">缺卡</span>
+									</div>
+								</li>
+							</ul>
+			            </div>
+			        </li>
+				 
+					
+			    </ul>
+
+		</div>
+
+		<loading :visible="isLoading"></loading>
+	</div>
+</template>
+
+<script>
+	require('$project/assets/js/mui.picker.min.js');
+	import * as API_Attendance from '@/apis/Master/attendance'
+	import Common from '$project/components/Common.vue'
+	import Loading from '$project/components/Loading.vue'
+	import TopHeader from '$project/components/TopHeader.vue'
+	import isReachBottom from '$project/utils/isReachBottom'
+	import {
+		mapGetters,
+		mapMutations
+	} from 'vuex'
+	import {
+		currentTimeStamp,
+		parseUnixTime
+	} from '$project/utils'
+	export default {
+		name: 'MasterAttendanceStatistic',
+		components: {
+			Common,
+			Loading,
+			TopHeader
+		},
+		data() {
+			return {
+				pageTitle: '考勤统计',
+				year:0,
+				month:1,
+				
+				listForm:{
+					date: '2021-06',
+				},
+				isLoading: false,
+				obj:{},
+				recordList: [],
+				status: ['缺卡', '正常', '迟到', '早退', '请假','出差'],
+				statusColor: ['#fe616c', '#05c8af', '#f6f448', '#f6f448', '#f6f448', '#f6f448'],
+				
+				rightLink: {
+					show: true,
+					icon: 'icon-shijian',
+					style: 'font-size:14px;color:#000;',
+					title: '缺卡记录'
+				},
+
+			}
+		},
+		created() {
+			 this.month= new Date().getMonth()+1;
+			 this.year= new Date().getYear()+1900;
+		},
+		methods: {
+			optMonth(opt){
+				
+				if(opt){
+					if( this.month==12){
+						 this.month=1;
+						  this.year++;
+					}else{
+						 this.month++;
+					}
+				}else{
+					if( this.month==1){
+						 this.month=12;
+						  this.year--;
+					}else{
+						 this.month--;
+					}
+				}
+				this.getList();
+			},
+			//申请补卡
+			applybk(id,time) {
+				this.$router.push({
+					name: 'MasterAttendanceApply',
+					query: {
+						id: id,
+						time:time
+					}
+				})
+			},
+			//跳转申请补卡详情
+			goToInfo(id) {
+				this.$router.push({
+					name: 'XsyApprovalInfo',
+					query: {
+						id: id,
+						formId:'applyWork'
+					}
+				})
+			},
+			//获取列表
+			getList() {
+				this.isLoading = true;
+				var obj={
+					date:this.year+"-"+(this.month>9?"":"0")+this.month
+				}
+				this.recordList=[];
+				API_Attendance.statistics(obj).then(response => {
+					
+					//this.recordList = response.list;
+					var recordList=[]
+					var status=this.status
+					response.list.forEach(function(item, index) {
+						var bl=true;
+						
+						 for(var i in recordList){
+							 var it=recordList[i];
+							 if(it.result==item.result){
+								 bl=false;
+								 it.list.push(item);
+								 break
+							 }
+						 }
+						 if(bl){
+							 var my={
+								 result:item.result,
+								 name:status[item.result],
+								 list:[],
+							 }
+							 my.list.push(item)
+							 recordList.push(my)
+						 }
+						 
+						 
+					})
+					this.recordList=recordList;
+					console.log(this.recordList)
+					this.obj=response;
+					
+					this.isLoading = false;
+				}).catch(error => {
+					this.isLoading = false;
+					mui.toast(error);
+				})
+			}, 
+			 
+			//选择日期
+			selectData() {
+				var _this = this;
+				var picker = new mui.DtPicker({
+					"type": "date",
+					"beginYear": 2020,
+					"endYear": 2040,
+					"endDate": new Date(),
+					"value": _this.subForm.queryDate
+				});
+				picker.show(function(rs) {
+					_this.subForm.queryDate = rs.text;
+					//获取公司列表
+					_this.getCompanyList();
+					picker.dispose();
+				});
+			},
+		 
+			asynCallBack() {
+
+			},
+		},
+		mounted() {
+			//获取列表
+		//	this.getCompanyList();
+			this.getList();
+		},
+		destroyed() {
+			
+		},
+		computed: {
+			...mapGetters({
+				openId: 'wx_openid',
+				token: 'token',
+				person_data: 'person_data',
+				person_popedom: 'person_popedom',
+			})
+		},
+		
+	}
+</script>
+<style scoped src="$project/assets/css/xpgj.css"></style>
+
+<style scoped src="$project/assets/css/xpwyfyy.css"></style>
+<style src="$project/assets/css/iconfont.css"></style>
+<style scoped>
+	.colorAAA {
+		color: #AAAAAA;
+	}
+</style>

+ 4 - 2
src/utils/request.js

@@ -16,8 +16,10 @@ axios.defaults.headers['Content-Type'] = 'application/x-www-form-urlencoded'
 var BACKEND_URL = process.env.VUE_APP_BACKEND_URL;
 
 if (process.env.VUE_APP_NODE_NAME == 'devlopment') {
-		//BACKEND_URL='http://192.168.33.120:8086/shinestar-server';
-		 BACKEND_URL="https://ykt-test.xiaoxinda.com/shinestar-server/"
+		// BACKEND_URL='http://192.168.33.120:8086/shinestar-server';
+		// BACKEND_URL='http://192.168.33.90:8086/shinestar-server';
+		
+		BACKEND_URL="https://ykt-test.xiaoxinda.com/shinestar-server/"
 		//BACKEND_URL='http://223.75.170.44:6060/shinestar-server';
 		
 }

+ 99 - 0
src/utils/request2.js

@@ -0,0 +1,99 @@
+import axios from 'axios';
+import store from '$project/store';
+import router from '@/router';
+import Vue from 'vue';
+import Qs from 'qs';
+import $ from 'jquery';
+
+import {
+	getToken,
+	getOpenId
+} from '$project/utils/storage'
+
+axios.defaults.headers['Content-Type'] = 'application/x-www-form-urlencoded'
+
+//检测是否可以访问通
+var BACKEND_URL = process.env.VUE_APP_BACKEND_URL;
+
+if (process.env.VUE_APP_NODE_NAME == 'devlopment') {
+		// BACKEND_URL='http://192.168.33.120:8086/shinestar-server';
+		 BACKEND_URL='http://192.168.33.90:8086/shinestar-server';
+		
+	//	BACKEND_URL="https://ykt-test.xiaoxinda.com/shinestar-server/"
+		//BACKEND_URL='http://223.75.170.44:6060/shinestar-server';
+		
+}
+
+//var BACKEND_URL = 'http://192.168.33.120:8086/shinestar-server'
+//http://223.75.170.44:6060/shinestar-server
+
+// 创建axios实例
+const service = axios.create({
+	baseURL: BACKEND_URL,
+	timeout: 20000,
+	// 请求头信息
+	headers: {
+		'Content-Type': 'application/x-www-form-urlencoded',
+		'X-Requested-With': 'XMLHttpRequest',
+	},
+});
+
+//request拦截器
+service.interceptors.request.use(config => {
+	let Authorization = getToken() ? getToken() : '';
+	config.headers['Authorization'] = Authorization;
+	return config;
+}, error => {
+	//对请求错误处理
+	return Promise.reject(error);
+});
+
+// response拦截器
+service.interceptors.response.use(
+	response => {
+		if (response.data.code === 200) {
+			if (response.data.result) {
+				return Promise.resolve(response.data.data);
+			} else {
+				return Promise.reject(response.data.message);
+			}
+		} else if (response.data.code === 415) {
+			//这里不执行,token过期
+		} else {
+			//无code的情况
+			if (response.data.result) {
+				return Promise.resolve(response.data.data);
+			} else {
+				return Promise.reject(response.data.message);
+			}
+
+			// todo 根据返回值判定去向,比如token过期,未登录等等
+
+			// 403 接口需要登录
+			/* if (response.data.code === 403) {
+				store.dispatch('clearToken');
+				router.replace({
+					name: 'Login',
+					query: {
+						redirect: router.currentRoute.fullPath
+					}
+				});
+			} */
+
+			return Promise.reject(response.data.message);
+		}
+	},
+	error => {
+		// alert('网络超时!请重新加载!');
+		//console.error(error);
+		// 判断请求异常信息中是否含有超时timeout字符串
+		if (error.message.includes('timeout')) {
+			return Promise.reject('请求超时,请稍后再试');
+		} else if (error.message.includes('NetworkError')) {
+			return Promise.reject('网络错误,请稍后再试');
+		}
+		return Promise.reject(error);
+	}
+);
+
+export default service;