y595705120 3 gadi atpakaļ
vecāks
revīzija
b77cf2ef65

+ 1 - 0
package.json

@@ -27,6 +27,7 @@
     "file-saver": "2.0.1",
     "fuse.js": "3.4.4",
     "js-cookie": "2.2.0",
+    "js-file-download": "^0.4.12",
     "jsonlint": "1.6.3",
     "jszip": "3.2.1",
     "lodash-es": "^4.17.20",

+ 7 - 1
src/api/article.js

@@ -8,6 +8,13 @@ export const getArticalList = (data) => {
     })
 }
 
+export const downloadFile = (articalId) => {
+    return service({
+        url: `/api/artical/downloadFile/${articalId}`,
+        method: 'get'
+    })
+}
+
 export const getHotArticalList = (data) => {
     return service({
         url: "/api/base/getHotArticalList",
@@ -122,4 +129,3 @@ export const replyArtical = (data) => {
         data
     })
 }
-

+ 5 - 0
src/assets/css/main.css

@@ -1,10 +1,12 @@
 .main{
   width: 1000px;
+  background: #FFF;
 }
 
 .main-body{
   background: #FFF;
   margin-top:20px;
+  margin-bottom: 20px;
 }
 
 .main-table{
@@ -14,6 +16,7 @@
 
 .main-left{
   width: 200px;
+  margin-top: 1px;
   display:inline-block;
 }
 
@@ -30,6 +33,8 @@
 
 .p20{padding: 20px;}
 
+.ml50{ margin-left: 50px;}
+
 .ml20{ margin-left: 20px;}
 .ml10{ margin-left: 10px;}/
 .ml2{ margin-left: 2px;}

+ 74 - 0
src/components/Upload/uploadFile.vue

@@ -0,0 +1,74 @@
+<template>
+  <div>
+      <el-upload
+        ref="upload"
+        :limit="1"
+        :action="action"
+        :auto-upload="true"
+        :show-file-list="false"
+        :headers="headers"
+        :before-upload="uploadBefore"
+        :on-success="uploadSuccess"
+        :on-change="handleChange"
+      >
+        <span style="float: left;">
+          <el-button plain type="primary" size="small" icon="el-icon-plus">
+            选择文件
+          </el-button>
+        </span>
+
+        <span style="margin-left: 20px;">
+          {{filename||''}}
+        </span>
+        <br>
+      </el-upload>
+  </div>
+</template>
+
+
+<script>
+import { authDB } from '@/db'
+
+export default {
+  name: 'UploadFile',
+  components:{},
+  data() {
+    return {
+      action: '/api/artical/uploadFile',
+      headers:{
+        'x-token': authDB.get('token'),
+        'x-user-id': authDB.get('uid')
+      },
+      filename:''
+    }
+  },
+  methods: {
+    uploadFile() {
+      this.$refs.upload.submit();
+    },
+    uploadBefore(file) {
+      const maxSize = file.size / 1024 / 1024 < 10;
+      if (!maxSize) {
+        this.$message.error('每个文件最大10M');
+      }
+      return maxSize;
+    },
+    uploadSuccess(res) {
+      const { data } = res;
+      if (data) {
+        this.$emit('onFinish', data.filename);
+      }
+    },
+    handleChange(file) {
+      if (file.status == 'ready') {
+        this.filename = file.name;
+      }
+    },
+
+  }
+}
+</script>
+
+<style lang="scss" scoped>
+
+</style>

+ 29 - 4
src/pages/data/data.js

@@ -1,5 +1,5 @@
 
-
+import {getMyArticalList, getArticalLikeList,getViewArticalList, getDownloadArticalList}  from '@/api/article'
 export default {
 	departs:[
         {
@@ -91,7 +91,32 @@ export default {
   ],
   owners:{
     0: '无权限',
-    1: '普通',
-    2: '管理'
-  }
+    1: '经办人',
+    2: '负责人',
+    3: '分管领导'
+  },
+  myfiles:[
+    {
+      id: "1",
+      value: '我发布的文件',
+      label: '我发布的文件',
+      listApi:getMyArticalList
+    }, {
+      id: "2",
+      value: '我收藏的文件',
+      label: '我收藏的文件',
+      listApi:getArticalLikeList
+    }, {
+      id: "3",
+      value: '最近浏览的文件',
+      label: '最近浏览的文件',
+      listApi:getViewArticalList
+
+    }, {
+      id: "4",
+      value: '最近下载的文件',
+      label: '最近下载的文件',
+      listApi:getDownloadArticalList
+    }
+  ]
 }

+ 13 - 1
src/pages/other/components/IHeader.vue

@@ -21,6 +21,15 @@
         <li :class="{'navfirst': isActive('/reply-list')}">
           <a href="#/reply-list">我的申请</a>
         </li>
+
+        <li :class="{'navfirst': isActive('/file-add')}" v-if="isActive('/file-add')">
+          <a href="#/apply-list">发布文章</a>
+        </li>
+        
+        <li :class="{'navfirst': isActive('/file-info')}" v-if="isActive('/file-info')">
+          <a href="#/apply-list">文件信息</a>
+        </li>
+
       </ul>
     </div>
     <div class="sousuo">
@@ -38,7 +47,7 @@
           clearable
         ></el-autocomplete>
         <el-button type="primary" size="mini" @click="handlerSearch">搜索</el-button>
-        <el-button type="success" size="mini" @click="handlerSearch">高级搜索</el-button>
+        <el-button type="success" size="mini" @click="addFile">发布文章</el-button>
       </div>
     </div>
   </div>
@@ -93,6 +102,9 @@ export default {
     },
     handlerSearch(){
       this.$router.push( {path:'/file-search', query:{keyword: this.searchInfo}})
+    },
+    addFile(){
+      this.$router.push( {path:'/file-add'})
     }
   }
 }

+ 148 - 0
src/pages/other/file-add.vue

@@ -0,0 +1,148 @@
+<template>
+  <div class="main">
+    <div class="main-body">
+      <el-form class="p20" label-width="100px"  label-position="left"
+      ref="elForm" :model="info" :rules="rules" >
+
+         <el-form-item label="所属部门" class="mt20" prop="department">
+           <el-select v-model="info.department"
+            @change="selectDepartment($event)"
+            collapse-tags placeholder="请选择"  clearable>
+             <el-option
+             v-for="item in userDepartments"
+             :value="item"
+             :key="item.departmentId">
+             {{item.department}} - {{item.isLeader|leader}}
+             </el-option>
+           </el-select>
+         </el-form-item>
+
+         <el-form-item label="所属分类" class="mt20" prop="category">
+             <el-select v-model="info.category" collapse-tags placeholder="请选择"  clearable>
+               <el-option v-for="(item,index) in categorys"
+               :value="item.value" :key="index" :label="item.value"></el-option>
+             </el-select>
+         </el-form-item>
+
+         <el-form-item label="文件标题" class="mt20" prop="title">
+             <el-input class="ipt-select" v-model="info.title"></el-input>
+         </el-form-item>
+
+         <el-form-item label="文件简介" class="mt20" prop="brief">
+             <el-input class="ipt-select" type="textarea" v-model="info.brief"></el-input>
+         </el-form-item>
+
+         <el-form-item label="上传文件"  prop="filename">
+            <upload-file  placeholder="上传文档"  @rmImage="info.filename=''"  @onFinish="onUpload"/>
+         </el-form-item>
+
+          <el-form-item label="">
+
+              <el-button type="primary" @click="onSubmit" class="btn-md">
+                提交文件
+              </el-button>
+
+          </el-form-item>
+
+      </el-form>
+    </div>
+  </div>
+
+</template>
+
+<script>
+  import UploadFile from "@/components/Upload/uploadFile.vue";
+  import data  from '../data/data.js'
+  import {mapGetters } from 'vuex'
+  import {addArtical} from '@/api/article.js'
+  export default {
+    name: 'application',
+    components:{ UploadFile },
+    data() {
+      return {
+        loading:false,
+        isLike: 0,
+        dropDownValue:'',
+        departments:data.departs,
+        showDepartments:data.departs,
+        categorys:data.categorys,
+        info: {
+          filename:'',
+          departmentId:0,
+          category:'',
+          department:'',
+          title:'',
+          brief:''
+        },
+        rules: {
+          title:[{required:true, message:'请输入标题'}],
+          brief:[{required:true, message:'请输入简介'}],
+          category:[{required:true, message:'请输入选择分类'}],
+          department:[{required:true, message:'请选择部门'}],
+          filename:[{required:true, message:'请上传文件'}]
+        }
+      }
+    },
+    computed: {
+    	...mapGetters("user", ["userDepartments"])
+    },
+    filters:{
+      leader(val){
+        return data.owners[ val ]
+      }
+    },
+    watch:{
+      dropDownValue(val){
+        this.showDepartments = this.departments.filter( item=>{
+          return item.department.indexOf( val  )>-1
+        })
+      }
+    },
+    methods:{
+      onUpload(filename){
+        this.info.filename = filename;
+      },
+      selectDepartment(item){
+        this.info.departmentId = +item.departmentId;
+        this.info.department = item.department
+      },
+
+      showFinish(){
+        let that = this
+        this.$msgbox({
+          title: "提交成功",
+          message: "恭喜你-提交成功",
+          showCancelButton: true,
+          cancelButtonText:"继续提交文件",
+          confirmButtonText: "回到我的文件",
+          beforeClose: (action, instance, done) => {
+            if (action === 'confirm') {
+              that.$router.push({path:'/my-file'});
+              done();
+            }else{
+              done();
+            }
+          }
+        }).catch((res) => {
+          console.log(res)
+         });
+      },
+      onSubmit(){
+        this.$refs["elForm"].validate((valid) => {
+          if (!valid) return;
+          addArtical( this.info ).then(res=>{
+            if( res.code == 200){
+              this.showFinish()
+            }
+          })
+        })
+      }
+    }
+  }
+</script>
+
+<style>
+  .ipt-select{
+    width: 500px;
+  }
+</style>

+ 12 - 29
src/pages/other/file-info.vue

@@ -56,14 +56,13 @@
 
        </el-form>
 
-       <div class="mt35">
+       <div class="mt10">
          <h2> 文章简介 </h2>
-         <div class="content mt20 p20">
+         <div class="content mt10 p20">
            <div>{{info.brief}} </div>
          </div>
        </div>
 
-
         <div class="p20">
           <el-button v-if="!isLike" icon="el-icon-star-off" @click="likeArtical"> 收藏</el-button>
           <el-button v-else icon="el-icon-star-on" type="info" @click="unLikeArtical">取消</el-button>
@@ -89,7 +88,9 @@
   import {toDatetime } from '@/utils/date.js'
   import data from '../data/data.js'
   import { getArticalInfo, likeArtical, unLikeArtical} from '@/api/article.js'
-    import { downloadArtical, applyArtical} from '@/api/article.js'
+  import {downloadFile, downloadArtical, applyArtical} from '@/api/article.js'
+
+  import {download} from '@/utils/download.js'
   import { mapGetters } from "vuex";
 
   export default {
@@ -124,37 +125,19 @@
     },
     methods: {
       download(){
-        let param ={articalId: this.articalId, isLeader:this.isLeader}
-        this.loading = true;
-        this.$message.successMsg("文件生成中", 1)
-        downloadArtical( param ).then( res=>{
-          console.log( "res", res)
-          if( res.status != 200 ) {
-            this.loading = false;
-            this.$message.errorMsg("下载失败", 1)
-            return;
-          }
-          const blob = new Blob([res.data])
-          const fileName = res.header.filename
-          const link = document.createElement('a')
-          link.download = fileName
-          link.style.display = 'none'
-          link.href = URL.createObjectURL(blob)
-          document.body.appendChild(link)
-          link.click()
-          URL.revokeObjectURL(link.href)
-          document.body.removeChild(link)
-          this.loading = false;
-        }).catch( ()=>{
-          this.loading = false;
-        })
+        let articalId = this.articalId
+        if( this.isLeader >0 ){
+          download( `/api/artical/downloadFile/${articalId}`)
+        }else{
+          this.$message.successMsg("无权限下载", 1)
+        }
       },
       applyDownload(){
         let param ={articalId: this.articalId}
         this.loading = true;
         applyArtical( param ).then( res=>{
           if( res.code == 200){
-            this.$message.successMsg("申请成功", 3)
+            this.$message.successMsg("申请成功", 1)
           }
           this.loading = false;
         }).catch( ()=>{

+ 17 - 28
src/pages/other/my-file.vue

@@ -38,11 +38,19 @@
             <el-table-column label="标题" min-width="200" prop="title">
             </el-table-column>
 
-            <el-table-column label="时间" min-width="60" prop="createAt">
+            <el-table-column label="时间" min-width="80" prop="createAt" align="center">
               <template slot-scope="{row, $index}">
                 <span> {{row.createAt|toDatetime}}</span>
               </template>
             </el-table-column>
+
+            <el-table-column label="备注" width="60" align="center">
+              <template v-slot="{row}">
+                <el-button  type="text" @click="download(row)" v-if="selectId==1"> 下载 </el-button>
+                <span v-else> 无 </span>
+              </template>
+            </el-table-column>
+
           </el-table>
 
 
@@ -65,31 +73,11 @@
 import IHeader from "./components/IHeader";
 import IFooter from "./components/IFooter";
 import {getArticalList,getApplyArticalList}  from '@/api/article'
-import {getMyArticalList, getArticalLikeList,getViewArticalList, getDownloadArticalList}  from '@/api/article'
+import {getMyArticalList,downloadFile}  from '@/api/article'
+import {download} from '@/utils/download.js'
 import {toDatetime} from '@/utils/date.js'
+import data from '../data/data.js'
 
-const options = [{
-  id: "1",
-  value: '我发布的文件',
-  label: '我发布的文件',
-  listApi:getMyArticalList
-}, {
-  id: "2",
-  value: '我收藏的文件',
-  label: '我收藏的文件',
-  listApi:getArticalLikeList
-}, {
-  id: "3",
-  value: '最近浏览的文件',
-  label: '最近浏览的文件',
-  listApi:getViewArticalList
-
-}, {
-  id: "4",
-  value: '最近下载的文件',
-  label: '最近下载的文件',
-  listApi:getDownloadArticalList
-}];
 
 export default {
   name: 'application',
@@ -106,7 +94,7 @@ export default {
     return {
       list: [],
       total: 0,
-      options:options,
+      options:data.myfiles,
       pageSize: 10,
       page:1,
       searchDepartId: "",
@@ -124,13 +112,14 @@ export default {
   filters:{
     toDatetime
   },
-  created() {
-    this.list = options
-  },
   mounted() {
     this.getArticalList();
   },
   methods: {
+    download( row ){
+      let articalId = row.articalId
+      download( `/api/artical/downloadFile/${articalId}`)
+    },
     selectTag( item ) {
       this.selectId = item.id;
       this.listApi = item.listApi,

+ 19 - 4
src/pages/other/reply-list.vue

@@ -6,7 +6,7 @@
           <span>我的申请</span>
         </div>
 
-        <el-table :data="restaurants"  border stripe>
+        <el-table :data="restaurants"  border stripe v-loading="loading">
           <el-table-column label="序号" min-width="60" prop="id">
           </el-table-column>
 
@@ -31,14 +31,13 @@
                 type="success"
                 size="small"
                 icon="el-icon-circle-check"
-                @click="applyDoc(row)"
+                @click="download(row)"
               >下载文件</el-button>
 
               <el-button
                 v-else
                 type="text"
                 size="small"
-                @click="applyDoc(row)"
               >等待审核</el-button>
             </template>
           </el-table-column>
@@ -74,7 +73,8 @@ import IHeader from "./components/IHeader";
 import IFooter from "./components/IFooter";
 import glIcon from '@/icons/img/2016smyjj_gl_icon.jpg'
 import data  from '../data/data.js'
-import {getHotArticalList,getArticalList,getReplyArticalList}  from '@/api/article'
+import {downloadArtical ,getArticalList,getReplyArticalList}  from '@/api/article'
+
 
 import {toDatetime} from '@/utils/date.js'
 
@@ -88,6 +88,7 @@ export default {
     return {
       dialogFormVisible: false,
       glIcon: glIcon,
+      loading:false,
       list: data.departs,
       total: 0,
       page:1,
@@ -120,6 +121,20 @@ export default {
       this.dialogFormVisible = true
       this.form = row
     },
+    download( row ){
+      let param ={articalId: row.articalId, isLeader:0, id:row.id}
+      this.loading = true;
+      this.$message.successMsg("文件生成中", 1)
+      downloadArtical( param ).then( res=>{
+        this.loading = false;
+        if( res.code == 200 ) {
+          window.open( res.data )
+          return;
+        }
+      }).catch( ()=>{
+        this.loading = false;
+      })
+    },
     getReplyArticalList() {
       getReplyArticalList( {} ).then( res=>{
         this.restaurants = res.data.list

+ 5 - 0
src/router/index.js

@@ -101,6 +101,11 @@ export const constantRoutes = [
           component: () => import('@/pages/other/my-file'),
           hidden: true
         },
+        {
+          path: '/file-add',
+          component: () => import('@/pages/other/file-add'),
+          hidden: true
+        },
         {
           path: '/file-info',
           component: () => import('@/pages/other/file-info'),

+ 51 - 0
src/utils/download.js

@@ -0,0 +1,51 @@
+import axios from 'axios';
+import { authDB } from '@/db'
+
+import fileDownload from 'js-file-download'
+
+export async function download(  url  ) {
+    const res = await axios({
+        baseURL: process.env.VUE_APP_BASE_API,
+        timeout: 2 * 60 * 60 * 1000,
+        headers:{
+          'Content-Type': 'application/json',
+          'x-token': authDB.get('token'),
+          'x-user-id': authDB.get('uid')
+        },
+        url:url,
+        method:"get",
+        responseType: "blob"
+    });
+    let disposition = res.headers['content-disposition'];
+    disposition= disposition.replace("attachment; filename=", "")
+    disposition= disposition.replace(" ", "")
+    let filename = decodeURI( disposition );
+    let fileType=res.headers['content-type'];
+
+    let resBlob = res.data;
+    let resData = null;
+    try {
+        let resText = await new Promise((resolve, reject) => {
+            // 通过 FileReader 接受并解析
+            let reader = new FileReader();
+            reader.addEventListener('abort', reject);
+            reader.addEventListener('error', reject);
+            reader.addEventListener('loadend', () => {
+                resolve(reader.result);
+            });
+            // 文件
+            reader.readAsText(resBlob);
+        });
+        resData = JSON.parse(resText);
+    } catch (err) {
+    }
+    if (resData) {
+        if (resData.error) {
+
+        } else {
+
+        }
+    } else {
+        fileDownload(resBlob, filename);
+    }
+}