''
liukangdong
2024-06-18 e209de113c9062a5111a395719a91406d1645d27
''
已添加2个文件
已修改6个文件
451 ■■■■■ 文件已修改
admin/src/api/business/visits.js 16 ●●●●● 补丁 | 查看 | 原始文档 | blame | 历史
admin/src/api/index.js 1 ●●●● 补丁 | 查看 | 原始文档 | blame | 历史
admin/src/api/other/other.js 6 ●●●●● 补丁 | 查看 | 原始文档 | blame | 历史
admin/src/components/business/operaVisitsReportWindow.vue 148 ●●●●● 补丁 | 查看 | 原始文档 | blame | 历史
admin/src/components/business/operaVisitsWindow.vue 180 ●●●●● 补丁 | 查看 | 原始文档 | blame | 历史
admin/src/views/business/reportRecord.vue 50 ●●●●● 补丁 | 查看 | 原始文档 | blame | 历史
admin/src/views/business/visits.vue 46 ●●●●● 补丁 | 查看 | 原始文档 | blame | 历史
h5/manifest.json 4 ●●●● 补丁 | 查看 | 原始文档 | blame | 历史
admin/src/api/business/visits.js
@@ -45,3 +45,19 @@
    }
  })
}
// æŸ¥è¯¢è¢«è®¿äººåˆ—表
export const getVisitedMember = (data) => {
  return request.post('/visitsAdmin/cloudService/web/visitor/getVisitedMember', data)
}
// æŸ¥è¯¢æ¥è®¿äº‹ç”±
export const getVisitedVisitReason = (data) => {
  return request.post('/visitsAdmin/cloudService/web/visitor/visitReason', data)
}
// æäº¤è®¿å®¢ä¿¡æ¯
export const createFk = (data) => {
  return request.post('/visitsAdmin/cloudService/web/visitor/createFk', data)
}
// è®¿å®¢æŠ¥å¤‡
export const createVisit = (data) => {
  return request.post('/visitsAdmin/cloudService/business/visits/createVisit', data)
}
admin/src/api/index.js
@@ -2,3 +2,4 @@
export * from './business/index'
export * from './platform'
export * from './other/other'
admin/src/api/other/other.js
@@ -6,3 +6,9 @@
    trim: true
  })
}
// æŸ¥è¯¢å­—典值数据
export const getSystemDictData = (params) => {
  return request.get('/visitsAdmin/cloudService/web/other/getSystemDictData', {
    params: { ...params }
  })
}
admin/src/components/business/operaVisitsReportWindow.vue
¶Ô±ÈÐÂÎļþ
@@ -0,0 +1,148 @@
<template>
  <GlobalWindow
      title="新增访客报备"
      width="600px"
      :visible.sync="isShowModal"
      :confirm-working="isWorking"
      @confirm="confirm"
  >
    <el-form :model="param" ref="paramRef" :rules="rules" >
      <div class="title_tip">访客预约</div>
      <el-form-item label="被访人" prop="startTime">
        {{ userInfo.realname }} {{ userInfo.company.companyNamePath }}
      </el-form-item>
      <el-form-item label="入园时间" prop="starttime">
        <el-date-picker
          v-model="param.starttime"
          format="yyyy-MM-dd HH:mm"
          value-format="yyyy-MM-dd HH:mm:ss"
          type="datetime"
          default-time="08:00:00"
        />
      </el-form-item>
      <el-form-item label="离园时间" prop="endtime">
        <el-date-picker
          v-model="param.endtime"
          format="yyyy-MM-dd HH:mm"
          value-format="yyyy-MM-dd HH:mm:ss"
          type="datetime"
          default-time="08:00:00"
        />
      </el-form-item>
      <div class="title_tip">访客信息</div>
      <el-form-item label="联系人" prop="name">
        <el-input v-model="param.name" placeholder="请输入联系人的姓名"></el-input>
      </el-form-item>
      <el-form-item label="手机号" prop="phone">
        <el-input v-model="param.phone" placeholder="请输入联系人的手机号"></el-input>
      </el-form-item>
      <el-form-item label="来访单位" prop="companyName">
        <el-input v-model="param.companyName" placeholder="请输入来访的单位全称"></el-input>
      </el-form-item>
      <el-form-item label="入园车辆" prop="carNos">
        <el-input v-model="param.carNos" placeholder="请输入车牌号"></el-input>
      </el-form-item>
      <el-form-item label="随车人数" prop="memberNum">
        <el-input v-model="param.memberNum" placeholder="请输入随车人员总数"></el-input>
      </el-form-item>
      <el-form-item label="来访事由" prop="reason">
        <el-select v-model="param.reason" placeholder="请选择">
          <el-option v-for="item in VisitReason" :key="item.id" :label="item.title" :value="item.title" />
        </el-select>
      </el-form-item>
    </el-form>
  </GlobalWindow>
</template>
<script>
import BaseOpera from '@/components/base/BaseOpera'
import GlobalWindow from '@/components/common/GlobalWindow'
import UploadFaceImg from '@/components/common/UploadFaceImg'
import { createVisit, getVisitedVisitReason } from '@/api/business/visits'
export default {
  name: 'OperaVisitsHkWindow',
  extends: BaseOpera,
  components: {
    GlobalWindow,
    UploadFaceImg
  },
  data () {
    return {
      isShowModal: false,
      param: {
        type: 2
      },
      userInfo: this.$store.state.userInfo,
      VisitReason: [],
      uploadData: {
        folder: 'member'
      },
      rules: {
        starttime: [{ required: true, message: '请选择日期', trigger: 'change' }],
        endtime: [{ required: true, message: '请选择日期', trigger: 'change' }],
        reason: [{ required: true, message: '请选择', trigger: 'change' }],
        type: [{ required: true, message: '请选择', trigger: 'change' }],
        idcardType: [{ required: true, message: '请选择', trigger: 'change' }],
        memberNum: [{ required: true, message: '请输入', trigger: 'blur' }],
        name: [{ required: true, message: '请输入', trigger: 'blur' }],
        idcardNo: [{ required: true, message: '请输入', trigger: 'blur' }],
        companyName: [{ required: true, message: '请输入', trigger: 'blur' }],
        phone: [{ required: true, message: '请输入', trigger: 'blur' }],
        carNos: [{ required: true, message: '请输入', trigger: 'blur' }],
        constructionReason: [{ required: true, message: '请输入', trigger: 'blur' }],
      }
    }
  },
  created () {
    this.initData()
  },
  methods: {
    initData () {
      getVisitedVisitReason({}).then(res => {
        this.VisitReason = res || []
      })
    },
    uploadAvatarSuccess (file) {
      this.$set(this.param, 'faceImg', file.imgurl)
      this.$set(this.param, 'faceImgUrl', file.imgurlfull)
    },
    // åŒæ­¥ä¿¡æ¯
    confirm () {
      this.$refs.paramRef.validate((valid) => {
        if (!valid) {
          return
        }
        // è°ƒç”¨æ–°å»ºæŽ¥å£
        this.isWorking = true
        createVisit({
          ...this.param,
          receptMemberId: this.userInfo.memberId,
          receptMemberName: this.userInfo.realname
        })
          .then(() => {
            this.visible = false
            this.$tip.apiSuccess('提交成功')
            this.$emit('success')
            this.$emit('close')
          })
          .catch(e => {
            this.$tip.apiFailed(e)
          })
          .finally(() => {
            this.isWorking = false
          })
      })
    }
  }
}
</script>
<style lang="scss" scoped>
.title_tip{
  font-size: 18px;
  font-weight: 600;
  margin-bottom: 10px;
}
</style>
admin/src/components/business/operaVisitsWindow.vue
¶Ô±ÈÐÂÎļþ
@@ -0,0 +1,180 @@
<template>
  <GlobalWindow
      title="新增访客预约"
      width="600px"
      :visible.sync="isShowModal"
      :confirm-working="isWorking"
      @confirm="confirm"
  >
    <el-form :model="param" ref="paramRef" :rules="rules" >
      <div class="title_tip">访客信息</div>
      <el-form-item label="访客姓名" prop="name">
        <el-input v-model="param.name" placeholder="请输入访客的姓名"></el-input>
      </el-form-item>
      <el-form-item label="访客手机号" prop="phone">
        <el-input v-model="param.phone" placeholder="请输入访客的手机号"></el-input>
      </el-form-item>
      <el-form-item label="证件类型" prop="idcardType">
        <el-select v-model="param.idcardType" placeholder="请选择">
          <el-option label="身份证" :value="0" />
          <el-option label="港澳证件" :value="1" />
          <el-option label="护照" :value="2" />
        </el-select>
      </el-form-item>
      <el-form-item label="证件号码" prop="idcardNo">
        <el-input maxlength="18" v-model="param.idcardNo" placeholder="请输入访客的证件号码"></el-input>
      </el-form-item>
      <el-form-item label="来访单位" prop="companyName">
        <el-input v-model="param.companyName" placeholder="请输入来访的单位全称"></el-input>
      </el-form-item>
      <el-form-item label="人脸照片" prop="faceImgUrl">
        <UploadFaceImg
          :file="{ 'imgurlfull': param.faceImgUrl, 'imgurl': param.faceImg }"
          :uploadData="uploadData"
          @uploadSuccess="uploadAvatarSuccess"
          @uploadEnd="isUploading = false"
          @uploadBegin="isUploading = true"
        />
      </el-form-item>
      <div class="title_tip" style="marginTop: 60px;">访客预约</div>
      <el-form-item label="被访人" prop="receptMemberId">
        <el-select v-model="param.receptMemberId" placeholder="请选择">
          <el-option v-for="item in memberList" :key="item.id" :label="item.name + ' ' + item.companyName" :value="item.id" />
        </el-select>
      </el-form-item>
      <el-form-item label="入园时间" prop="starttime">
        <el-date-picker
          v-model="param.starttime"
          format="yyyy-MM-dd HH:mm"
          value-format="yyyy-MM-dd HH:mm:ss"
          type="datetime"
          default-time="08:00:00"
        />
      </el-form-item>
      <el-form-item label="离园时间" prop="endtime">
        <el-date-picker
          v-model="param.endtime"
          format="yyyy-MM-dd HH:mm"
          value-format="yyyy-MM-dd HH:mm:ss"
          type="datetime"
          default-time="08:00:00"
        />
      </el-form-item>
      <el-form-item label="来访事由" prop="reason">
        <el-select v-model="param.reason" placeholder="请选择">
          <el-option v-for="item in VisitReason" :key="item.id" :label="item.title" :value="item.title" />
        </el-select>
      </el-form-item>
      <el-form-item label="是否施工作业" prop="type">
        <el-switch
          style="width: 200px"
          v-model="param.type"
          :active-value="1"
          :inactive-value="0">
        </el-switch>
      </el-form-item>
      <el-form-item v-if="param.type == 1" label="施工内容" prop="constructionReason">
        <el-input v-model="param.constructionReason" placeholder="请输入施工内容"></el-input>
      </el-form-item>
      <el-form-item label="随行车辆" prop="carNos">
        <el-input v-model="param.carNos" placeholder="请输入车牌号"></el-input>
      </el-form-item>
    </el-form>
  </GlobalWindow>
</template>
<script>
import BaseOpera from '@/components/base/BaseOpera'
import GlobalWindow from '@/components/common/GlobalWindow'
import UploadFaceImg from '@/components/common/UploadFaceImg'
import { createFk, getVisitedVisitReason, getVisitedMember } from '@/api/business/visits'
export default {
  name: 'OperaVisitsHkWindow',
  extends: BaseOpera,
  components: {
    GlobalWindow,
    UploadFaceImg
  },
  data () {
    return {
      isShowModal: false,
      param: {
        type: 0,
        idcardType: 0
      },
      VisitReason: [],
      memberList: [],
      uploadData: {
        folder: 'member'
      },
      rules: {
        starttime: [{ required: true, message: '请选择日期', trigger: 'change' }],
        endtime: [{ required: true, message: '请选择日期', trigger: 'change' }],
        reason: [{ required: true, message: '请选择', trigger: 'change' }],
        type: [{ required: true, message: '请选择', trigger: 'change' }],
        idcardType: [{ required: true, message: '请选择', trigger: 'change' }],
        faceImgUrl: [{ required: true, message: '请上传', trigger: 'change' }],
        name: [{ required: true, message: '请输入', trigger: 'blur' }],
        idcardNo: [{ required: true, message: '请输入', trigger: 'blur' }],
        companyName: [{ required: true, message: '请输入', trigger: 'blur' }],
        phone: [{ required: true, message: '请输入', trigger: 'blur' }],
        carNos: [{ required: true, message: '请输入', trigger: 'blur' }],
        constructionReason: [{ required: true, message: '请输入', trigger: 'blur' }],
      }
    }
  },
  created () {
    this.$set(this.param, 'receptMemberId', this.$store.state.userInfo.memberId)
    this.initData()
  },
  methods: {
    initData () {
      getVisitedVisitReason({}).then(res => {
        this.VisitReason = res || []
      })
      getVisitedMember({}).then(res => {
        this.memberList = res || []
      })
    },
    uploadAvatarSuccess (file) {
      this.$set(this.param, 'faceImg', file.imgurl)
      this.$set(this.param, 'faceImgUrl', file.imgurlfull)
    },
    // åŒæ­¥ä¿¡æ¯
    confirm () {
      this.$refs.paramRef.validate((valid) => {
        if (!valid) {
          return
        }
        // è°ƒç”¨æ–°å»ºæŽ¥å£
        this.isWorking = true
        createFk({
          ...this.param
        })
          .then(() => {
            this.visible = false
            this.$tip.apiSuccess('提交成功')
            this.$emit('success')
            this.$emit('close')
          })
          .catch(e => {
            this.$tip.apiFailed(e)
          })
          .finally(() => {
            this.isWorking = false
          })
      })
    }
  }
}
</script>
<style lang="scss" scoped>
.title_tip{
  font-size: 18px;
  font-weight: 600;
  margin-bottom: 10px;
}
</style>
admin/src/views/business/reportRecord.vue
@@ -6,6 +6,10 @@
      @handleQuery="getList(1)"
      @clear="clear"
    />
    <div style="margin: 16px 0 0" v-permissions="['business:visits:create', 'business:visits:exportExcel']">
      <el-button type="primary" @click="handleEdit()" icon="el-icon-plus" v-permissions="['business:visits:create']">新建</el-button>
      <el-button type="primary" :loading="exLoading" @click="exportExcel" v-permissions="['business:visits:exportExcel']">导出</el-button>
    </div>
    <el-table
      v-loading="loading"
      :data="dataList"
@@ -92,6 +96,7 @@
      :pagination="pagination"
    />
    <ReportDetail v-if="isShowReport" ref="VisReportDetailRef" />
    <OperaVisitsReportWindow @close="isShowEdit = false" @success="getList"  v-if="isShowEdit" ref="operaVisitsWindowRef" />
  </div>
</template>
@@ -100,18 +105,25 @@
import QueryForm from '@/components/common/QueryForm'
// import ReportDetail from './page-components/ReportDetail.vue'
import ReportDetail from '@/views/task/visReportDetail.vue'
import { fetchList } from '@/api/business/visits'
import OperaVisitsReportWindow from '@/components/business/operaVisitsReportWindow.vue'
import { fetchList, exportExcel } from '@/api/business/visits'
export default {
  components: {
    ReportDetail,
    QueryForm,
    Pagination
    Pagination,
    OperaVisitsReportWindow
  },
  data () {
    return {
      isShowEdit: false,
      exLoading: false,
      isShowReport: false,
      activeTab: '0',
      filters: {},
      filters: {
        type: 2
      },
      dataList: [],
      queryFormConfig: {
        formItems: [
@@ -144,6 +156,32 @@
    this.getList()
  },
  methods: {
    exportExcel () {
      this.$dialog.exportConfirm('确认导出吗?')
        .then(() => {
          this.exLoading = true
          exportExcel({
            page: this.pagination.page,
            capacity: 1000000,
            model: this.filters
          })
            .then(response => {
              this.download(response)
            })
            .catch(e => {
              this.$tip.apiFailed(e)
            })
            .finally(() => {
              this.exLoading = false
            })
        })
    },
    handleEdit () {
      this.isShowEdit = true
      this.$nextTick(() => {
        this.$refs.operaVisitsWindowRef.isShowModal = true
      })
    },
    handleDetail (row) {
      this.isShowReport = true
      this.$nextTick(() => {
@@ -159,14 +197,16 @@
      const { pagination, filters } = this
      pagination.page = page || pagination.page
      fetchList({
        model: { ...filters, type: 2 },
        model: { ...filters },
        ...pagination
      }).then(res => {
        this.dataList = res.records || []
      })
    },
    clear () {
      this.filters = {}
      this.filters = {
        type: 2
      }
      this.getList(0)
    },
    handleSizeChange (capacity) {
admin/src/views/business/visits.vue
@@ -33,10 +33,10 @@
        </el-form>
        <!-- è¡¨æ ¼å’Œåˆ†é¡µ -->
        <template v-slot:table-wrap>
<!--            <ul class="toolbar" v-permissions="['business:visits:create', 'business:visits:delete']">-->
<!--                <li><el-button type="primary" @click="$refs.operaVisitsWindow.open('新建访客申请信息表')" icon="el-icon-plus" v-permissions="['business:visits:create']">新建</el-button></li>-->
<!--                <li><el-button @click="deleteByIdInBatch" icon="el-icon-delete" v-permissions="['business:visits:delete']">删除</el-button></li>-->
<!--            </ul>-->
           <ul class="toolbar" v-permissions="['business:visits:create', 'business:visits:exportExcel']">
               <li><el-button type="primary" @click="handleEdit()" icon="el-icon-plus" v-permissions="['business:visits:create']">新建</el-button></li>
               <li><el-button type="primary" :loading="isWorking.export" @click="exportExcel" v-permissions="['business:visits:exportExcel']">导出</el-button></li>
           </ul>
            <el-table
                v-loading="isWorking.search"
                :data="tableData.list"
@@ -110,6 +110,8 @@
            </pagination>
            <!--      è¯¦æƒ…      -->
            <OperaVisitsDesWindow ref="OperaVisitsDesWindow" />
            <!-- æ–°å»º -->
            <OperaVisitsWindow @close="isShowEdit = false" @success="search"  v-if="isShowEdit" ref="operaVisitsWindowRef" />
        </template>
    </TableLayout>
</template>
@@ -119,13 +121,15 @@
import TableLayout from '@/layouts/TableLayout'
import Pagination from '@/components/common/Pagination'
import OperaVisitsDesWindow from '@/components/business/OperaVisitsDesWindow'
import OperaVisitsWindow from '@/components/business/operaVisitsWindow'
export default {
  name: 'Visits',
  extends: BaseTable,
  components: { TableLayout, Pagination, OperaVisitsDesWindow },
  components: { TableLayout, Pagination, OperaVisitsDesWindow, OperaVisitsWindow },
  data () {
    return {
      isShowEdit: false,
      // æœç´¢
      searchForm: {
        name: '',
@@ -145,36 +149,42 @@
    this.search()
  },
  methods: {
    departure(id) {
    handleEdit () {
      this.isShowEdit = true
      this.$nextTick(() => {
        this.$refs.operaVisitsWindowRef.isShowModal = true
      })
    },
    departure (id) {
      this.$confirm('确定离场吗, æ˜¯å¦ç»§ç»­?', '提示', {
        confirmButtonText: '确定',
        cancelButtonText: '取消',
        type: 'warning'
      }).then(() => {
        level(id)
            .then(res => {
              this.page = 1
              this.getData()
            })
          .then(res => {
            this.page = 1
            this.getData()
          })
      }).catch(() => {
      });
      })
    },
    cancel(id) {
    cancel (id) {
      this.$confirm('确定取消预约吗, æ˜¯å¦ç»§ç»­?', '提示', {
        confirmButtonText: '确定',
        cancelButtonText: '取消',
        type: 'warning'
      }).then(() => {
        visitCancel(id)
            .then(res => {
              this.page = 1
              this.getData()
            })
          .then(res => {
            this.page = 1
            this.getData()
          })
      }).catch(() => {
      });
    },
      })
    }
  }
}
</script>
h5/manifest.json
@@ -89,12 +89,12 @@
            "historyApiFallback" : true,
            "disableHostCheck" : true,
            "proxy" : {
                "/api" : {
                "/admin_interface" : {
                    // è¿™ä¸ªå­—段名需与你配置的basePrefixUrl一致,系统识别到带有/dev-api请求的地址时,会在前面拼接上代理服务器地址
                    "target" : "http://192.168.0.173/admin_interface", // ä»£ç†æœåŠ¡å™¨åŸŸåæˆ–IP地址
                    "changeOrigin" : true, // å…è®¸è·¨åŸŸ 
                    "pathRewrite" : {
                        "^/api" : "" // é‡å†™åœ°å€ï¼Œå¦‚果实际接口中是不带/dev-api,需要将这个前缀置空,因为这个前缀只是为了识别用,识别完之后就没用了
                        "^/admin_interface" : "" // é‡å†™åœ°å€ï¼Œå¦‚果实际接口中是不带/dev-api,需要将这个前缀置空,因为这个前缀只是为了识别用,识别完之后就没用了
                    }
                }
            },