zory 1 周之前
父节点
当前提交
2ffb89c8a4
共有 56 个文件被更改,包括 3385 次插入90 次删除
  1. 40 0
      src/api/model/merShop.js
  2. 7 0
      src/api/model/store.js
  3. 33 0
      src/api/model/storeShop.js
  4. 87 0
      src/views/manage/agent/components/express.vue
  5. 10 2
      src/views/manage/agent/components/table.vue
  6. 3 1
      src/views/manage/order/refund/components/table.vue
  7. 1 0
      src/views/manage/order/refund/index.vue
  8. 1 0
      src/views/manage/order/send/index.vue
  9. 1 0
      src/views/manage/refund/index.vue
  10. 92 0
      src/views/manage/shop/index/components/auth.vue
  11. 10 2
      src/views/manage/shop/index/components/table.vue
  12. 1 1
      src/views/manage/shop/index/index.vue
  13. 2 38
      src/views/merchant/components/store.vue
  14. 1 0
      src/views/merchant/order/refund/index.vue
  15. 1 0
      src/views/merchant/order/send/index.vue
  16. 1 0
      src/views/merchant/refund/index.vue
  17. 5 33
      src/views/merchant/shop/index/components/form.vue
  18. 3 3
      src/views/merchant/shop/index/components/table.vue
  19. 1 1
      src/views/merchant/shop/index/index.vue
  20. 4 1
      src/views/merchant/shop/store/components/form.vue
  21. 6 3
      src/views/merchant/user/components/form.vue
  22. 0 2
      src/views/merchant/user/components/option.vue
  23. 0 2
      src/views/merchant/user/components/table.vue
  24. 1 1
      src/views/store/dashboard/index.vue
  25. 86 0
      src/views/store/order/before/components/form.vue
  26. 56 0
      src/views/store/order/before/components/option.vue
  27. 54 0
      src/views/store/order/before/components/search.vue
  28. 229 0
      src/views/store/order/before/components/table.vue
  29. 49 0
      src/views/store/order/before/index.vue
  30. 64 0
      src/views/store/order/components/log.vue
  31. 86 0
      src/views/store/order/done/components/form.vue
  32. 56 0
      src/views/store/order/done/components/option.vue
  33. 54 0
      src/views/store/order/done/components/search.vue
  34. 229 0
      src/views/store/order/done/components/table.vue
  35. 49 0
      src/views/store/order/done/index.vue
  36. 60 0
      src/views/store/order/life/components/form.vue
  37. 56 0
      src/views/store/order/life/components/option.vue
  38. 69 0
      src/views/store/order/life/components/search.vue
  39. 169 0
      src/views/store/order/life/components/table.vue
  40. 49 0
      src/views/store/order/life/index.vue
  41. 86 0
      src/views/store/order/refund/components/form.vue
  42. 56 0
      src/views/store/order/refund/components/option.vue
  43. 54 0
      src/views/store/order/refund/components/search.vue
  44. 229 0
      src/views/store/order/refund/components/table.vue
  45. 50 0
      src/views/store/order/refund/index.vue
  46. 86 0
      src/views/store/order/send/components/form.vue
  47. 56 0
      src/views/store/order/send/components/option.vue
  48. 54 0
      src/views/store/order/send/components/search.vue
  49. 229 0
      src/views/store/order/send/components/table.vue
  50. 50 0
      src/views/store/order/send/index.vue
  51. 86 0
      src/views/store/refund/components/form.vue
  52. 56 0
      src/views/store/refund/components/option.vue
  53. 54 0
      src/views/store/refund/components/search.vue
  54. 229 0
      src/views/store/refund/components/table.vue
  55. 50 0
      src/views/store/refund/index.vue
  56. 234 0
      src/views/store/setting/index.vue

+ 40 - 0
src/api/model/merShop.js

@@ -0,0 +1,40 @@
+import config from "@/config";
+import http from "@/utils/request";
+
+export default {
+    list: {
+        url: `${config.API_URL}/merchant/shop/list`,
+        name: "-",
+        get: async function (params) {
+            return await http.get(this.url, params);
+        },
+    },
+    save: {
+        url: `${config.API_URL}/merchant/shop/save`,
+        name: "-",
+        post: async function (params) {
+            return await http.post(this.url, params);
+        },
+    },
+    edit: {
+        url: `${config.API_URL}/merchant/shop/edit`,
+        name: "-",
+        post: async function (params) {
+            return await http.post(this.url, params);
+        },
+    },
+    batch: {
+        url: `${config.API_URL}/merchant/shop/batch`,
+        name: "-",
+        post: async function (params) {
+            return await http.post(this.url, params);
+        },
+    },
+    del: {
+        url: `${config.API_URL}/merchant/shop/del`,
+        name: "-",
+        post: async function (params) {
+            return await http.post(this.url, params);
+        },
+    },
+}

+ 7 - 0
src/api/model/store.js

@@ -16,6 +16,13 @@ export default {
             return await http.post(this.url, params);
         },
     },
+    hook: {
+        url: `${config.API_URL}/store/hook`,
+        name: "-",
+        get: async function (params) {
+            return await http.get(this.url, params);
+        },
+    },
     edit: {
         url: `${config.API_URL}/store/edit`,
         name: "-",

+ 33 - 0
src/api/model/storeShop.js

@@ -0,0 +1,33 @@
+import config from "@/config";
+import http from "@/utils/request";
+
+export default {
+    list: {
+        url: `${config.API_URL}/store/shop/list`,
+        name: "-",
+        get: async function (params) {
+            return await http.get(this.url, params);
+        },
+    },
+    detail: {
+        url: `${config.API_URL}/store/shop/detail`,
+        name: "-",
+        get: async function (params) {
+            return await http.get(this.url, params);
+        },
+    },
+    save: {
+        url: `${config.API_URL}/store/shop/save`,
+        name: "-",
+        post: async function (params) {
+            return await http.post(this.url, params);
+        },
+    },
+    shopSave: {
+        url: `${config.API_URL}/store/shop/edit`,
+        name: "-",
+        post: async function (params) {
+            return await http.post(this.url, params);
+        },
+    },
+}

+ 87 - 0
src/views/manage/agent/components/express.vue

@@ -0,0 +1,87 @@
+<template>
+    <el-dialog :title="titleMap[mode]" v-model="visible" :width="600" destroy-on-close @closed="$emit('closed')" :close-on-click-modal="false" :close-on-press-escape="false">
+        <el-form ref="dialogForm" :model="formData" :rules="rules" label-width="100px" label-position="top">
+            
+            <el-form-item label="顾客编码" prop="appid">
+                <el-input v-model="formData.appid" clearable placeholder="请输入"></el-input>
+                <div class="el-form-item-msg">顺丰开放平台获取</div>
+            </el-form-item>
+            <el-form-item label="校验码" prop="secret">
+                <el-input v-model="formData.secret" clearable placeholder="请输入"></el-input>
+                <div class="el-form-item-msg"></div>
+            </el-form-item>
+            <el-form-item label="月结账号" prop="account">
+                <el-input v-model="formData.account" clearable placeholder="请输入"></el-input>
+                <div class="el-form-item-msg"></div>
+            </el-form-item>
+        </el-form>
+		<template #footer>
+			<el-button @click="visible=false" >取 消</el-button>
+			<el-button type="primary" :loading="isSaveing" @click="submit()">提交</el-button>
+		</template>
+    </el-dialog>
+</template>
+
+<script>
+export default{
+    data(){
+        return {
+            loading: false,
+            mode:"add",
+            titleMap:{
+                add:"顺丰开放平台授权",
+                edit:"顺丰开放平台授权"
+            },
+            formData:{
+                appid:"",
+                secret:"",
+                account:""
+            },
+            rules:{
+                appid: [
+                    {required: true, message: '请输入'}
+                ],
+                secret: [
+                    {required: true, message: '请输入'}
+                ],
+                account: [
+                    {required: true, message: '请输入'}
+                ],
+            },
+            visible: false,
+            isSaveing: false,
+            agent_id:0
+        }
+    },
+    methods:{
+        open(mode = 'add'){
+            this.mode = mode;
+            this.visible = true;
+            return this
+        },
+        //表单注入数据
+        setData(data){
+            if (data.express.appid) {
+                this.formData = data.express;
+            }
+            this.agent_id = data.agent_id;
+        },
+        async submit(){
+            var validate = await this.$refs.dialogForm.validate().catch(()=>{});
+            if(!validate){ return false }
+            var submitData = {};
+            submitData.express = this.formData;
+            submitData.agent_id = this.agent_id;
+            var resp = await this.$API.agent.edit.post(submitData);
+            if (resp.code == 0) {
+                return this.$message.error(resp.msg);
+            }
+            this.$message.success(resp.msg);
+            this.visible = false;
+            this.formData = {};
+            this.submitState = false;
+            this.$emit("success");
+        }
+    }
+}
+</script>

+ 10 - 2
src/views/manage/agent/components/table.vue

@@ -36,6 +36,7 @@
         <el-table-column label="操作" width="200" align="center" fixed="right">
             <template #default="scope">
                 <el-button-group>
+                    <el-button text type="danger" size="small" @click="table_express(scope.row)">顺丰开平</el-button>
                     <el-button text type="primary" size="small" @click="table_view(scope.row)">编辑</el-button>
                     <el-button text type="danger" size="small" @click="table_del(scope.row)">删除</el-button>
                 </el-button-group>
@@ -43,13 +44,15 @@
         </el-table-column>
     </scTable>
     <formMain ref="formMain" @success="handleSuccess"></formMain>
+    <expressMain ref="expressMain" @success="handleSuccess"></expressMain>
 </template>
 
 <script>
 import formMain from './form';
+import expressMain from './express';
 export default {
     components: {
-        formMain
+        formMain,expressMain
     },
     data(){
         return {
@@ -63,6 +66,11 @@ export default {
     },
     
     methods: {
+        table_express(data){
+            this.$nextTick(() => {
+                this.$refs.expressMain.open("edit").setData(data)
+            })
+        },
         table_view(data){
             this.$nextTick(() => {
                 this.$refs.formMain.open("edit").setData(data)
@@ -77,7 +85,7 @@ export default {
                     return this.$message.warning(resp.msg);
                 }
                 this.$message.success(resp.msg);
-                this.$emit("success");
+                this.$refs.table.refresh()
             }).catch(()=>{})
         },
         refresh(){

+ 3 - 1
src/views/manage/order/refund/components/table.vue

@@ -113,7 +113,9 @@ export default {
             },
             dataSelect:[],
             dataSelectFull:[],
-            searchKey:{}
+            searchKey:{
+                ex_status:4
+            }
         }
     },
     methods: {

+ 1 - 0
src/views/manage/order/refund/index.vue

@@ -2,6 +2,7 @@
     <el-container class="flex-column">
         <div class="table-search">
             <search @success="handleSuccess"></search>
+            <el-alert type="warning" show-icon title="栏目提醒" description="已解锁并不代表用户该笔订单已退款,用户可以再次进入小程序进行预约" :closable="false" style="margin-bottom: 10px;"></el-alert>
             <optionBtn @success="handleSuccess" :dataSelect="dataSelect" :dataSelectFull="dataSelectFull" type="3"></optionBtn>
         </div>
         <el-main class="nopadding">

+ 1 - 0
src/views/manage/order/send/index.vue

@@ -2,6 +2,7 @@
     <el-container class="flex-column">
         <div class="table-search">
             <search @success="handleSuccess"></search>
+            <el-alert type="warning" show-icon title="栏目提醒" description="已预约栏目的订单,用户如取消订单,无需商家同意,产品如已发货,请尽快修改订单状态到服务中,如造成经济损失,本核销系统不负法律责任(使用自动呼叫快递功能的商家忽略)" :closable="false" style="margin-bottom: 10px;"></el-alert>
             <optionBtn @success="handleSuccess" :dataSelect="dataSelect" :dataSelectFull="dataSelectFull" type="3"></optionBtn>
         </div>
         <el-main class="nopadding">

+ 1 - 0
src/views/manage/refund/index.vue

@@ -2,6 +2,7 @@
     <el-container class="flex-column">
         <div class="table-search">
             <search @success="handleSuccess"></search>
+            <el-alert type="warning" show-icon title="栏目提醒" description="该栏目只处理服务中订单,已核销订单,请去抖音来客后台处理撤销核销/协助退款" :closable="false" style="margin-bottom: 10px;"></el-alert>
             <optionBtn @success="handleSuccess" :dataSelect="dataSelect" :dataSelectFull="dataSelectFull" type="3"></optionBtn>
         </div>
         <el-main class="nopadding">

+ 92 - 0
src/views/manage/shop/index/components/auth.vue

@@ -0,0 +1,92 @@
+<template>
+    <el-drawer :title="titleMap[mode]" :append-to-body="true" v-model="visible" :size="800" destroy-on-close :close-on-click-modal="false" @closed="$emit('closed')" :with-header="false">
+        <el-container class="flex-column" v-loading="loading">
+            <div class="drawer-detail-main">
+                <div class="drawer-detail-header">
+                    <div class="drawer-detail-header-body">
+                        <div class="drawer-detail-header-left">{{ titleMap[mode] }}</div>
+                        <div class="drawer-detail-header-left">
+                            <el-button type="default" icon="el-icon-close" @click="visible=false"></el-button>
+                        </div>
+                    </div>
+                </div>
+            </div>
+            <el-main>
+                <el-form ref="dialogForm" :model="formData" :rules="rules" label-width="100px" label-position="top" v-loading="loading">
+                    <fieldset>
+                        <legend><el-tag>抖音开放平台</el-tag></legend>
+                        <el-form-item label="WebHooks">
+                            <el-input v-model="formData.webhook" disabled readonly clearable placeholder="门店名称">
+                                <template #append><el-button v-copy="formData.webhook">复制</el-button></template>
+                            </el-input>
+                            <div class="el-form-item-msg">开放平台 - 开发配置 - Webhooks中设置</div>
+                        </el-form-item>
+                    </fieldset>
+                    <fieldset>
+                        <legend><el-tag>顺丰开放平台</el-tag></legend>
+                        <el-form-item label="路由推送接口">
+                            <el-input v-model="formData.sf" disabled readonly clearable placeholder="路由推送接口">
+                                <template #append><el-button v-copy="formData.sf">复制</el-button></template>
+                            </el-input>
+                            <div class="el-form-item-msg">顺丰开放平台</div>
+                        </el-form-item>
+                        <el-form-item label="订单状态推送接口">
+                            <el-input v-model="formData.sf" disabled readonly clearable placeholder="订单状态推送接口">
+                                <template #append><el-button v-copy="formData.sf">复制</el-button></template>
+                            </el-input>
+                            <div class="el-form-item-msg">顺丰开放平台</div>
+                        </el-form-item>
+                        <el-form-item label="清单运费推送接口">
+                            <el-input v-model="formData.sf" disabled readonly clearable placeholder="清单运费推送接口">
+                                <template #append><el-button v-copy="formData.sf">复制</el-button></template>
+                            </el-input>
+                            <div class="el-form-item-msg">顺丰开放平台</div>
+                        </el-form-item>
+                    </fieldset>
+                </el-form>
+            </el-main>
+            <el-footer style="text-align: right;">
+                <el-button @click="visible=false" >取 消</el-button>
+            </el-footer>
+        </el-container>
+    </el-drawer>
+</template>
+
+<script>
+export default {
+    data(){
+        return {
+            loading:true,
+            mode:"add",
+            titleMap:{
+                add:"授权地址",
+                edit:"授权地址"
+            },
+            visible: false,
+            isSaveing: false,
+            formData:{}
+        }
+    },
+    methods: {
+        open(mode = 'add'){
+            this.mode = mode;
+            this.visible = true;
+            return this
+        },
+        async getConfig(data){
+            this.loading = true;
+            var resp = await this.$API.store.hook.get();
+            this.loading = false;
+            data.webhook = resp.data.url+"notify/hook/"+data.store_id;
+            data.spi = resp.data.url+"notify/spi/"+data.store_id;
+            data.sf = resp.data.url+"sf/hook/"+data.store_id;
+            data.pdf = resp.data.url+"sf/pdf/"+data.store_id;
+            this.formData = data;
+        },
+        //表单注入数据
+        setData(data){
+            this.getConfig(data);
+        },
+    }
+}
+</script>

+ 10 - 2
src/views/manage/shop/index/components/table.vue

@@ -50,7 +50,8 @@
         <el-table-column label="操作" width="220" align="center" fixed="right">
             <template #default="scope">
                 <el-button-group>
-                    <el-button text type="warning" size="small" @click="table_auth(scope.row)">设置Path</el-button>
+                    <el-button text type="success" size="small" @click="table_auth(scope.row)">授权地址</el-button>
+                    <el-button text type="warning" size="small" @click="table_path(scope.row)">设置Path</el-button>
                     <el-button text type="primary" size="small" @click="table_view(scope.row)">编辑</el-button>
                     <el-button text type="danger" size="small" @click="table_del(scope.row)">删除</el-button>
                 </el-button-group>
@@ -58,13 +59,15 @@
         </el-table-column>
     </scTable>
     <formMain ref="formMain" @success="handleSuccess"></formMain>
+    <authMain ref="authMain" @success="handleSuccess"></authMain>
 </template>
 
 <script>
 import formMain from './form';
+import authMain from './auth';
 export default {
     components: {
-        formMain
+        formMain,authMain
     },
     data(){
         return {
@@ -79,6 +82,11 @@ export default {
     
     methods: {
         table_auth(data){
+            this.$nextTick(() => {
+                this.$refs.authMain.open("edit").setData(data)
+            })
+        },
+        table_path(data){
             this.$confirm(`【必须】设置小程序全量用户订单按钮以及跳转路径`, '提示', {
                 type: 'warning'
             }).then(async ()=>{

+ 1 - 1
src/views/manage/shop/index/index.vue

@@ -1,8 +1,8 @@
 <template>
     <el-container class="flex-column">
-        <el-alert type="warning" title="添加完店铺后,必须点击【设置Path】,不然抖音下单后会没有进入小程序的入口" :closable="false" style="margin-bottom: 10px;"></el-alert>
         <div class="table-search">
             <search @success="handleSuccess"></search>
+            <el-alert type="warning" show-icon title="特别提醒" description="添加完店铺后,必须点击【设置Path】,不然抖音下单后会没有进入小程序的入口" :closable="false" style="margin-bottom: 10px;"></el-alert>
             <optionBtn @success="handleSuccess" :dataSelect="dataSelect" :dataSelectFull="dataSelectFull" type="3"></optionBtn>
         </div>
         <el-main class="nopadding">

+ 2 - 38
src/views/merchant/components/store.vue

@@ -33,28 +33,10 @@
                             <div class="checkbox"></div>
                         </el-table-column>
                         <el-table-column label="店铺名称" width="200" fixed="left" prop="store_name"></el-table-column>
-                        <el-table-column label="账户ID" prop="account_id" width="200"></el-table-column>
-                        <el-table-column label="团单类型" prop="type" width="150">
-                            <template #default="scope">
-                                <div class="status-success" v-if="scope.row.type==1"><sc-status-indicator type="success"></sc-status-indicator> 团购</div>
-                                <div class="status-danger" v-else><sc-status-indicator type="danger"></sc-status-indicator> 提货券/代金券</div>
-                            </template>
-                        </el-table-column>
-                        <el-table-column label="发券方式" prop="type" width="150">
-                            <template #default="scope">
-                                <div class="status-success" v-if="scope.row.code_type==1"><sc-status-indicator type="success"></sc-status-indicator> 平台码</div>
-                                <div class="status-danger" v-else><sc-status-indicator type="danger"></sc-status-indicator> 商家码</div>
-                            </template>
-                        </el-table-column>
+                        <el-table-column label="账户ID" prop="store_id" width="200"></el-table-column>
                         <el-table-column label="物品名称" prop="express_goods" width="150"></el-table-column>
                         <el-table-column label="物品单位" prop="express_unit" width="150"></el-table-column>
                         <el-table-column label="发货地址" prop="express_address" width="260"></el-table-column>
-                        <el-table-column label="AppId" prop="appid" width="150">
-                            <template #default="scope">
-                                <span v-if="scope.row.appid">{{ scope.row.appid }}</span>
-                                <span class="status-danger" v-else>未设置</span>
-                            </template>
-                        </el-table-column>
                         <el-table-column label="联系人" prop="express_name" width="150">
                             <template #default="scope">
                                 <span v-if="scope.row.express_name">{{ scope.row.express_name }}</span>
@@ -80,28 +62,10 @@
                     <scTable ref="table" :apiObj="list.apiObj" :hideSetting="true" paginationLayout="total, prev, pager, next" :params="searchKey" @selectionChange="selectionChange" row-key="id" @sortChange="sortChange">
                         <el-table-column type="selection" width="50" fixed="left"></el-table-column>
                         <el-table-column label="店铺名称" width="200" fixed="left" prop="store_name"></el-table-column>
-                        <el-table-column label="账户ID" prop="account_id" width="200"></el-table-column>
-                        <el-table-column label="团单类型" prop="type" width="150">
-                            <template #default="scope">
-                                <div class="status-success" v-if="scope.row.type==1"><sc-status-indicator type="success"></sc-status-indicator> 团购</div>
-                                <div class="status-danger" v-else><sc-status-indicator type="danger"></sc-status-indicator> 提货券/代金券</div>
-                            </template>
-                        </el-table-column>
-                        <el-table-column label="发券方式" prop="type" width="150">
-                            <template #default="scope">
-                                <div class="status-success" v-if="scope.row.code_type==1"><sc-status-indicator type="success"></sc-status-indicator> 平台码</div>
-                                <div class="status-danger" v-else><sc-status-indicator type="danger"></sc-status-indicator> 商家码</div>
-                            </template>
-                        </el-table-column>
+                        <el-table-column label="账户ID" prop="store_id" width="200"></el-table-column>
                         <el-table-column label="物品名称" prop="express_goods" width="150"></el-table-column>
                         <el-table-column label="物品单位" prop="express_unit" width="150"></el-table-column>
                         <el-table-column label="发货地址" prop="express_address" width="260"></el-table-column>
-                        <el-table-column label="AppId" prop="appid" width="150">
-                            <template #default="scope">
-                                <span v-if="scope.row.appid">{{ scope.row.appid }}</span>
-                                <span class="status-danger" v-else>未设置</span>
-                            </template>
-                        </el-table-column>
                         <el-table-column label="联系人" prop="express_name" width="150">
                             <template #default="scope">
                                 <span v-if="scope.row.express_name">{{ scope.row.express_name }}</span>

+ 1 - 0
src/views/merchant/order/refund/index.vue

@@ -2,6 +2,7 @@
     <el-container class="flex-column">
         <div class="table-search">
             <search @success="handleSuccess"></search>
+            <el-alert type="warning" show-icon title="栏目提醒" description="已解锁并不代表用户该笔订单已退款,用户可以再次进入小程序进行预约" :closable="false" style="margin-bottom: 10px;"></el-alert>
             <optionBtn @success="handleSuccess" :dataSelect="dataSelect" :dataSelectFull="dataSelectFull" type="3"></optionBtn>
         </div>
         <el-main class="nopadding">

+ 1 - 0
src/views/merchant/order/send/index.vue

@@ -2,6 +2,7 @@
     <el-container class="flex-column">
         <div class="table-search">
             <search @success="handleSuccess"></search>
+            <el-alert type="warning" show-icon title="栏目提醒" description="已预约栏目的订单,用户如取消订单,无需商家同意,产品如已发货,请尽快修改订单状态到服务中,如造成经济损失,本核销系统不负法律责任(使用自动呼叫快递功能的商家忽略)" :closable="false" style="margin-bottom: 10px;"></el-alert>
             <optionBtn @success="handleSuccess" :dataSelect="dataSelect" :dataSelectFull="dataSelectFull" type="3"></optionBtn>
         </div>
         <el-main class="nopadding">

+ 1 - 0
src/views/merchant/refund/index.vue

@@ -2,6 +2,7 @@
     <el-container class="flex-column">
         <div class="table-search">
             <search @success="handleSuccess"></search>
+            <el-alert type="warning" show-icon title="栏目提醒" description="该栏目只处理服务中订单,已核销订单,请去抖音来客后台处理撤销核销/协助退款" :closable="false" style="margin-bottom: 10px;"></el-alert>
             <optionBtn @success="handleSuccess" :dataSelect="dataSelect" :dataSelectFull="dataSelectFull" type="3"></optionBtn>
         </div>
         <el-main class="nopadding">

+ 5 - 33
src/views/merchant/shop/index/components/form.vue

@@ -23,10 +23,10 @@
                                     <div class="el-form-item-msg"></div>
                                 </el-form-item>
                             </el-col>
-                            <el-col :span="6">
+                            <el-col :span="12">
                                 <el-form-item label="来客账户ID" prop="store_id">
-                                    <el-input v-model="formData.store_id" clearable placeholder="来客账户ID"></el-input>
-                                    <div class="el-form-item-msg"></div>
+                                    <el-input :disabled="mode=='add'?false:true" v-model="formData.store_id" clearable placeholder="来客账户ID"></el-input>
+                                    <div class="el-form-item-msg">提交后不可修改,请仔细核对,如需修改请联系管理员</div>
                                 </el-form-item>
                             </el-col>
                             <el-col :span="6">
@@ -100,15 +100,6 @@
                                     <div class="el-form-item-msg">在小程序选择门店中展现</div>
                                 </el-form-item>
                             </el-col>
-                            <el-col :span="6">
-                                <el-form-item label="核销形式" prop="service_type">
-                                    <el-select v-model="formData.service_type" clearable placeholder="请选择" :style="{width: '100%'}">
-                                        <el-option :value="1" label="预约"></el-option>
-                                        <el-option :value="2" label="快递"></el-option>
-                                    </el-select>
-                                    <div class="el-form-item-msg">预约无需添加收货地址</div>
-                                </el-form-item>
-                            </el-col>
                         </el-row>
                     </fieldset>
                     <fieldset>
@@ -182,14 +173,9 @@
         </el-container>
     
     </el-drawer>
-    <agentData ref="agentData" :multiple="false" @success="handleAgent"></agentData>
 </template>
 <script>
-import agentData from "@/views/manage/components/agent";
 export default {
-    components: {
-        agentData
-    },
     data(){
         return {
             stepActive:1,
@@ -255,9 +241,6 @@ export default {
                 store_id: [
                     {required: true, message: '请输入'}
                 ],
-                agent_id: [
-                    {required: true, message: '请选择'}
-                ],
                 express_name: [
                     {required: true, message: '请输入'}
                 ],
@@ -283,17 +266,6 @@ export default {
         }
     },
     methods:{
-        handleAgent(data){
-            this.formData.agent_id = data.agent_id;
-        },
-        clearUser(){
-            this.formData.agent_id = "";
-        },
-        selectUser(){
-            this.$nextTick(() => {
-                this.$refs.agentData.open()
-            })
-        },
         open(mode = 'add'){
             this.mode = mode;
             this.visible = true;
@@ -319,9 +291,9 @@ export default {
                 submitData.password = this.$TOOL.crypto.MD5(this.formData.password)
                 submitData.password2 = this.$TOOL.crypto.MD5(this.formData.password2)
                 submitData.scene = "register";
-                var resp = await this.$API.store.save.post(submitData);
+                var resp = await this.$API.merStore.save.post(submitData);
             } else {
-                var resp = await this.$API.store.edit.post(submitData);
+                var resp = await this.$API.merStore.edit.post(submitData);
             }
             this.isSaveing = false;
             if (resp.code == 0) {

+ 3 - 3
src/views/merchant/shop/index/components/table.vue

@@ -63,7 +63,7 @@ export default {
     data(){
         return {
             list: {
-                apiObj: this.$API.store.list
+                apiObj: this.$API.merStore.list
             },
             dataSelect:[],
             dataSelectFull:[],
@@ -76,7 +76,7 @@ export default {
             this.$confirm(`【必须】设置小程序全量用户订单按钮以及跳转路径`, '提示', {
                 type: 'warning'
             }).then(async ()=>{
-                var resp = await this.$API.store.auth.post({"id":data.id});
+                var resp = await this.$API.merStore.auth.post({"id":data.id});
                 if (resp.code == 0) {
                     return this.$message.error(resp.msg);
                 }
@@ -93,7 +93,7 @@ export default {
             this.$confirm(`删除店铺后,所有有关该店铺的门店、订单等信息都将删除,不可恢复,确定要执行删除吗`, '提示', {
                 type: 'warning'
             }).then(async ()=>{
-                var resp = await this.$API.store.del.post({"id":data.id});
+                var resp = await this.$API.merStore.del.post({"id":data.id});
                 if (resp.code == 0) {
                     return this.$message.error(resp.msg);
                 }

+ 1 - 1
src/views/merchant/shop/index/index.vue

@@ -1,8 +1,8 @@
 <template>
     <el-container class="flex-column">
-        <el-alert type="warning" title="添加完店铺后,必须点击【设置Path】,不然抖音下单后会没有进入小程序的入口" :closable="false" style="margin-bottom: 10px;"></el-alert>
         <div class="table-search">
             <search @success="handleSuccess"></search>
+            <el-alert type="warning" show-icon title="特别提醒" description="添加完店铺后,必须点击【设置Path】,不然抖音下单后会没有进入小程序的入口" :closable="false" style="margin-bottom: 10px;"></el-alert>
             <optionBtn @success="handleSuccess" :dataSelect="dataSelect" :dataSelectFull="dataSelectFull" type="3"></optionBtn>
         </div>
         <el-main class="nopadding">

+ 4 - 1
src/views/merchant/shop/store/components/form.vue

@@ -86,6 +86,9 @@ export default {
                 poi_address: [
                     {required: true, message: '请输入'}
                 ],
+                poi_location: [
+                    {required: true, message: '请输入'}
+                ],
                 store_id: [
                     {required: true, message: '请选择'}
                 ]
@@ -117,7 +120,7 @@ export default {
             var validate = await this.$refs.dialogForm.validate().catch(()=>{});
             if(!validate){ return false }
             let submitData = JSON.parse(JSON.stringify(this.formData));
-            var resp = await this.$API.shop.save.post(submitData);
+            var resp = await this.$API.merShop.save.post(submitData);
             if(resp.code !== 1) {
                 return this.$message.error(resp.msg);
             }

+ 6 - 3
src/views/merchant/user/components/form.vue

@@ -5,8 +5,8 @@
                 <legend><el-tag>基础信息</el-tag></legend>
                 <el-row :gutter="15">
                     <el-col :span="24" v-if="type == 3">
-                    <el-form-item label="所属店铺" prop="account_id">
-                        <el-input v-model="formData.account_id" placeholder="所属店铺" clearable readonly :style="{ width: '100%' }" @click="selectUser">
+                    <el-form-item label="所属店铺" prop="store_id">
+                        <el-input v-model="formData.store_id" placeholder="所属店铺" clearable readonly :style="{ width: '100%' }" @click="selectUser">
                             <template #append>
                                 <el-tooltip
                                     effect="dark"
@@ -87,6 +87,9 @@ export default {
             submitState:false,
             disabled:false,
             rules:{
+                store_id: [
+                    {required: true, message: '请选择'}
+                ],
                 username: [
                     {required: true, message: '请输入登录账号'}
                 ],
@@ -146,7 +149,7 @@ export default {
             var validate = await this.$refs.dialogForm.validate().catch(()=>{});
             if(!validate){ return false }
             this.formData.type = this.type;
-            if (this.type == 3 && !this.formData.account_id) {
+            if (this.type == 3 && !this.formData.store_id) {
                 return this.$message.error("请选择店铺");
             }
             this.isSaveing = true;

+ 0 - 2
src/views/merchant/user/components/option.vue

@@ -34,7 +34,6 @@ export default {
     },
     methods: {
         async table_batch_status(status){
-            return this.$message.error("暂未开放")
             if (this.dataSelect.length == 0) {
                 return this.$message.error("请选择修改数据")
             }
@@ -50,7 +49,6 @@ export default {
             this.$emit("success");
         },
         table_add(type){
-            return this.$message.error("暂未开放")
             this.$nextTick(() => {
                 this.$refs.formMain.open("add",type)
             })

+ 0 - 2
src/views/merchant/user/components/table.vue

@@ -77,7 +77,6 @@ export default {
     },
     methods: {
         async table_del(data){
-            return this.$message.error("暂未开放")
             var resp = await this.$API.merUser.del.post({"id":data.id});
             if (resp.code == 0) {
                 return this.$message.error(resp.msg)
@@ -125,7 +124,6 @@ export default {
             this.$emit("successFull",this.dataSelectFull);
         },
         table_passwd(row){
-            return this.$message.error("暂未开放")
             this.$nextTick(() => {
                 this.$refs.userPasswd.open("edit").setData(row)
             })

+ 1 - 1
src/views/store/dashboard/index.vue

@@ -153,7 +153,7 @@ export default {
     created(){
         var baseData = this.$TOOL.data.get("SERVICE");
         this.baseData = baseData;
-        // this.getData()
+        this.getData()
     },
     methods: {
         async getData(){

+ 86 - 0
src/views/store/order/before/components/form.vue

@@ -0,0 +1,86 @@
+<template>
+    <el-dialog :title="titleMap[mode]" v-model="visible" :width="600" destroy-on-close @closed="$emit('closed')" :close-on-click-modal="false" :close-on-press-escape="false">
+        <el-form ref="dialogForm" :model="formData" :rules="rules" label-width="100px" label-position="top">
+            <el-form-item label="联系人" prop="username">
+                <el-input v-model="formData.username" clearable placeholder="请输入"></el-input>
+                <div class="el-form-item-msg"></div>
+            </el-form-item>
+            <el-form-item label="联系电话" prop="mobile">
+                <el-input v-model="formData.mobile" clearable placeholder="请输入"></el-input>
+                <div class="el-form-item-msg"></div>
+            </el-form-item>
+            <el-form-item label="详细地址" prop="address">
+                <el-input v-model="formData.address" clearable placeholder="请输入"></el-input>
+                <div class="el-form-item-msg"></div>
+            </el-form-item>
+        </el-form>
+		<template #footer>
+			<el-button @click="visible=false" >取 消</el-button>
+			<el-button type="primary" :loading="isSaveing" @click="submit()">提交</el-button>
+		</template>
+    </el-dialog>
+</template>
+<script>
+export default {
+    data(){
+        return {
+            loading: false,
+            mode:"add",
+            titleMap:{
+                add:"更新地址",
+                edit:"更新地址"
+            },
+            visible: false,
+            isSaveing: false,
+            formData:{},
+            submitState:false,
+            disabled:false,
+            rules:{
+                username: [
+                    {required: true, message: '请输入'}
+                ],
+                mobile: [
+                    {required: true, message: '请输入'}
+                ],
+                address: [
+                    {required: true, message: '请输入'}
+                ]
+            },
+            sms:""
+        }
+    },
+    methods:{
+        open(mode = 'add'){
+            this.mode = mode;
+            this.visible = true;
+            return this
+        },
+        //表单注入数据
+        setData(data){
+            data.address = data.region+data.address;
+            this.formData = data;
+        },
+        async submit(){
+            var validate = await this.$refs.dialogForm.validate().catch(()=>{});
+            if(!validate){ return false }
+            this.isSaveing = true;
+            let submitData = JSON.parse(JSON.stringify(this.formData));
+            var resp = await this.$API.order.save.post(submitData);
+            this.isSaveing = false;
+            if (resp.code !== 1) {
+                return this.$message.error(resp.msg);
+            }
+            this.$message.success(resp.msg);
+            this.visible = false;
+            this.formData = {};
+            this.submitState = false;
+            this.$emit("success");
+        }
+    }
+}
+</script>
+<style>
+.mt20 {margin-top: 20px;}
+.login-msg-yzm {display: flex;width: 100%;}
+.login-msg-yzm .el-button {margin-left: 10px;--el-button-size:42px;}
+</style>

+ 56 - 0
src/views/store/order/before/components/option.vue

@@ -0,0 +1,56 @@
+<template>
+    <fieldset>
+        <legend>
+            <el-tag type="info">按需操作</el-tag>
+        </legend>
+        <div class="op-header">
+            <div class="left-panel">
+                <sc-file-export :apiObj="$API.orderlife.export" :data="searchKey" :fileName="'来客订单_'+(new Date().getTime())" async>
+                    <template #default="{ open }">
+                        <el-button type="primary" icon="sc-icon-download" @click="open">导出</el-button>
+                    </template>
+                </sc-file-export>
+            </div>
+        </div>
+    </fieldset>
+</template>
+
+<script>
+import scFileExport from '@/components/scFileExport'
+export default {
+    components: {
+        scFileExport
+    },
+    props: {
+        type: { type: String, default: "1" },
+        dataSelect: { type: Array, default: () => [] },
+        searchKey: { type: Object, default: () => {} },
+        dataSelectFull: { type: Array, default: () => [] }
+    },
+    data(){
+        return {
+
+        }
+    },
+    methods: {
+        table_export(){
+            
+        },
+        async table_batch_status(status){
+            if (this.dataSelect.length == 0) {
+                return this.$message.error("请选择修改数据")
+            }
+            let submitData = {"id":this.dataSelect,"value":status,"field":"status","type":"batch"};
+            var resp = await this.$API.merGoods.batch.post(submitData);
+            if (resp.code == 0) {
+                return this.$message.error(resp.msg);
+            }
+            this.$message.success(resp.msg);
+            this.$emit("success");
+        },
+        handleSuccess(){
+            this.$emit("success");
+        },
+    }
+}
+</script>

+ 54 - 0
src/views/store/order/before/components/search.vue

@@ -0,0 +1,54 @@
+<template>
+    <fieldset>
+        <legend>
+            <el-tag type="info">条件筛选</el-tag>
+        </legend>
+        <el-form class="lv-form-inline" ref="searchForm" :model="searchKey" label-position="right" label-width="100px">
+            <div class="search-form">
+                <div class="form-left">
+                    <el-row :gutter="10">
+                        <el-col :span="this.$store.state.global.ismobile?12:4">
+                            <el-input v-model="searchKey.orderid" placeholder="订单编号" clearable :style="{ width: '100%' }" @keyup.enter="searchForm()">
+                                <template #prepend>订单编号</template>
+                            </el-input>
+                        </el-col>
+                        <el-col :span="this.$store.state.global.ismobile?12:4">
+                            <el-input v-model="searchKey.product" placeholder="商品ID" clearable :style="{ width: '100%' }" @keyup.enter="searchForm()">
+                                <template #prepend>商品ID</template>
+                            </el-input>
+                        </el-col>
+                        <el-col :span="this.$store.state.global.ismobile?12:4">
+                            <el-input v-model="searchKey.name" placeholder="商品标题" clearable :style="{ width: '100%' }" @keyup.enter="searchForm()">
+                                <template #prepend>商品标题</template>
+                            </el-input>
+                        </el-col>
+                        <el-col :span="this.$store.state.global.ismobile?12:4">
+                            <el-date-picker v-model="searchKey.create" :style="{width: '100%'}" placeholder="请选择创建时间" start-placeholder="开始时间" end-placeholder="结束时间" type="daterange" range-separator="至" @change="searchForm" />
+                        </el-col>
+                    </el-row>
+                </div>
+                <div class="form-line"></div>
+                <div class="form-right">
+                    <el-button type="primary" icon="el-icon-search" @click="searchForm">搜索</el-button>
+                </div>
+            </div>
+        </el-form>
+    </fieldset>
+</template>
+
+<script>
+export default {
+    data(){
+        return {
+            searchKey:{
+                ex_status:2
+            }
+        }
+    },
+    methods: {
+        searchForm(){
+            this.$emit("success",this.searchKey);
+        }
+    }
+}
+</script>

+ 229 - 0
src/views/store/order/before/components/table.vue

@@ -0,0 +1,229 @@
+<template>
+    <scTable ref="table" :apiObj="list.apiObj" :params="searchKey" @selectionChange="selectionChange" row-key="id">
+        <el-table-column type="selection" width="50" fixed="left"></el-table-column>
+        <el-table-column label="订单编号" prop="order_id" width="220" fixed="left">
+            <template #default="scope">
+                <span v-if="scope.row.order_id">{{ scope.row.order_id }}</span>
+                <span class="status-danger" v-else>未设置</span>
+            </template>
+        </el-table-column>
+        <el-table-column label="所属代理" prop="status" width="160">
+            <template #default="scope">
+                <span>{{ scope.row.agent?scope.row.agent.name:'-' }}</span>
+            </template>
+        </el-table-column>
+        <el-table-column label="所属店铺" prop="status" width="160">
+            <template #default="scope">
+                <span>{{ scope.row.store?scope.row.store.store_name:'-' }}</span>
+            </template>
+        </el-table-column>
+        <el-table-column label="订单类型" prop="status" width="120">
+            <template #default="scope">
+                <div class="status-danger" v-if="scope.row.service_type==1"><sc-status-indicator type="danger"></sc-status-indicator> 预约</div>
+                <div class="status-success" v-if="scope.row.service_type==2"><sc-status-indicator type="success"></sc-status-indicator> 快递</div>
+            </template>
+        </el-table-column>
+        <el-table-column label="收货地址" prop="company_id" width="120">
+            <template #default="scope">
+                <el-popover :width="200" placement="top-start">
+                    <template #reference>
+                        <div class="el-text">
+                            {{scope.row.username?scope.row.username:'-'}}
+                            <div class="desc" v-copy="'联系人:'+scope.row.username+'联系电话:'+scope.row.mobile+'联系地址:'+scope.row.region+scope.row.address"><span>一键复制</span></div>
+                        </div>
+                    </template>
+                    <div class="flex-tags-size">
+                        <span>联系人</span>{{scope.row.username?scope.row.username:'-'}}<br><br>
+                        <span>联系电话</span>{{scope.row.mobile?scope.row.mobile:'-'}}<br><br>
+                        <span>联系地址</span>{{scope.row.region?scope.row.region:'-'}}{{scope.row.address?scope.row.address:'-'}}
+                    </div>
+                </el-popover>
+            </template>
+        </el-table-column>
+        <el-table-column label="商品ID" prop="out_id" width="150">
+            <template #default="scope">
+                <span v-if="scope.row.product_id">{{ scope.row.product_id }}</span>
+                <span class="status-danger" v-else>未设置</span>
+            </template>
+        </el-table-column>
+        <el-table-column label="商品名称" prop="product_name" width="220">
+            <template #default="scope">
+                <span v-if="scope.row.product_name">{{ scope.row.product_name }}</span>
+                <span class="status-danger" v-else>未设置</span>
+            </template>
+        </el-table-column>
+        <el-table-column label="数量" prop="count" width="100">
+            <template #default="scope">
+                <span>{{ scope.row.parent.count }}件</span>
+            </template>
+        </el-table-column>
+        <el-table-column label="订单金额" prop="order_amount" width="150">
+            <template #default="scope">
+                <span v-if="scope.row.parent.order_amount">¥{{ scope.row.parent.order_amount }}</span>
+                <span class="status-danger" v-else>未设置</span>
+            </template>
+        </el-table-column>
+        <el-table-column label="支付金额" prop="pay_amount" width="150">
+            <template #default="scope">
+                <span v-if="scope.row.parent.pay_amount">¥{{ scope.row.parent.pay_amount }}</span>
+                <span class="status-danger" v-else>未设置</span>
+            </template>
+        </el-table-column>
+        <el-table-column label="状态" prop="status" width="180">
+            <template #default="scope">
+                <div class="status-danger" v-if="scope.row.express_status==0"><sc-status-indicator type="danger"></sc-status-indicator> 待发货</div>
+                <div class="status-success" v-if="scope.row.express_status==1"><sc-status-indicator type="success"></sc-status-indicator> 待核销</div>
+                <div class="status-danger" v-if="scope.row.express_status==2"><sc-status-indicator type="danger"></sc-status-indicator> 已完成</div>
+                <div class="status-info" v-if="scope.row.express_status==3"><sc-status-indicator type="info"></sc-status-indicator> 已取消</div>
+                <div class="status-info" v-if="scope.row.express_status==4"><sc-status-indicator type="info"></sc-status-indicator> 退款审核</div>
+                <div class="status-info" v-if="scope.row.express_status==5"><sc-status-indicator type="info"></sc-status-indicator> 拒绝退款</div>
+                <div v-if="scope.row.status==5 && scope.row.remark">{{ scope.row.remark }}</div>
+            </template>
+        </el-table-column>
+        <el-table-column label="创建时间" prop="create_at" width="180"></el-table-column>
+        <el-table-column label="操作" width="200" align="right" fixed="right">
+            <template #default="scope">
+                <el-button-group>
+                    <el-button text type="warning" size="small" @click="table_log(scope.row)">订单记录</el-button>
+                    <el-button text type="warning" size="small" @click="table_express(scope.row)" v-if="scope.row.express_status==0">呼叫快递</el-button>
+                    <el-button text type="warning" size="small" v-if="scope.row.express_status==1" @click="table_print(scope.row)">打印面单</el-button>
+                    <el-button text type="success" size="small" @click="table_end(scope.row)" v-if="scope.row.express_status==1">手动核销</el-button>
+                    <el-button text type="success" size="small" @click="table_passwd(scope.row)" v-if="scope.row.express_status==0 && scope.row.service_type==2">更新地址</el-button>
+                </el-button-group>
+            </template>
+        </el-table-column>
+    </scTable>
+    <formMain ref="formMain" @success="handleSuccess"></formMain>
+    <addMain ref="addMain" @success="handleSuccess"></addMain>
+    <logMain ref="logMain" @success="handleSuccess"></logMain>
+</template>
+
+<script>
+import formMain from './form';
+import addMain from "@/views/manage/components/send";
+import logMain from '@/views/manage/order/components/log'
+export default {
+    components: {
+        formMain,addMain,logMain
+    },
+    data(){
+        return {
+            list: {
+                apiObj: this.$API.order.list
+            },
+            dataSelect:[],
+            dataSelectFull:[],
+            searchKey:{
+                ex_status:2
+            }
+        }
+    },
+    methods: {
+        table_passwd(row){
+            return this.$message.success("暂未开放");
+            this.$nextTick(() => {
+                this.$refs.formMain.open("edit").setData(row)
+            })
+        },
+        table_end(data){
+            return this.$message.success("暂未开放");
+            this.$confirm(`核销后该笔订单即为完成,如客户需退款只能通过来客后台进行操作,当前后台不支持核销后退款操作,确定要执行吗?`, '提示', {
+                type: 'warning'
+            }).then(async () => {
+                var loading = this.$loading();
+                var resp = await this.$API.order.end.post({"order_id":data.order_id});
+                loading.close();
+                if (resp.code !== 1) {
+                    return this.$message.error(resp.msg);
+                }
+                this.$message.success(resp.msg);
+                this.$refs.table.refresh()
+            }).catch(() => {
+
+            })
+        },
+        table_express(data){
+            return this.$message.success("暂未开放");
+            this.$confirm(`呼叫快递成功后,可进入【待核销】栏目进行打印快递面单,如已接通云打印可忽略`, '提示', {
+                type: 'warning'
+            }).then(async ()=>{
+                var loading = this.$loading();
+                var resp = await this.$API.merOrder.express.post({"id":data.id});
+                loading.close();
+                if (resp.code == 0) {
+                    return this.$message.warning(resp.msg);
+                }
+                this.$message.success(resp.msg);
+                this.$refs.table.refresh()
+            }).catch(()=>{})
+        },
+        table_log(data){
+            this.$nextTick(() => {
+                this.$refs.logMain.open("edit").setData(data)
+            })
+        },
+        refresh(){
+            this.$refs.table.refresh()
+        },
+        upData(data){
+            this.$refs.table.upData(data)
+        },
+        handleSuccess(){
+            this.$refs.table.refresh()
+        },
+        sortChange(event){
+            if (event.order) {
+                var data = {
+                    "field":event.prop,
+                    "order":event.order
+                }
+                this.$refs.table.upData(data)
+            } else {
+                this.$refs.table.reload(this.searchKey)
+            }
+            return ;
+        },
+        selectionChange(event){
+            this.dataSelect = [];
+            var arr = [];
+            var arrCompany = [];
+            event.forEach(function(val,index){
+                arr[index] = val.id;
+                arrCompany[index] = val;
+            });
+            this.dataSelectFull = arrCompany;
+            this.dataSelect = arr;
+            this.$emit("success",this.dataSelect);
+            this.$emit("successFull",this.dataSelectFull);
+        },
+    }
+}
+</script>
+
+<style>
+.desc{
+    color: #999;
+    font-size: 12px;
+}
+.flex-btn{
+    display: flex;
+    flex-wrap: wrap;
+    gap: 5px;
+}
+.flex-tags {
+    display: flex;
+    gap: 2px;
+    flex-wrap: wrap;
+}
+.flex-btn .el-button.is-text{
+    margin-left: 0;
+}
+.flex-tags-size{
+    font-size: 12px;
+}
+.flex-tags-size span{
+    display: block;
+    margin-bottom: 5px;
+    color: #999;
+}
+</style>

+ 49 - 0
src/views/store/order/before/index.vue

@@ -0,0 +1,49 @@
+<template>
+    <el-container class="flex-column">
+        <div class="table-search">
+            <search @success="handleSuccess"></search>
+            <optionBtn @success="handleSuccess" :dataSelect="dataSelect" :dataSelectFull="dataSelectFull" type="3"></optionBtn>
+        </div>
+        <el-main class="nopadding">
+            <div class="table-container">
+                <tablePage ref="tablePage" @success="tableHandle" @successFull="tableHandleFull" type="3"></tablePage>
+            </div>
+        </el-main>
+    </el-container>  
+</template>
+
+<script>
+import search from './components/search';
+import optionBtn from './components/option';
+import tablePage from './components/table';
+export default {
+    components: {
+        search,tablePage,optionBtn
+    },
+    data(){
+        return {
+            searchKey:{
+                ex_status:2
+            },
+            dataSelect:[],
+            dataSelectFull:[],
+        }
+    },
+    methods: {
+        tableHandle(data){
+            this.dataSelect = data;
+        },
+        tableHandleFull(data){
+            this.dataSelectFull = data;
+        },
+        handleSuccess(data){
+            this.$refs.tablePage.upData(data)
+        },
+        handleClick(name){
+            this.activeName = name;
+            this.searchKey.type = name;
+            this.$refs.tablePage.upData(this.searchKey)
+        }
+    }
+}
+</script>

+ 64 - 0
src/views/store/order/components/log.vue

@@ -0,0 +1,64 @@
+<template>
+    <el-drawer :title="titleMap[mode]" :append-to-body="true" v-model="visible" :size="1000" destroy-on-close :close-on-click-modal="false" @closed="$emit('closed')" :with-header="false">
+        <el-container class="flex-column" v-loading="loading">
+            <div class="drawer-detail-main">
+                <div class="drawer-detail-header">
+                    <div class="drawer-detail-header-body">
+                        <div class="drawer-detail-header-left">{{ titleMap[mode] }}</div>
+                        <div class="drawer-detail-header-left">
+                            <el-button type="default" icon="el-icon-close" @click="visible=false"></el-button>
+                        </div>
+                    </div>
+                </div>
+            </div>
+            <el-main>
+                <el-timeline>
+                    <el-timeline-item :timestamp="item.create_at" center placement="top"  v-for="(item,index) in logData" :key="index">
+                        <el-card shadow="never">
+                            <template #header>{{ item.title }}</template>
+                            <p>{{ item.remark }}</p>
+                        </el-card>
+                    </el-timeline-item>
+                </el-timeline>
+            </el-main>
+            <el-footer style="text-align: right;">
+                <el-button @click="visible=false" >关 闭</el-button>
+            </el-footer>
+        </el-container>
+    </el-drawer>
+</template>
+
+<script>
+export default {
+    data(){
+        return {
+            loading: false,
+            mode:"add",
+            titleMap:{
+                add:"订单记录",
+                edit:"订单记录"
+            },
+            visible: false,
+            isSaveing: false,
+            logData:[]
+        }
+    },
+    methods:{
+        open(mode = 'add'){
+            this.mode = mode;
+            this.visible = true;
+            return this
+        },
+        //表单注入数据
+        setData(data){
+            this.getLogData(data);
+        },
+        async getLogData(order){
+            this.loading = true;
+            var resp = await this.$API.order.log.get({"order":order.order_id});
+            this.loading = false;
+            this.logData = resp.data;
+        }
+    }
+}
+</script>

+ 86 - 0
src/views/store/order/done/components/form.vue

@@ -0,0 +1,86 @@
+<template>
+    <el-dialog :title="titleMap[mode]" v-model="visible" :width="600" destroy-on-close @closed="$emit('closed')" :close-on-click-modal="false" :close-on-press-escape="false">
+        <el-form ref="dialogForm" :model="formData" :rules="rules" label-width="100px" label-position="top">
+            <el-form-item label="联系人" prop="username">
+                <el-input v-model="formData.username" clearable placeholder="请输入"></el-input>
+                <div class="el-form-item-msg"></div>
+            </el-form-item>
+            <el-form-item label="联系电话" prop="mobile">
+                <el-input v-model="formData.mobile" clearable placeholder="请输入"></el-input>
+                <div class="el-form-item-msg"></div>
+            </el-form-item>
+            <el-form-item label="详细地址" prop="address">
+                <el-input v-model="formData.address" clearable placeholder="请输入"></el-input>
+                <div class="el-form-item-msg"></div>
+            </el-form-item>
+        </el-form>
+		<template #footer>
+			<el-button @click="visible=false" >取 消</el-button>
+			<el-button type="primary" :loading="isSaveing" @click="submit()">提交</el-button>
+		</template>
+    </el-dialog>
+</template>
+<script>
+export default {
+    data(){
+        return {
+            loading: false,
+            mode:"add",
+            titleMap:{
+                add:"更新地址",
+                edit:"更新地址"
+            },
+            visible: false,
+            isSaveing: false,
+            formData:{},
+            submitState:false,
+            disabled:false,
+            rules:{
+                username: [
+                    {required: true, message: '请输入'}
+                ],
+                mobile: [
+                    {required: true, message: '请输入'}
+                ],
+                address: [
+                    {required: true, message: '请输入'}
+                ]
+            },
+            sms:""
+        }
+    },
+    methods:{
+        open(mode = 'add'){
+            this.mode = mode;
+            this.visible = true;
+            return this
+        },
+        //表单注入数据
+        setData(data){
+            data.address = data.region+data.address;
+            this.formData = data;
+        },
+        async submit(){
+            var validate = await this.$refs.dialogForm.validate().catch(()=>{});
+            if(!validate){ return false }
+            this.isSaveing = true;
+            let submitData = JSON.parse(JSON.stringify(this.formData));
+            var resp = await this.$API.order.save.post(submitData);
+            this.isSaveing = false;
+            if (resp.code !== 1) {
+                return this.$message.error(resp.msg);
+            }
+            this.$message.success(resp.msg);
+            this.visible = false;
+            this.formData = {};
+            this.submitState = false;
+            this.$emit("success");
+        }
+    }
+}
+</script>
+<style>
+.mt20 {margin-top: 20px;}
+.login-msg-yzm {display: flex;width: 100%;}
+.login-msg-yzm .el-button {margin-left: 10px;--el-button-size:42px;}
+</style>

+ 56 - 0
src/views/store/order/done/components/option.vue

@@ -0,0 +1,56 @@
+<template>
+    <fieldset>
+        <legend>
+            <el-tag type="info">按需操作</el-tag>
+        </legend>
+        <div class="op-header">
+            <div class="left-panel">
+                <sc-file-export :apiObj="$API.orderlife.export" :data="searchKey" :fileName="'来客订单_'+(new Date().getTime())" async>
+                    <template #default="{ open }">
+                        <el-button type="primary" icon="sc-icon-download" @click="open">导出</el-button>
+                    </template>
+                </sc-file-export>
+            </div>
+        </div>
+    </fieldset>
+</template>
+
+<script>
+import scFileExport from '@/components/scFileExport'
+export default {
+    components: {
+        scFileExport
+    },
+    props: {
+        type: { type: String, default: "1" },
+        dataSelect: { type: Array, default: () => [] },
+        searchKey: { type: Object, default: () => {} },
+        dataSelectFull: { type: Array, default: () => [] }
+    },
+    data(){
+        return {
+
+        }
+    },
+    methods: {
+        table_export(){
+            
+        },
+        async table_batch_status(status){
+            if (this.dataSelect.length == 0) {
+                return this.$message.error("请选择修改数据")
+            }
+            let submitData = {"id":this.dataSelect,"value":status,"field":"status","type":"batch"};
+            var resp = await this.$API.merGoods.batch.post(submitData);
+            if (resp.code == 0) {
+                return this.$message.error(resp.msg);
+            }
+            this.$message.success(resp.msg);
+            this.$emit("success");
+        },
+        handleSuccess(){
+            this.$emit("success");
+        },
+    }
+}
+</script>

+ 54 - 0
src/views/store/order/done/components/search.vue

@@ -0,0 +1,54 @@
+<template>
+    <fieldset>
+        <legend>
+            <el-tag type="info">条件筛选</el-tag>
+        </legend>
+        <el-form class="lv-form-inline" ref="searchForm" :model="searchKey" label-position="right" label-width="100px">
+            <div class="search-form">
+                <div class="form-left">
+                    <el-row :gutter="10">
+                        <el-col :span="this.$store.state.global.ismobile?12:4">
+                            <el-input v-model="searchKey.orderid" placeholder="订单编号" clearable :style="{ width: '100%' }" @keyup.enter="searchForm()">
+                                <template #prepend>订单编号</template>
+                            </el-input>
+                        </el-col>
+                        <el-col :span="this.$store.state.global.ismobile?12:4">
+                            <el-input v-model="searchKey.product" placeholder="商品ID" clearable :style="{ width: '100%' }" @keyup.enter="searchForm()">
+                                <template #prepend>商品ID</template>
+                            </el-input>
+                        </el-col>
+                        <el-col :span="this.$store.state.global.ismobile?12:4">
+                            <el-input v-model="searchKey.name" placeholder="商品标题" clearable :style="{ width: '100%' }" @keyup.enter="searchForm()">
+                                <template #prepend>商品标题</template>
+                            </el-input>
+                        </el-col>
+                        <el-col :span="this.$store.state.global.ismobile?12:4">
+                            <el-date-picker v-model="searchKey.create" :style="{width: '100%'}" placeholder="请选择创建时间" start-placeholder="开始时间" end-placeholder="结束时间" type="daterange" range-separator="至" @change="searchForm" />
+                        </el-col>
+                    </el-row>
+                </div>
+                <div class="form-line"></div>
+                <div class="form-right">
+                    <el-button type="primary" icon="el-icon-search" @click="searchForm">搜索</el-button>
+                </div>
+            </div>
+        </el-form>
+    </fieldset>
+</template>
+
+<script>
+export default {
+    data(){
+        return {
+            searchKey:{
+                ex_status:3
+            }
+        }
+    },
+    methods: {
+        searchForm(){
+            this.$emit("success",this.searchKey);
+        }
+    }
+}
+</script>

+ 229 - 0
src/views/store/order/done/components/table.vue

@@ -0,0 +1,229 @@
+<template>
+    <scTable ref="table" :apiObj="list.apiObj" :params="searchKey" @selectionChange="selectionChange" row-key="id">
+        <el-table-column type="selection" width="50" fixed="left"></el-table-column>
+        <el-table-column label="订单编号" prop="order_id" width="220" fixed="left">
+            <template #default="scope">
+                <span v-if="scope.row.order_id">{{ scope.row.order_id }}</span>
+                <span class="status-danger" v-else>未设置</span>
+            </template>
+        </el-table-column>
+        <el-table-column label="所属代理" prop="status" width="160">
+            <template #default="scope">
+                <span>{{ scope.row.agent?scope.row.agent.name:'-' }}</span>
+            </template>
+        </el-table-column>
+        <el-table-column label="所属店铺" prop="status" width="160">
+            <template #default="scope">
+                <span>{{ scope.row.store?scope.row.store.store_name:'-' }}</span>
+            </template>
+        </el-table-column>
+        <el-table-column label="订单类型" prop="status" width="120">
+            <template #default="scope">
+                <div class="status-danger" v-if="scope.row.service_type==1"><sc-status-indicator type="danger"></sc-status-indicator> 预约</div>
+                <div class="status-success" v-if="scope.row.service_type==2"><sc-status-indicator type="success"></sc-status-indicator> 快递</div>
+            </template>
+        </el-table-column>
+        <el-table-column label="收货地址" prop="company_id" width="120">
+            <template #default="scope">
+                <el-popover :width="200" placement="top-start">
+                    <template #reference>
+                        <div class="el-text">
+                            {{scope.row.username?scope.row.username:'-'}}
+                            <div class="desc" v-copy="'联系人:'+scope.row.username+'联系电话:'+scope.row.mobile+'联系地址:'+scope.row.region+scope.row.address"><span>一键复制</span></div>
+                        </div>
+                    </template>
+                    <div class="flex-tags-size">
+                        <span>联系人</span>{{scope.row.username?scope.row.username:'-'}}<br><br>
+                        <span>联系电话</span>{{scope.row.mobile?scope.row.mobile:'-'}}<br><br>
+                        <span>联系地址</span>{{scope.row.region?scope.row.region:'-'}}{{scope.row.address?scope.row.address:'-'}}
+                    </div>
+                </el-popover>
+            </template>
+        </el-table-column>
+        <el-table-column label="商品ID" prop="out_id" width="150">
+            <template #default="scope">
+                <span v-if="scope.row.product_id">{{ scope.row.product_id }}</span>
+                <span class="status-danger" v-else>未设置</span>
+            </template>
+        </el-table-column>
+        <el-table-column label="商品名称" prop="product_name" width="220">
+            <template #default="scope">
+                <span v-if="scope.row.product_name">{{ scope.row.product_name }}</span>
+                <span class="status-danger" v-else>未设置</span>
+            </template>
+        </el-table-column>
+        <el-table-column label="数量" prop="count" width="100">
+            <template #default="scope">
+                <span>{{ scope.row.parent.count }}件</span>
+            </template>
+        </el-table-column>
+        <el-table-column label="订单金额" prop="order_amount" width="150">
+            <template #default="scope">
+                <span v-if="scope.row.parent.order_amount">¥{{ scope.row.parent.order_amount }}</span>
+                <span class="status-danger" v-else>未设置</span>
+            </template>
+        </el-table-column>
+        <el-table-column label="支付金额" prop="pay_amount" width="150">
+            <template #default="scope">
+                <span v-if="scope.row.parent.pay_amount">¥{{ scope.row.parent.pay_amount }}</span>
+                <span class="status-danger" v-else>未设置</span>
+            </template>
+        </el-table-column>
+        <el-table-column label="状态" prop="status" width="180">
+            <template #default="scope">
+                <div class="status-danger" v-if="scope.row.express_status==0"><sc-status-indicator type="danger"></sc-status-indicator> 待发货</div>
+                <div class="status-success" v-if="scope.row.express_status==1"><sc-status-indicator type="success"></sc-status-indicator> 待核销</div>
+                <div class="status-danger" v-if="scope.row.express_status==2"><sc-status-indicator type="danger"></sc-status-indicator> 已完成</div>
+                <div class="status-info" v-if="scope.row.express_status==3"><sc-status-indicator type="info"></sc-status-indicator> 已取消</div>
+                <div class="status-info" v-if="scope.row.express_status==4"><sc-status-indicator type="info"></sc-status-indicator> 退款审核</div>
+                <div class="status-info" v-if="scope.row.express_status==5"><sc-status-indicator type="info"></sc-status-indicator> 拒绝退款</div>
+                <div v-if="scope.row.status==5 && scope.row.remark">{{ scope.row.remark }}</div>
+            </template>
+        </el-table-column>
+        <el-table-column label="创建时间" prop="create_at" width="180"></el-table-column>
+        <el-table-column label="操作" width="200" align="right" fixed="right">
+            <template #default="scope">
+                <el-button-group>
+                    <el-button text type="warning" size="small" @click="table_log(scope.row)">订单记录</el-button>
+                    <el-button text type="warning" size="small" @click="table_express(scope.row)" v-if="scope.row.express_status==0">呼叫快递</el-button>
+                    <el-button text type="warning" size="small" v-if="scope.row.express_status==1" @click="table_print(scope.row)">打印面单</el-button>
+                    <el-button text type="success" size="small" @click="table_end(scope.row)" v-if="scope.row.express_status==1">手动核销</el-button>
+                    <el-button text type="success" size="small" @click="table_passwd(scope.row)" v-if="scope.row.express_status==0 && scope.row.service_type==2">更新地址</el-button>
+                </el-button-group>
+            </template>
+        </el-table-column>
+    </scTable>
+    <formMain ref="formMain" @success="handleSuccess"></formMain>
+    <addMain ref="addMain" @success="handleSuccess"></addMain>
+    <logMain ref="logMain" @success="handleSuccess"></logMain>
+</template>
+
+<script>
+import formMain from './form';
+import addMain from "@/views/manage/components/send";
+import logMain from '@/views/manage/order/components/log'
+export default {
+    components: {
+        formMain,addMain,logMain
+    },
+    data(){
+        return {
+            list: {
+                apiObj: this.$API.order.list
+            },
+            dataSelect:[],
+            dataSelectFull:[],
+            searchKey:{
+                ex_status:3
+            }
+        }
+    },
+    methods: {
+        table_passwd(row){
+            return this.$message.success("暂未开放");
+            this.$nextTick(() => {
+                this.$refs.formMain.open("edit").setData(row)
+            })
+        },
+        table_end(data){
+            return this.$message.success("暂未开放");
+            this.$confirm(`核销后该笔订单即为完成,如客户需退款只能通过来客后台进行操作,当前后台不支持核销后退款操作,确定要执行吗?`, '提示', {
+                type: 'warning'
+            }).then(async () => {
+                var loading = this.$loading();
+                var resp = await this.$API.order.end.post({"order_id":data.order_id});
+                loading.close();
+                if (resp.code !== 1) {
+                    return this.$message.error(resp.msg);
+                }
+                this.$message.success(resp.msg);
+                this.$refs.table.refresh()
+            }).catch(() => {
+
+            })
+        },
+        table_express(data){
+            return this.$message.success("暂未开放");
+            this.$confirm(`呼叫快递成功后,可进入【待核销】栏目进行打印快递面单,如已接通云打印可忽略`, '提示', {
+                type: 'warning'
+            }).then(async ()=>{
+                var loading = this.$loading();
+                var resp = await this.$API.merOrder.express.post({"id":data.id});
+                loading.close();
+                if (resp.code == 0) {
+                    return this.$message.warning(resp.msg);
+                }
+                this.$message.success(resp.msg);
+                this.$refs.table.refresh()
+            }).catch(()=>{})
+        },
+        table_log(data){
+            this.$nextTick(() => {
+                this.$refs.logMain.open("edit").setData(data)
+            })
+        },
+        refresh(){
+            this.$refs.table.refresh()
+        },
+        upData(data){
+            this.$refs.table.upData(data)
+        },
+        handleSuccess(){
+            this.$refs.table.refresh()
+        },
+        sortChange(event){
+            if (event.order) {
+                var data = {
+                    "field":event.prop,
+                    "order":event.order
+                }
+                this.$refs.table.upData(data)
+            } else {
+                this.$refs.table.reload(this.searchKey)
+            }
+            return ;
+        },
+        selectionChange(event){
+            this.dataSelect = [];
+            var arr = [];
+            var arrCompany = [];
+            event.forEach(function(val,index){
+                arr[index] = val.id;
+                arrCompany[index] = val;
+            });
+            this.dataSelectFull = arrCompany;
+            this.dataSelect = arr;
+            this.$emit("success",this.dataSelect);
+            this.$emit("successFull",this.dataSelectFull);
+        },
+    }
+}
+</script>
+
+<style>
+.desc{
+    color: #999;
+    font-size: 12px;
+}
+.flex-btn{
+    display: flex;
+    flex-wrap: wrap;
+    gap: 5px;
+}
+.flex-tags {
+    display: flex;
+    gap: 2px;
+    flex-wrap: wrap;
+}
+.flex-btn .el-button.is-text{
+    margin-left: 0;
+}
+.flex-tags-size{
+    font-size: 12px;
+}
+.flex-tags-size span{
+    display: block;
+    margin-bottom: 5px;
+    color: #999;
+}
+</style>

+ 49 - 0
src/views/store/order/done/index.vue

@@ -0,0 +1,49 @@
+<template>
+    <el-container class="flex-column">
+        <div class="table-search">
+            <search @success="handleSuccess"></search>
+            <optionBtn @success="handleSuccess" :dataSelect="dataSelect" :dataSelectFull="dataSelectFull" type="3"></optionBtn>
+        </div>
+        <el-main class="nopadding">
+            <div class="table-container">
+                <tablePage ref="tablePage" @success="tableHandle" @successFull="tableHandleFull" type="3"></tablePage>
+            </div>
+        </el-main>
+    </el-container>  
+</template>
+
+<script>
+import search from './components/search';
+import optionBtn from './components/option';
+import tablePage from './components/table';
+export default {
+    components: {
+        search,tablePage,optionBtn
+    },
+    data(){
+        return {
+            searchKey:{
+                ex_status:3
+            },
+            dataSelect:[],
+            dataSelectFull:[],
+        }
+    },
+    methods: {
+        tableHandle(data){
+            this.dataSelect = data;
+        },
+        tableHandleFull(data){
+            this.dataSelectFull = data;
+        },
+        handleSuccess(data){
+            this.$refs.tablePage.upData(data)
+        },
+        handleClick(name){
+            this.activeName = name;
+            this.searchKey.type = name;
+            this.$refs.tablePage.upData(this.searchKey)
+        }
+    }
+}
+</script>

+ 60 - 0
src/views/store/order/life/components/form.vue

@@ -0,0 +1,60 @@
+<template>
+    <el-dialog :title="titleMap[mode]" v-model="visible" :width="600" destroy-on-close @closed="$emit('closed')" :close-on-click-modal="false" :close-on-press-escape="false">
+        <el-form ref="dialogForm" :model="formData" :rules="rules" label-width="100px" label-position="top">
+            <el-form-item label="短信内容">
+                <el-input v-model="sms" type="textarea" disabled readonly clearable placeholder="门店名称" rows="5"></el-input>
+                <div class="el-form-item-msg" style="margin-top: 10px;">
+                    <el-button v-copy="sms">复制</el-button>
+                </div>
+            </el-form-item>
+        </el-form>
+		<template #footer>
+			<el-button @click="visible=false" >关 闭</el-button>
+		</template>
+    </el-dialog>
+</template>
+<script>
+export default {
+    data(){
+        return {
+            loading: false,
+            mode:"add",
+            titleMap:{
+                add:"查看短信",
+                edit:"查看短信"
+            },
+            visible: false,
+            isSaveing: false,
+            formData:{},
+            submitState:false,
+            disabled:false,
+            rules:{},
+            sms:""
+        }
+    },
+    methods:{
+        open(mode = 'add'){
+            this.mode = mode;
+            this.visible = true;
+            return this
+        },
+        //表单注入数据
+        setData(data){
+            this.formData = data;
+            this.getSms();
+        },
+        async getSms(){
+            var resp = await this.$API.merOrderlife.sms.get({id:this.formData.id});
+            if (resp.code == 0) {
+                return this.$message.error(resp.msg);
+            }
+            this.sms = resp.data.sms;
+        }
+    }
+}
+</script>
+<style>
+.mt20 {margin-top: 20px;}
+.login-msg-yzm {display: flex;width: 100%;}
+.login-msg-yzm .el-button {margin-left: 10px;--el-button-size:42px;}
+</style>

+ 56 - 0
src/views/store/order/life/components/option.vue

@@ -0,0 +1,56 @@
+<template>
+    <fieldset>
+        <legend>
+            <el-tag type="info">按需操作</el-tag>
+        </legend>
+        <div class="op-header">
+            <div class="left-panel">
+                <sc-file-export :apiObj="$API.orderlife.export" :data="searchKey" :fileName="'来客订单_'+(new Date().getTime())" async>
+                    <template #default="{ open }">
+                        <el-button type="primary" icon="sc-icon-download" @click="open">导出</el-button>
+                    </template>
+                </sc-file-export>
+            </div>
+        </div>
+    </fieldset>
+</template>
+
+<script>
+import scFileExport from '@/components/scFileExport'
+export default {
+    components: {
+        scFileExport
+    },
+    props: {
+        type: { type: String, default: "1" },
+        dataSelect: { type: Array, default: () => [] },
+        searchKey: { type: Object, default: () => {} },
+        dataSelectFull: { type: Array, default: () => [] }
+    },
+    data(){
+        return {
+
+        }
+    },
+    methods: {
+        table_export(){
+            
+        },
+        async table_batch_status(status){
+            if (this.dataSelect.length == 0) {
+                return this.$message.error("请选择修改数据")
+            }
+            let submitData = {"id":this.dataSelect,"value":status,"field":"status","type":"batch"};
+            var resp = await this.$API.merGoods.batch.post(submitData);
+            if (resp.code == 0) {
+                return this.$message.error(resp.msg);
+            }
+            this.$message.success(resp.msg);
+            this.$emit("success");
+        },
+        handleSuccess(){
+            this.$emit("success");
+        },
+    }
+}
+</script>

+ 69 - 0
src/views/store/order/life/components/search.vue

@@ -0,0 +1,69 @@
+<template>
+    <fieldset>
+        <legend>
+            <el-tag type="info">条件筛选</el-tag>
+        </legend>
+        <el-form class="lv-form-inline" ref="searchForm" :model="searchKey" label-position="right" label-width="100px">
+            <div class="search-form">
+                <div class="form-left">
+                    <el-row :gutter="10">
+                        <el-col :span="this.$store.state.global.ismobile?12:4">
+                            <el-input v-model="searchKey.orderid" placeholder="订单编号" clearable :style="{ width: '100%' }" @keyup.enter="searchForm()">
+                                <template #prepend>订单编号</template>
+                            </el-input>
+                        </el-col>
+                        <el-col :span="this.$store.state.global.ismobile?12:4">
+                            <el-input v-model="searchKey.product" placeholder="商品ID" clearable :style="{ width: '100%' }" @keyup.enter="searchForm()">
+                                <template #prepend>商品ID</template>
+                            </el-input>
+                        </el-col>
+                        <el-col :span="this.$store.state.global.ismobile?12:4">
+                            <el-input v-model="searchKey.name" placeholder="商品标题" clearable :style="{ width: '100%' }" @keyup.enter="searchForm()">
+                                <template #prepend>商品标题</template>
+                            </el-input>
+                        </el-col>
+                        <el-col :span="this.$store.state.global.ismobile?12:4">
+                            <el-input v-model="searchKey.mobile" placeholder="手机号码" clearable :style="{ width: '100%' }" @keyup.enter="searchForm()">
+                                <template #prepend>手机号码</template>
+                            </el-input>
+                        </el-col>
+                        <el-col :span="this.$store.state.global.ismobile?12:4">
+                            <el-select v-model="searchKey.status" clearable placeholder="请选择状态" @change="searchForm" :style="{width: '100%'}" class="diy-select">
+                                <el-option value="1" label="待支付"></el-option>
+                                <el-option value="2" label="已支付"></el-option>
+                                <el-option value="3" label="待核销"></el-option>
+                                <el-option value="4" label="已核销"></el-option>
+                                <el-option value="5" label="已取消"></el-option>
+                                <el-option value="6" label="退款审核"></el-option>
+                                <el-option value="7" label="拒绝退款"></el-option>
+                                <template #prefix>状态</template>
+                            </el-select>
+                        </el-col>
+                        <el-col :span="this.$store.state.global.ismobile?12:4">
+                            <el-date-picker v-model="searchKey.create" :style="{width: '100%'}" placeholder="请选择创建时间" start-placeholder="开始时间" end-placeholder="结束时间" type="daterange" range-separator="至" @change="searchForm" />
+                        </el-col>
+                    </el-row>
+                </div>
+                <div class="form-line"></div>
+                <div class="form-right">
+                    <el-button type="primary" icon="el-icon-search" @click="searchForm">搜索</el-button>
+                </div>
+            </div>
+        </el-form>
+    </fieldset>
+</template>
+
+<script>
+export default {
+    data(){
+        return {
+            searchKey:{}
+        }
+    },
+    methods: {
+        searchForm(){
+            this.$emit("success",this.searchKey);
+        }
+    }
+}
+</script>

+ 169 - 0
src/views/store/order/life/components/table.vue

@@ -0,0 +1,169 @@
+<template>
+    <scTable ref="table" :apiObj="list.apiObj" :params="searchKey" @selectionChange="selectionChange" row-key="id">
+        <el-table-column type="selection" width="50" fixed="left"></el-table-column>
+        <el-table-column label="订单编号" prop="order_id" width="220" fixed="left">
+            <template #default="scope">
+                <span v-if="scope.row.order_id">{{ scope.row.order_id }}</span>
+                <span class="status-danger" v-else>未设置</span>
+            </template>
+        </el-table-column>
+        <el-table-column label="所属代理" prop="status" width="160">
+            <template #default="scope">
+                <span>{{ scope.row.agent?scope.row.agent.name:'-' }}</span>
+            </template>
+        </el-table-column>
+        <el-table-column label="所属店铺" prop="status" width="160">
+            <template #default="scope">
+                <span>{{ scope.row.store?scope.row.store.store_name:'-' }}</span>
+            </template>
+        </el-table-column>
+        <el-table-column label="用户ID" prop="open_id" width="320">
+            <template #default="scope">
+                <span v-if="scope.row.open_id">{{ scope.row.open_id }}</span>
+                <span class="status-danger" v-else>未设置</span>
+            </template>
+        </el-table-column>
+        <el-table-column label="商品ID" prop="out_id" width="150">
+            <template #default="scope">
+                <span v-if="scope.row.out_id">{{ scope.row.out_id }}</span>
+                <span class="status-danger" v-else>未设置</span>
+            </template>
+        </el-table-column>
+        <el-table-column label="商品名称" prop="product_name" width="220">
+            <template #default="scope">
+                <span v-if="scope.row.product_name">{{ scope.row.product_name }}</span>
+                <span class="status-danger" v-else>未设置</span>
+            </template>
+        </el-table-column>
+        <el-table-column label="数量" prop="count" width="100">
+            <template #default="scope">
+                <span>{{ scope.row.count }}件</span>
+            </template>
+        </el-table-column>
+        <el-table-column label="订单金额" prop="order_amount" width="150">
+            <template #default="scope">
+                <span v-if="scope.row.order_amount">¥{{ scope.row.order_amount }}</span>
+                <span class="status-danger" v-else>未设置</span>
+            </template>
+        </el-table-column>
+        <el-table-column label="支付金额" prop="pay_amount" width="150">
+            <template #default="scope">
+                <span v-if="scope.row.pay_amount">¥{{ scope.row.pay_amount }}</span>
+                <span class="status-danger" v-else>未设置</span>
+            </template>
+        </el-table-column>
+        <el-table-column label="状态" prop="status" width="180">
+            <template #default="scope">
+                <div class="status-danger" v-if="scope.row.status==0"><sc-status-indicator type="danger"></sc-status-indicator> 待支付</div>
+                <div class="status-success" v-if="scope.row.status==1"><sc-status-indicator type="success"></sc-status-indicator> 已支付</div>
+                <div class="status-danger" v-if="scope.row.status==2"><sc-status-indicator type="danger"></sc-status-indicator> 待核销</div>
+                <div class="status-info" v-if="scope.row.status==3"><sc-status-indicator type="info"></sc-status-indicator> 已核销</div>
+                <div class="status-info" v-if="scope.row.status==4"><sc-status-indicator type="info"></sc-status-indicator> 已取消</div>
+                <div class="status-info" v-if="scope.row.status==5"><sc-status-indicator type="info"></sc-status-indicator> 退款审核</div>
+                <div class="status-info" v-if="scope.row.status==6"><sc-status-indicator type="info"></sc-status-indicator> 拒绝退款</div>
+                <div v-if="scope.row.status==2 && scope.row.remark">{{ scope.row.remark }}</div>
+            </template>
+        </el-table-column>
+        <el-table-column label="支付时间" prop="pay_at" width="180">
+            <template #default="scope">
+                <span v-if="scope.row.pay_at">{{ scope.row.pay_at }}</span>
+                <span class="status-danger" v-else>-</span>
+            </template>
+
+        </el-table-column>
+        <el-table-column label="退款时间" prop="refund_at" width="180">
+            <template #default="scope">
+                <span v-if="scope.row.refund_at">{{ scope.row.refund_at }}</span>
+                <span class="status-danger" v-else>-</span>
+            </template>
+        </el-table-column>
+        <el-table-column label="创建时间" prop="create_at" width="180"></el-table-column>
+    </scTable>
+    <formMain ref="formMain" @success="handleSuccess"></formMain>
+    <addMain ref="addMain" @success="handleSuccess"></addMain>
+</template>
+
+<script>
+import formMain from './form';
+import addMain from "@/views/manage/components/send";
+export default {
+    components: {
+        formMain,addMain
+    },
+    data(){
+        return {
+            list: {
+                apiObj: this.$API.orderlife.list
+            },
+            dataSelect:[],
+            dataSelectFull:[],
+            searchKey:{}
+        }
+    },
+    methods: {
+        table_express(data){
+            this.$confirm(`手动录入核销订单后,开启自动呼叫快递订单将转移至【待核销】列表中,未开启则转移至【待发货】中`, '提示', {
+                type: 'warning'
+            }).then(() => {
+                this.$nextTick(() => {
+                    this.$refs.addMain.open("edit").setData(data)
+                })
+            }).catch(() => {
+
+            })
+        },
+        async table_send(data){
+            var resp = await this.$API.orderlife.del.post({"id":data.id});
+            if (resp.code == 0) {
+                return this.$message.error(resp.msg)
+            }
+            this.$message.success(resp.msg)
+            this.$refs.table.refresh()
+        },
+        table_view(data){
+            this.$nextTick(() => {
+                this.$refs.detailMain.open().setData(data)
+            })
+        },
+        refresh(){
+            this.$refs.table.refresh()
+        },
+        upData(data){
+            this.$refs.table.upData(data)
+        },
+        handleSuccess(){
+            this.$refs.table.refresh()
+        },
+        sortChange(event){
+            if (event.order) {
+                var data = {
+                    "field":event.prop,
+                    "order":event.order
+                }
+                this.$refs.table.upData(data)
+            } else {
+                this.$refs.table.reload(this.searchKey)
+            }
+            return ;
+        },
+        selectionChange(event){
+            this.dataSelect = [];
+            var arr = [];
+            var arrCompany = [];
+            event.forEach(function(val,index){
+                arr[index] = val.id;
+                arrCompany[index] = val;
+            });
+            this.dataSelectFull = arrCompany;
+            this.dataSelect = arr;
+            this.$emit("success",this.dataSelect);
+            this.$emit("successFull",this.dataSelectFull);
+        },
+        table_passwd(row){
+            this.$nextTick(() => {
+                this.$refs.formMain.open("edit").setData(row)
+            })
+        },
+    }
+}
+</script>

+ 49 - 0
src/views/store/order/life/index.vue

@@ -0,0 +1,49 @@
+<template>
+    <el-container class="flex-column">
+        <div class="table-search">
+            <search @success="handleSuccess"></search>
+            <optionBtn @success="handleSuccess" :dataSelect="dataSelect" :dataSelectFull="dataSelectFull" type="3"></optionBtn>
+        </div>
+        <el-main class="nopadding">
+            <div class="table-container">
+                <tablePage ref="tablePage" @success="tableHandle" @successFull="tableHandleFull" type="3"></tablePage>
+            </div>
+        </el-main>
+    </el-container>  
+</template>
+
+<script>
+import search from './components/search';
+import optionBtn from './components/option';
+import tablePage from './components/table';
+export default {
+    components: {
+        search,tablePage,optionBtn
+    },
+    data(){
+        return {
+            searchKey:{
+                status:7
+            },
+            dataSelect:[],
+            dataSelectFull:[],
+        }
+    },
+    methods: {
+        tableHandle(data){
+            this.dataSelect = data;
+        },
+        tableHandleFull(data){
+            this.dataSelectFull = data;
+        },
+        handleSuccess(data){
+            this.$refs.tablePage.upData(data)
+        },
+        handleClick(name){
+            this.activeName = name;
+            this.searchKey.type = name;
+            this.$refs.tablePage.upData(this.searchKey)
+        }
+    }
+}
+</script>

+ 86 - 0
src/views/store/order/refund/components/form.vue

@@ -0,0 +1,86 @@
+<template>
+    <el-dialog :title="titleMap[mode]" v-model="visible" :width="600" destroy-on-close @closed="$emit('closed')" :close-on-click-modal="false" :close-on-press-escape="false">
+        <el-form ref="dialogForm" :model="formData" :rules="rules" label-width="100px" label-position="top">
+            <el-form-item label="联系人" prop="username">
+                <el-input v-model="formData.username" clearable placeholder="请输入"></el-input>
+                <div class="el-form-item-msg"></div>
+            </el-form-item>
+            <el-form-item label="联系电话" prop="mobile">
+                <el-input v-model="formData.mobile" clearable placeholder="请输入"></el-input>
+                <div class="el-form-item-msg"></div>
+            </el-form-item>
+            <el-form-item label="详细地址" prop="address">
+                <el-input v-model="formData.address" clearable placeholder="请输入"></el-input>
+                <div class="el-form-item-msg"></div>
+            </el-form-item>
+        </el-form>
+		<template #footer>
+			<el-button @click="visible=false" >取 消</el-button>
+			<el-button type="primary" :loading="isSaveing" @click="submit()">提交</el-button>
+		</template>
+    </el-dialog>
+</template>
+<script>
+export default {
+    data(){
+        return {
+            loading: false,
+            mode:"add",
+            titleMap:{
+                add:"更新地址",
+                edit:"更新地址"
+            },
+            visible: false,
+            isSaveing: false,
+            formData:{},
+            submitState:false,
+            disabled:false,
+            rules:{
+                username: [
+                    {required: true, message: '请输入'}
+                ],
+                mobile: [
+                    {required: true, message: '请输入'}
+                ],
+                address: [
+                    {required: true, message: '请输入'}
+                ]
+            },
+            sms:""
+        }
+    },
+    methods:{
+        open(mode = 'add'){
+            this.mode = mode;
+            this.visible = true;
+            return this
+        },
+        //表单注入数据
+        setData(data){
+            data.address = data.region+data.address;
+            this.formData = data;
+        },
+        async submit(){
+            var validate = await this.$refs.dialogForm.validate().catch(()=>{});
+            if(!validate){ return false }
+            this.isSaveing = true;
+            let submitData = JSON.parse(JSON.stringify(this.formData));
+            var resp = await this.$API.order.save.post(submitData);
+            this.isSaveing = false;
+            if (resp.code !== 1) {
+                return this.$message.error(resp.msg);
+            }
+            this.$message.success(resp.msg);
+            this.visible = false;
+            this.formData = {};
+            this.submitState = false;
+            this.$emit("success");
+        }
+    }
+}
+</script>
+<style>
+.mt20 {margin-top: 20px;}
+.login-msg-yzm {display: flex;width: 100%;}
+.login-msg-yzm .el-button {margin-left: 10px;--el-button-size:42px;}
+</style>

+ 56 - 0
src/views/store/order/refund/components/option.vue

@@ -0,0 +1,56 @@
+<template>
+    <fieldset>
+        <legend>
+            <el-tag type="info">按需操作</el-tag>
+        </legend>
+        <div class="op-header">
+            <div class="left-panel">
+                <sc-file-export :apiObj="$API.orderlife.export" :data="searchKey" :fileName="'来客订单_'+(new Date().getTime())" async>
+                    <template #default="{ open }">
+                        <el-button type="primary" icon="sc-icon-download" @click="open">导出</el-button>
+                    </template>
+                </sc-file-export>
+            </div>
+        </div>
+    </fieldset>
+</template>
+
+<script>
+import scFileExport from '@/components/scFileExport'
+export default {
+    components: {
+        scFileExport
+    },
+    props: {
+        type: { type: String, default: "1" },
+        dataSelect: { type: Array, default: () => [] },
+        searchKey: { type: Object, default: () => {} },
+        dataSelectFull: { type: Array, default: () => [] }
+    },
+    data(){
+        return {
+
+        }
+    },
+    methods: {
+        table_export(){
+            
+        },
+        async table_batch_status(status){
+            if (this.dataSelect.length == 0) {
+                return this.$message.error("请选择修改数据")
+            }
+            let submitData = {"id":this.dataSelect,"value":status,"field":"status","type":"batch"};
+            var resp = await this.$API.merGoods.batch.post(submitData);
+            if (resp.code == 0) {
+                return this.$message.error(resp.msg);
+            }
+            this.$message.success(resp.msg);
+            this.$emit("success");
+        },
+        handleSuccess(){
+            this.$emit("success");
+        },
+    }
+}
+</script>

+ 54 - 0
src/views/store/order/refund/components/search.vue

@@ -0,0 +1,54 @@
+<template>
+    <fieldset>
+        <legend>
+            <el-tag type="info">条件筛选</el-tag>
+        </legend>
+        <el-form class="lv-form-inline" ref="searchForm" :model="searchKey" label-position="right" label-width="100px">
+            <div class="search-form">
+                <div class="form-left">
+                    <el-row :gutter="10">
+                        <el-col :span="this.$store.state.global.ismobile?12:4">
+                            <el-input v-model="searchKey.orderid" placeholder="订单编号" clearable :style="{ width: '100%' }" @keyup.enter="searchForm()">
+                                <template #prepend>订单编号</template>
+                            </el-input>
+                        </el-col>
+                        <el-col :span="this.$store.state.global.ismobile?12:4">
+                            <el-input v-model="searchKey.product" placeholder="商品ID" clearable :style="{ width: '100%' }" @keyup.enter="searchForm()">
+                                <template #prepend>商品ID</template>
+                            </el-input>
+                        </el-col>
+                        <el-col :span="this.$store.state.global.ismobile?12:4">
+                            <el-input v-model="searchKey.name" placeholder="商品标题" clearable :style="{ width: '100%' }" @keyup.enter="searchForm()">
+                                <template #prepend>商品标题</template>
+                            </el-input>
+                        </el-col>
+                        <el-col :span="this.$store.state.global.ismobile?12:4">
+                            <el-date-picker v-model="searchKey.create" :style="{width: '100%'}" placeholder="请选择创建时间" start-placeholder="开始时间" end-placeholder="结束时间" type="daterange" range-separator="至" @change="searchForm" />
+                        </el-col>
+                    </el-row>
+                </div>
+                <div class="form-line"></div>
+                <div class="form-right">
+                    <el-button type="primary" icon="el-icon-search" @click="searchForm">搜索</el-button>
+                </div>
+            </div>
+        </el-form>
+    </fieldset>
+</template>
+
+<script>
+export default {
+    data(){
+        return {
+            searchKey:{
+                ex_status:4
+            }
+        }
+    },
+    methods: {
+        searchForm(){
+            this.$emit("success",this.searchKey);
+        }
+    }
+}
+</script>

+ 229 - 0
src/views/store/order/refund/components/table.vue

@@ -0,0 +1,229 @@
+<template>
+    <scTable ref="table" :apiObj="list.apiObj" :params="searchKey" @selectionChange="selectionChange" row-key="id">
+        <el-table-column type="selection" width="50" fixed="left"></el-table-column>
+        <el-table-column label="订单编号" prop="order_id" width="220" fixed="left">
+            <template #default="scope">
+                <span v-if="scope.row.order_id">{{ scope.row.order_id }}</span>
+                <span class="status-danger" v-else>未设置</span>
+            </template>
+        </el-table-column>
+        <el-table-column label="所属代理" prop="status" width="160">
+            <template #default="scope">
+                <span>{{ scope.row.agent?scope.row.agent.name:'-' }}</span>
+            </template>
+        </el-table-column>
+        <el-table-column label="所属店铺" prop="status" width="160">
+            <template #default="scope">
+                <span>{{ scope.row.store?scope.row.store.store_name:'-' }}</span>
+            </template>
+        </el-table-column>
+        <el-table-column label="订单类型" prop="status" width="120">
+            <template #default="scope">
+                <div class="status-danger" v-if="scope.row.service_type==1"><sc-status-indicator type="danger"></sc-status-indicator> 预约</div>
+                <div class="status-success" v-if="scope.row.service_type==2"><sc-status-indicator type="success"></sc-status-indicator> 快递</div>
+            </template>
+        </el-table-column>
+        <el-table-column label="收货地址" prop="company_id" width="120">
+            <template #default="scope">
+                <el-popover :width="200" placement="top-start">
+                    <template #reference>
+                        <div class="el-text">
+                            {{scope.row.username?scope.row.username:'-'}}
+                            <div class="desc" v-copy="'联系人:'+scope.row.username+'联系电话:'+scope.row.mobile+'联系地址:'+scope.row.region+scope.row.address"><span>一键复制</span></div>
+                        </div>
+                    </template>
+                    <div class="flex-tags-size">
+                        <span>联系人</span>{{scope.row.username?scope.row.username:'-'}}<br><br>
+                        <span>联系电话</span>{{scope.row.mobile?scope.row.mobile:'-'}}<br><br>
+                        <span>联系地址</span>{{scope.row.region?scope.row.region:'-'}}{{scope.row.address?scope.row.address:'-'}}
+                    </div>
+                </el-popover>
+            </template>
+        </el-table-column>
+        <el-table-column label="商品ID" prop="out_id" width="150">
+            <template #default="scope">
+                <span v-if="scope.row.product_id">{{ scope.row.product_id }}</span>
+                <span class="status-danger" v-else>未设置</span>
+            </template>
+        </el-table-column>
+        <el-table-column label="商品名称" prop="product_name" width="220">
+            <template #default="scope">
+                <span v-if="scope.row.product_name">{{ scope.row.product_name }}</span>
+                <span class="status-danger" v-else>未设置</span>
+            </template>
+        </el-table-column>
+        <el-table-column label="数量" prop="count" width="100">
+            <template #default="scope">
+                <span>{{ scope.row.parent.count }}件</span>
+            </template>
+        </el-table-column>
+        <el-table-column label="订单金额" prop="order_amount" width="150">
+            <template #default="scope">
+                <span v-if="scope.row.parent.order_amount">¥{{ scope.row.parent.order_amount }}</span>
+                <span class="status-danger" v-else>未设置</span>
+            </template>
+        </el-table-column>
+        <el-table-column label="支付金额" prop="pay_amount" width="150">
+            <template #default="scope">
+                <span v-if="scope.row.parent.pay_amount">¥{{ scope.row.parent.pay_amount }}</span>
+                <span class="status-danger" v-else>未设置</span>
+            </template>
+        </el-table-column>
+        <el-table-column label="状态" prop="status" width="180">
+            <template #default="scope">
+                <div class="status-danger" v-if="scope.row.express_status==0"><sc-status-indicator type="danger"></sc-status-indicator> 待发货</div>
+                <div class="status-success" v-if="scope.row.express_status==1"><sc-status-indicator type="success"></sc-status-indicator> 待核销</div>
+                <div class="status-danger" v-if="scope.row.express_status==2"><sc-status-indicator type="danger"></sc-status-indicator> 已完成</div>
+                <div class="status-info" v-if="scope.row.express_status==3"><sc-status-indicator type="info"></sc-status-indicator> 已取消</div>
+                <div class="status-info" v-if="scope.row.express_status==4"><sc-status-indicator type="info"></sc-status-indicator> 退款审核</div>
+                <div class="status-info" v-if="scope.row.express_status==5"><sc-status-indicator type="info"></sc-status-indicator> 拒绝退款</div>
+                <div v-if="scope.row.status==5 && scope.row.remark">{{ scope.row.remark }}</div>
+            </template>
+        </el-table-column>
+        <el-table-column label="创建时间" prop="create_at" width="180"></el-table-column>
+        <el-table-column label="操作" width="200" align="right" fixed="right">
+            <template #default="scope">
+                <el-button-group>
+                    <el-button text type="warning" size="small" @click="table_log(scope.row)">订单记录</el-button>
+                    <el-button text type="warning" size="small" @click="table_express(scope.row)" v-if="scope.row.express_status==0">呼叫快递</el-button>
+                    <el-button text type="warning" size="small" v-if="scope.row.express_status==1" @click="table_print(scope.row)">打印面单</el-button>
+                    <el-button text type="success" size="small" @click="table_end(scope.row)" v-if="scope.row.express_status==1">手动核销</el-button>
+                    <el-button text type="success" size="small" @click="table_passwd(scope.row)" v-if="scope.row.express_status==0 && scope.row.service_type==2">更新地址</el-button>
+                </el-button-group>
+            </template>
+        </el-table-column>
+    </scTable>
+    <formMain ref="formMain" @success="handleSuccess"></formMain>
+    <addMain ref="addMain" @success="handleSuccess"></addMain>
+    <logMain ref="logMain" @success="handleSuccess"></logMain>
+</template>
+
+<script>
+import formMain from './form';
+import addMain from "@/views/manage/components/send";
+import logMain from '@/views/manage/order/components/log'
+export default {
+    components: {
+        formMain,addMain,logMain
+    },
+    data(){
+        return {
+            list: {
+                apiObj: this.$API.order.list
+            },
+            dataSelect:[],
+            dataSelectFull:[],
+            searchKey:{
+                ex_status:4
+            }
+        }
+    },
+    methods: {
+        table_passwd(row){
+            return this.$message.success("暂未开放");
+            this.$nextTick(() => {
+                this.$refs.formMain.open("edit").setData(row)
+            })
+        },
+        table_end(data){
+            return this.$message.success("暂未开放");
+            this.$confirm(`核销后该笔订单即为完成,如客户需退款只能通过来客后台进行操作,当前后台不支持核销后退款操作,确定要执行吗?`, '提示', {
+                type: 'warning'
+            }).then(async () => {
+                var loading = this.$loading();
+                var resp = await this.$API.order.end.post({"order_id":data.order_id});
+                loading.close();
+                if (resp.code !== 1) {
+                    return this.$message.error(resp.msg);
+                }
+                this.$message.success(resp.msg);
+                this.$refs.table.refresh()
+            }).catch(() => {
+
+            })
+        },
+        table_express(data){
+            return this.$message.success("暂未开放");
+            this.$confirm(`呼叫快递成功后,可进入【待核销】栏目进行打印快递面单,如已接通云打印可忽略`, '提示', {
+                type: 'warning'
+            }).then(async ()=>{
+                var loading = this.$loading();
+                var resp = await this.$API.merOrder.express.post({"id":data.id});
+                loading.close();
+                if (resp.code == 0) {
+                    return this.$message.warning(resp.msg);
+                }
+                this.$message.success(resp.msg);
+                this.$refs.table.refresh()
+            }).catch(()=>{})
+        },
+        table_log(data){
+            this.$nextTick(() => {
+                this.$refs.logMain.open("edit").setData(data)
+            })
+        },
+        refresh(){
+            this.$refs.table.refresh()
+        },
+        upData(data){
+            this.$refs.table.upData(data)
+        },
+        handleSuccess(){
+            this.$refs.table.refresh()
+        },
+        sortChange(event){
+            if (event.order) {
+                var data = {
+                    "field":event.prop,
+                    "order":event.order
+                }
+                this.$refs.table.upData(data)
+            } else {
+                this.$refs.table.reload(this.searchKey)
+            }
+            return ;
+        },
+        selectionChange(event){
+            this.dataSelect = [];
+            var arr = [];
+            var arrCompany = [];
+            event.forEach(function(val,index){
+                arr[index] = val.id;
+                arrCompany[index] = val;
+            });
+            this.dataSelectFull = arrCompany;
+            this.dataSelect = arr;
+            this.$emit("success",this.dataSelect);
+            this.$emit("successFull",this.dataSelectFull);
+        },
+    }
+}
+</script>
+
+<style>
+.desc{
+    color: #999;
+    font-size: 12px;
+}
+.flex-btn{
+    display: flex;
+    flex-wrap: wrap;
+    gap: 5px;
+}
+.flex-tags {
+    display: flex;
+    gap: 2px;
+    flex-wrap: wrap;
+}
+.flex-btn .el-button.is-text{
+    margin-left: 0;
+}
+.flex-tags-size{
+    font-size: 12px;
+}
+.flex-tags-size span{
+    display: block;
+    margin-bottom: 5px;
+    color: #999;
+}
+</style>

+ 50 - 0
src/views/store/order/refund/index.vue

@@ -0,0 +1,50 @@
+<template>
+    <el-container class="flex-column">
+        <div class="table-search">
+            <search @success="handleSuccess"></search>
+            <el-alert type="warning" show-icon title="栏目提醒" description="已解锁并不代表用户该笔订单已退款,用户可以再次进入小程序进行预约" :closable="false" style="margin-bottom: 10px;"></el-alert>
+            <optionBtn @success="handleSuccess" :dataSelect="dataSelect" :dataSelectFull="dataSelectFull" type="3"></optionBtn>
+        </div>
+        <el-main class="nopadding">
+            <div class="table-container">
+                <tablePage ref="tablePage" @success="tableHandle" @successFull="tableHandleFull" type="3"></tablePage>
+            </div>
+        </el-main>
+    </el-container>  
+</template>
+
+<script>
+import search from './components/search';
+import optionBtn from './components/option';
+import tablePage from './components/table';
+export default {
+    components: {
+        search,tablePage,optionBtn
+    },
+    data(){
+        return {
+            searchKey:{
+                ex_status:4
+            },
+            dataSelect:[],
+            dataSelectFull:[],
+        }
+    },
+    methods: {
+        tableHandle(data){
+            this.dataSelect = data;
+        },
+        tableHandleFull(data){
+            this.dataSelectFull = data;
+        },
+        handleSuccess(data){
+            this.$refs.tablePage.upData(data)
+        },
+        handleClick(name){
+            this.activeName = name;
+            this.searchKey.type = name;
+            this.$refs.tablePage.upData(this.searchKey)
+        }
+    }
+}
+</script>

+ 86 - 0
src/views/store/order/send/components/form.vue

@@ -0,0 +1,86 @@
+<template>
+    <el-dialog :title="titleMap[mode]" v-model="visible" :width="600" destroy-on-close @closed="$emit('closed')" :close-on-click-modal="false" :close-on-press-escape="false">
+        <el-form ref="dialogForm" :model="formData" :rules="rules" label-width="100px" label-position="top">
+            <el-form-item label="联系人" prop="username">
+                <el-input v-model="formData.username" clearable placeholder="请输入"></el-input>
+                <div class="el-form-item-msg"></div>
+            </el-form-item>
+            <el-form-item label="联系电话" prop="mobile">
+                <el-input v-model="formData.mobile" clearable placeholder="请输入"></el-input>
+                <div class="el-form-item-msg"></div>
+            </el-form-item>
+            <el-form-item label="详细地址" prop="address">
+                <el-input v-model="formData.address" clearable placeholder="请输入"></el-input>
+                <div class="el-form-item-msg"></div>
+            </el-form-item>
+        </el-form>
+		<template #footer>
+			<el-button @click="visible=false" >取 消</el-button>
+			<el-button type="primary" :loading="isSaveing" @click="submit()">提交</el-button>
+		</template>
+    </el-dialog>
+</template>
+<script>
+export default {
+    data(){
+        return {
+            loading: false,
+            mode:"add",
+            titleMap:{
+                add:"更新地址",
+                edit:"更新地址"
+            },
+            visible: false,
+            isSaveing: false,
+            formData:{},
+            submitState:false,
+            disabled:false,
+            rules:{
+                username: [
+                    {required: true, message: '请输入'}
+                ],
+                mobile: [
+                    {required: true, message: '请输入'}
+                ],
+                address: [
+                    {required: true, message: '请输入'}
+                ]
+            },
+            sms:""
+        }
+    },
+    methods:{
+        open(mode = 'add'){
+            this.mode = mode;
+            this.visible = true;
+            return this
+        },
+        //表单注入数据
+        setData(data){
+            data.address = data.region+data.address;
+            this.formData = data;
+        },
+        async submit(){
+            var validate = await this.$refs.dialogForm.validate().catch(()=>{});
+            if(!validate){ return false }
+            this.isSaveing = true;
+            let submitData = JSON.parse(JSON.stringify(this.formData));
+            var resp = await this.$API.order.save.post(submitData);
+            this.isSaveing = false;
+            if (resp.code !== 1) {
+                return this.$message.error(resp.msg);
+            }
+            this.$message.success(resp.msg);
+            this.visible = false;
+            this.formData = {};
+            this.submitState = false;
+            this.$emit("success");
+        }
+    }
+}
+</script>
+<style>
+.mt20 {margin-top: 20px;}
+.login-msg-yzm {display: flex;width: 100%;}
+.login-msg-yzm .el-button {margin-left: 10px;--el-button-size:42px;}
+</style>

+ 56 - 0
src/views/store/order/send/components/option.vue

@@ -0,0 +1,56 @@
+<template>
+    <fieldset>
+        <legend>
+            <el-tag type="info">按需操作</el-tag>
+        </legend>
+        <div class="op-header">
+            <div class="left-panel">
+                <sc-file-export :apiObj="$API.orderlife.export" :data="searchKey" :fileName="'来客订单_'+(new Date().getTime())" async>
+                    <template #default="{ open }">
+                        <el-button type="primary" icon="sc-icon-download" @click="open">导出</el-button>
+                    </template>
+                </sc-file-export>
+            </div>
+        </div>
+    </fieldset>
+</template>
+
+<script>
+import scFileExport from '@/components/scFileExport'
+export default {
+    components: {
+        scFileExport
+    },
+    props: {
+        type: { type: String, default: "1" },
+        dataSelect: { type: Array, default: () => [] },
+        searchKey: { type: Object, default: () => {} },
+        dataSelectFull: { type: Array, default: () => [] }
+    },
+    data(){
+        return {
+
+        }
+    },
+    methods: {
+        table_export(){
+            
+        },
+        async table_batch_status(status){
+            if (this.dataSelect.length == 0) {
+                return this.$message.error("请选择修改数据")
+            }
+            let submitData = {"id":this.dataSelect,"value":status,"field":"status","type":"batch"};
+            var resp = await this.$API.merGoods.batch.post(submitData);
+            if (resp.code == 0) {
+                return this.$message.error(resp.msg);
+            }
+            this.$message.success(resp.msg);
+            this.$emit("success");
+        },
+        handleSuccess(){
+            this.$emit("success");
+        },
+    }
+}
+</script>

+ 54 - 0
src/views/store/order/send/components/search.vue

@@ -0,0 +1,54 @@
+<template>
+    <fieldset>
+        <legend>
+            <el-tag type="info">条件筛选</el-tag>
+        </legend>
+        <el-form class="lv-form-inline" ref="searchForm" :model="searchKey" label-position="right" label-width="100px">
+            <div class="search-form">
+                <div class="form-left">
+                    <el-row :gutter="10">
+                        <el-col :span="this.$store.state.global.ismobile?12:4">
+                            <el-input v-model="searchKey.orderid" placeholder="订单编号" clearable :style="{ width: '100%' }" @keyup.enter="searchForm()">
+                                <template #prepend>订单编号</template>
+                            </el-input>
+                        </el-col>
+                        <el-col :span="this.$store.state.global.ismobile?12:4">
+                            <el-input v-model="searchKey.product" placeholder="商品ID" clearable :style="{ width: '100%' }" @keyup.enter="searchForm()">
+                                <template #prepend>商品ID</template>
+                            </el-input>
+                        </el-col>
+                        <el-col :span="this.$store.state.global.ismobile?12:4">
+                            <el-input v-model="searchKey.name" placeholder="商品标题" clearable :style="{ width: '100%' }" @keyup.enter="searchForm()">
+                                <template #prepend>商品标题</template>
+                            </el-input>
+                        </el-col>
+                        <el-col :span="this.$store.state.global.ismobile?12:4">
+                            <el-date-picker v-model="searchKey.create" :style="{width: '100%'}" placeholder="请选择创建时间" start-placeholder="开始时间" end-placeholder="结束时间" type="daterange" range-separator="至" @change="searchForm" />
+                        </el-col>
+                    </el-row>
+                </div>
+                <div class="form-line"></div>
+                <div class="form-right">
+                    <el-button type="primary" icon="el-icon-search" @click="searchForm">搜索</el-button>
+                </div>
+            </div>
+        </el-form>
+    </fieldset>
+</template>
+
+<script>
+export default {
+    data(){
+        return {
+            searchKey:{
+                ex_status:1
+            }
+        }
+    },
+    methods: {
+        searchForm(){
+            this.$emit("success",this.searchKey);
+        }
+    }
+}
+</script>

+ 229 - 0
src/views/store/order/send/components/table.vue

@@ -0,0 +1,229 @@
+<template>
+    <scTable ref="table" :apiObj="list.apiObj" :params="searchKey" @selectionChange="selectionChange" row-key="id">
+        <el-table-column type="selection" width="50" fixed="left"></el-table-column>
+        <el-table-column label="订单编号" prop="order_id" width="220" fixed="left">
+            <template #default="scope">
+                <span v-if="scope.row.order_id">{{ scope.row.order_id }}</span>
+                <span class="status-danger" v-else>未设置</span>
+            </template>
+        </el-table-column>
+        <el-table-column label="所属代理" prop="status" width="160">
+            <template #default="scope">
+                <span>{{ scope.row.agent?scope.row.agent.name:'-' }}</span>
+            </template>
+        </el-table-column>
+        <el-table-column label="所属店铺" prop="status" width="160">
+            <template #default="scope">
+                <span>{{ scope.row.store?scope.row.store.store_name:'-' }}</span>
+            </template>
+        </el-table-column>
+        <el-table-column label="订单类型" prop="status" width="120">
+            <template #default="scope">
+                <div class="status-danger" v-if="scope.row.service_type==1"><sc-status-indicator type="danger"></sc-status-indicator> 预约</div>
+                <div class="status-success" v-if="scope.row.service_type==2"><sc-status-indicator type="success"></sc-status-indicator> 快递</div>
+            </template>
+        </el-table-column>
+        <el-table-column label="收货地址" prop="company_id" width="120">
+            <template #default="scope">
+                <el-popover :width="200" placement="top-start">
+                    <template #reference>
+                        <div class="el-text">
+                            {{scope.row.username?scope.row.username:'-'}}
+                            <div class="desc" v-copy="'联系人:'+scope.row.username+'联系电话:'+scope.row.mobile+'联系地址:'+scope.row.region+scope.row.address"><span>一键复制</span></div>
+                        </div>
+                    </template>
+                    <div class="flex-tags-size">
+                        <span>联系人</span>{{scope.row.username?scope.row.username:'-'}}<br><br>
+                        <span>联系电话</span>{{scope.row.mobile?scope.row.mobile:'-'}}<br><br>
+                        <span>联系地址</span>{{scope.row.region?scope.row.region:'-'}}{{scope.row.address?scope.row.address:'-'}}
+                    </div>
+                </el-popover>
+            </template>
+        </el-table-column>
+        <el-table-column label="商品ID" prop="out_id" width="150">
+            <template #default="scope">
+                <span v-if="scope.row.product_id">{{ scope.row.product_id }}</span>
+                <span class="status-danger" v-else>未设置</span>
+            </template>
+        </el-table-column>
+        <el-table-column label="商品名称" prop="product_name" width="220">
+            <template #default="scope">
+                <span v-if="scope.row.product_name">{{ scope.row.product_name }}</span>
+                <span class="status-danger" v-else>未设置</span>
+            </template>
+        </el-table-column>
+        <el-table-column label="数量" prop="count" width="100">
+            <template #default="scope">
+                <span>{{ scope.row.parent.count }}件</span>
+            </template>
+        </el-table-column>
+        <el-table-column label="订单金额" prop="order_amount" width="150">
+            <template #default="scope">
+                <span v-if="scope.row.parent.order_amount">¥{{ scope.row.parent.order_amount }}</span>
+                <span class="status-danger" v-else>未设置</span>
+            </template>
+        </el-table-column>
+        <el-table-column label="支付金额" prop="pay_amount" width="150">
+            <template #default="scope">
+                <span v-if="scope.row.parent.pay_amount">¥{{ scope.row.parent.pay_amount }}</span>
+                <span class="status-danger" v-else>未设置</span>
+            </template>
+        </el-table-column>
+        <el-table-column label="状态" prop="status" width="180">
+            <template #default="scope">
+                <div class="status-danger" v-if="scope.row.express_status==0"><sc-status-indicator type="danger"></sc-status-indicator> 待发货</div>
+                <div class="status-success" v-if="scope.row.express_status==1"><sc-status-indicator type="success"></sc-status-indicator> 待核销</div>
+                <div class="status-danger" v-if="scope.row.express_status==2"><sc-status-indicator type="danger"></sc-status-indicator> 已完成</div>
+                <div class="status-info" v-if="scope.row.express_status==3"><sc-status-indicator type="info"></sc-status-indicator> 已取消</div>
+                <div class="status-info" v-if="scope.row.express_status==4"><sc-status-indicator type="info"></sc-status-indicator> 退款审核</div>
+                <div class="status-info" v-if="scope.row.express_status==5"><sc-status-indicator type="info"></sc-status-indicator> 拒绝退款</div>
+                <div v-if="scope.row.status==5 && scope.row.remark">{{ scope.row.remark }}</div>
+            </template>
+        </el-table-column>
+        <el-table-column label="创建时间" prop="create_at" width="180"></el-table-column>
+        <el-table-column label="操作" width="200" align="right" fixed="right">
+            <template #default="scope">
+                <el-button-group>
+                    <el-button text type="warning" size="small" @click="table_log(scope.row)">订单记录</el-button>
+                    <el-button text type="warning" size="small" @click="table_express(scope.row)" v-if="scope.row.express_status==0">呼叫快递</el-button>
+                    <el-button text type="warning" size="small" v-if="scope.row.express_status==1" @click="table_print(scope.row)">打印面单</el-button>
+                    <el-button text type="success" size="small" @click="table_end(scope.row)" v-if="scope.row.express_status==1">手动核销</el-button>
+                    <el-button text type="success" size="small" @click="table_passwd(scope.row)" v-if="scope.row.express_status==0 && scope.row.service_type==2">更新地址</el-button>
+                </el-button-group>
+            </template>
+        </el-table-column>
+    </scTable>
+    <formMain ref="formMain" @success="handleSuccess"></formMain>
+    <addMain ref="addMain" @success="handleSuccess"></addMain>
+    <logMain ref="logMain" @success="handleSuccess"></logMain>
+</template>
+
+<script>
+import formMain from './form';
+import addMain from "@/views/manage/components/send";
+import logMain from '@/views/manage/order/components/log'
+export default {
+    components: {
+        formMain,addMain,logMain
+    },
+    data(){
+        return {
+            list: {
+                apiObj: this.$API.order.list
+            },
+            dataSelect:[],
+            dataSelectFull:[],
+            searchKey:{
+                ex_status:1
+            }
+        }
+    },
+    methods: {
+        table_passwd(row){
+            return this.$message.success("暂未开放");
+            this.$nextTick(() => {
+                this.$refs.formMain.open("edit").setData(row)
+            })
+        },
+        table_end(data){
+            return this.$message.success("暂未开放");
+            this.$confirm(`核销后该笔订单即为完成,如客户需退款只能通过来客后台进行操作,当前后台不支持核销后退款操作,确定要执行吗?`, '提示', {
+                type: 'warning'
+            }).then(async () => {
+                var loading = this.$loading();
+                var resp = await this.$API.order.end.post({"order_id":data.order_id});
+                loading.close();
+                if (resp.code !== 1) {
+                    return this.$message.error(resp.msg);
+                }
+                this.$message.success(resp.msg);
+                this.$refs.table.refresh()
+            }).catch(() => {
+
+            })
+        },
+        table_express(data){
+            return this.$message.success("暂未开放");
+            this.$confirm(`呼叫快递成功后,可进入【待核销】栏目进行打印快递面单,如已接通云打印可忽略`, '提示', {
+                type: 'warning'
+            }).then(async ()=>{
+                var loading = this.$loading();
+                var resp = await this.$API.merOrder.express.post({"id":data.id});
+                loading.close();
+                if (resp.code == 0) {
+                    return this.$message.warning(resp.msg);
+                }
+                this.$message.success(resp.msg);
+                this.$refs.table.refresh()
+            }).catch(()=>{})
+        },
+        table_log(data){
+            this.$nextTick(() => {
+                this.$refs.logMain.open("edit").setData(data)
+            })
+        },
+        refresh(){
+            this.$refs.table.refresh()
+        },
+        upData(data){
+            this.$refs.table.upData(data)
+        },
+        handleSuccess(){
+            this.$refs.table.refresh()
+        },
+        sortChange(event){
+            if (event.order) {
+                var data = {
+                    "field":event.prop,
+                    "order":event.order
+                }
+                this.$refs.table.upData(data)
+            } else {
+                this.$refs.table.reload(this.searchKey)
+            }
+            return ;
+        },
+        selectionChange(event){
+            this.dataSelect = [];
+            var arr = [];
+            var arrCompany = [];
+            event.forEach(function(val,index){
+                arr[index] = val.id;
+                arrCompany[index] = val;
+            });
+            this.dataSelectFull = arrCompany;
+            this.dataSelect = arr;
+            this.$emit("success",this.dataSelect);
+            this.$emit("successFull",this.dataSelectFull);
+        },
+    }
+}
+</script>
+
+<style>
+.desc{
+    color: #999;
+    font-size: 12px;
+}
+.flex-btn{
+    display: flex;
+    flex-wrap: wrap;
+    gap: 5px;
+}
+.flex-tags {
+    display: flex;
+    gap: 2px;
+    flex-wrap: wrap;
+}
+.flex-btn .el-button.is-text{
+    margin-left: 0;
+}
+.flex-tags-size{
+    font-size: 12px;
+}
+.flex-tags-size span{
+    display: block;
+    margin-bottom: 5px;
+    color: #999;
+}
+</style>

+ 50 - 0
src/views/store/order/send/index.vue

@@ -0,0 +1,50 @@
+<template>
+    <el-container class="flex-column">
+        <div class="table-search">
+            <search @success="handleSuccess"></search>
+            <el-alert type="warning" show-icon title="栏目提醒" description="已预约栏目的订单,用户如取消订单,无需商家同意,产品如已发货,请尽快修改订单状态到服务中,如造成经济损失,本核销系统不负法律责任(使用自动呼叫快递功能的商家忽略)" :closable="false" style="margin-bottom: 10px;"></el-alert>
+            <optionBtn @success="handleSuccess" :dataSelect="dataSelect" :dataSelectFull="dataSelectFull" type="3"></optionBtn>
+        </div>
+        <el-main class="nopadding">
+            <div class="table-container">
+                <tablePage ref="tablePage" @success="tableHandle" @successFull="tableHandleFull" type="3"></tablePage>
+            </div>
+        </el-main>
+    </el-container>  
+</template>
+
+<script>
+import search from './components/search';
+import optionBtn from './components/option';
+import tablePage from './components/table';
+export default {
+    components: {
+        search,tablePage,optionBtn
+    },
+    data(){
+        return {
+            searchKey:{
+                ex_status:1
+            },
+            dataSelect:[],
+            dataSelectFull:[],
+        }
+    },
+    methods: {
+        tableHandle(data){
+            this.dataSelect = data;
+        },
+        tableHandleFull(data){
+            this.dataSelectFull = data;
+        },
+        handleSuccess(data){
+            this.$refs.tablePage.upData(data)
+        },
+        handleClick(name){
+            this.activeName = name;
+            this.searchKey.type = name;
+            this.$refs.tablePage.upData(this.searchKey)
+        }
+    }
+}
+</script>

+ 86 - 0
src/views/store/refund/components/form.vue

@@ -0,0 +1,86 @@
+<template>
+    <el-dialog :title="titleMap[mode]" v-model="visible" :width="600" destroy-on-close @closed="$emit('closed')" :close-on-click-modal="false" :close-on-press-escape="false">
+        <el-form ref="dialogForm" :model="formData" :rules="rules" label-width="100px" label-position="top">
+            <el-form-item label="联系人" prop="username">
+                <el-input v-model="formData.username" clearable placeholder="请输入"></el-input>
+                <div class="el-form-item-msg"></div>
+            </el-form-item>
+            <el-form-item label="联系电话" prop="mobile">
+                <el-input v-model="formData.mobile" clearable placeholder="请输入"></el-input>
+                <div class="el-form-item-msg"></div>
+            </el-form-item>
+            <el-form-item label="详细地址" prop="address">
+                <el-input v-model="formData.address" clearable placeholder="请输入"></el-input>
+                <div class="el-form-item-msg"></div>
+            </el-form-item>
+        </el-form>
+		<template #footer>
+			<el-button @click="visible=false" >取 消</el-button>
+			<el-button type="primary" :loading="isSaveing" @click="submit()">提交</el-button>
+		</template>
+    </el-dialog>
+</template>
+<script>
+export default {
+    data(){
+        return {
+            loading: false,
+            mode:"add",
+            titleMap:{
+                add:"更新地址",
+                edit:"更新地址"
+            },
+            visible: false,
+            isSaveing: false,
+            formData:{},
+            submitState:false,
+            disabled:false,
+            rules:{
+                username: [
+                    {required: true, message: '请输入'}
+                ],
+                mobile: [
+                    {required: true, message: '请输入'}
+                ],
+                address: [
+                    {required: true, message: '请输入'}
+                ]
+            },
+            sms:""
+        }
+    },
+    methods:{
+        open(mode = 'add'){
+            this.mode = mode;
+            this.visible = true;
+            return this
+        },
+        //表单注入数据
+        setData(data){
+            data.address = data.region+data.address;
+            this.formData = data;
+        },
+        async submit(){
+            var validate = await this.$refs.dialogForm.validate().catch(()=>{});
+            if(!validate){ return false }
+            this.isSaveing = true;
+            let submitData = JSON.parse(JSON.stringify(this.formData));
+            var resp = await this.$API.order.save.post(submitData);
+            this.isSaveing = false;
+            if (resp.code !== 1) {
+                return this.$message.error(resp.msg);
+            }
+            this.$message.success(resp.msg);
+            this.visible = false;
+            this.formData = {};
+            this.submitState = false;
+            this.$emit("success");
+        }
+    }
+}
+</script>
+<style>
+.mt20 {margin-top: 20px;}
+.login-msg-yzm {display: flex;width: 100%;}
+.login-msg-yzm .el-button {margin-left: 10px;--el-button-size:42px;}
+</style>

+ 56 - 0
src/views/store/refund/components/option.vue

@@ -0,0 +1,56 @@
+<template>
+    <fieldset>
+        <legend>
+            <el-tag type="info">按需操作</el-tag>
+        </legend>
+        <div class="op-header">
+            <div class="left-panel">
+                <sc-file-export :apiObj="$API.orderlife.export" :data="searchKey" :fileName="'来客订单_'+(new Date().getTime())" async>
+                    <template #default="{ open }">
+                        <el-button type="primary" icon="sc-icon-download" @click="open">导出</el-button>
+                    </template>
+                </sc-file-export>
+            </div>
+        </div>
+    </fieldset>
+</template>
+
+<script>
+import scFileExport from '@/components/scFileExport'
+export default {
+    components: {
+        scFileExport
+    },
+    props: {
+        type: { type: String, default: "1" },
+        dataSelect: { type: Array, default: () => [] },
+        searchKey: { type: Object, default: () => {} },
+        dataSelectFull: { type: Array, default: () => [] }
+    },
+    data(){
+        return {
+
+        }
+    },
+    methods: {
+        table_export(){
+            
+        },
+        async table_batch_status(status){
+            if (this.dataSelect.length == 0) {
+                return this.$message.error("请选择修改数据")
+            }
+            let submitData = {"id":this.dataSelect,"value":status,"field":"status","type":"batch"};
+            var resp = await this.$API.merGoods.batch.post(submitData);
+            if (resp.code == 0) {
+                return this.$message.error(resp.msg);
+            }
+            this.$message.success(resp.msg);
+            this.$emit("success");
+        },
+        handleSuccess(){
+            this.$emit("success");
+        },
+    }
+}
+</script>

+ 54 - 0
src/views/store/refund/components/search.vue

@@ -0,0 +1,54 @@
+<template>
+    <fieldset>
+        <legend>
+            <el-tag type="info">条件筛选</el-tag>
+        </legend>
+        <el-form class="lv-form-inline" ref="searchForm" :model="searchKey" label-position="right" label-width="100px">
+            <div class="search-form">
+                <div class="form-left">
+                    <el-row :gutter="10">
+                        <el-col :span="this.$store.state.global.ismobile?12:4">
+                            <el-input v-model="searchKey.orderid" placeholder="订单编号" clearable :style="{ width: '100%' }" @keyup.enter="searchForm()">
+                                <template #prepend>订单编号</template>
+                            </el-input>
+                        </el-col>
+                        <el-col :span="this.$store.state.global.ismobile?12:4">
+                            <el-input v-model="searchKey.product" placeholder="商品ID" clearable :style="{ width: '100%' }" @keyup.enter="searchForm()">
+                                <template #prepend>商品ID</template>
+                            </el-input>
+                        </el-col>
+                        <el-col :span="this.$store.state.global.ismobile?12:4">
+                            <el-input v-model="searchKey.name" placeholder="商品标题" clearable :style="{ width: '100%' }" @keyup.enter="searchForm()">
+                                <template #prepend>商品标题</template>
+                            </el-input>
+                        </el-col>
+                        <el-col :span="this.$store.state.global.ismobile?12:4">
+                            <el-date-picker v-model="searchKey.create" :style="{width: '100%'}" placeholder="请选择创建时间" start-placeholder="开始时间" end-placeholder="结束时间" type="daterange" range-separator="至" @change="searchForm" />
+                        </el-col>
+                    </el-row>
+                </div>
+                <div class="form-line"></div>
+                <div class="form-right">
+                    <el-button type="primary" icon="el-icon-search" @click="searchForm">搜索</el-button>
+                </div>
+            </div>
+        </el-form>
+    </fieldset>
+</template>
+
+<script>
+export default {
+    data(){
+        return {
+            searchKey:{
+                ex_status:5
+            }
+        }
+    },
+    methods: {
+        searchForm(){
+            this.$emit("success",this.searchKey);
+        }
+    }
+}
+</script>

+ 229 - 0
src/views/store/refund/components/table.vue

@@ -0,0 +1,229 @@
+<template>
+    <scTable ref="table" :apiObj="list.apiObj" :params="searchKey" @selectionChange="selectionChange" row-key="id">
+        <el-table-column type="selection" width="50" fixed="left"></el-table-column>
+        <el-table-column label="订单编号" prop="order_id" width="220" fixed="left">
+            <template #default="scope">
+                <span v-if="scope.row.order_id">{{ scope.row.order_id }}</span>
+                <span class="status-danger" v-else>未设置</span>
+            </template>
+        </el-table-column>
+        <el-table-column label="所属代理" prop="status" width="160">
+            <template #default="scope">
+                <span>{{ scope.row.agent?scope.row.agent.name:'-' }}</span>
+            </template>
+        </el-table-column>
+        <el-table-column label="所属店铺" prop="status" width="160">
+            <template #default="scope">
+                <span>{{ scope.row.store?scope.row.store.store_name:'-' }}</span>
+            </template>
+        </el-table-column>
+        <el-table-column label="订单类型" prop="status" width="120">
+            <template #default="scope">
+                <div class="status-danger" v-if="scope.row.service_type==1"><sc-status-indicator type="danger"></sc-status-indicator> 预约</div>
+                <div class="status-success" v-if="scope.row.service_type==2"><sc-status-indicator type="success"></sc-status-indicator> 快递</div>
+            </template>
+        </el-table-column>
+        <el-table-column label="收货地址" prop="company_id" width="120">
+            <template #default="scope">
+                <el-popover :width="200" placement="top-start">
+                    <template #reference>
+                        <div class="el-text">
+                            {{scope.row.username?scope.row.username:'-'}}
+                            <div class="desc" v-copy="'联系人:'+scope.row.username+'联系电话:'+scope.row.mobile+'联系地址:'+scope.row.region+scope.row.address"><span>一键复制</span></div>
+                        </div>
+                    </template>
+                    <div class="flex-tags-size">
+                        <span>联系人</span>{{scope.row.username?scope.row.username:'-'}}<br><br>
+                        <span>联系电话</span>{{scope.row.mobile?scope.row.mobile:'-'}}<br><br>
+                        <span>联系地址</span>{{scope.row.region?scope.row.region:'-'}}{{scope.row.address?scope.row.address:'-'}}
+                    </div>
+                </el-popover>
+            </template>
+        </el-table-column>
+        <el-table-column label="商品ID" prop="out_id" width="150">
+            <template #default="scope">
+                <span v-if="scope.row.product_id">{{ scope.row.product_id }}</span>
+                <span class="status-danger" v-else>未设置</span>
+            </template>
+        </el-table-column>
+        <el-table-column label="商品名称" prop="product_name" width="220">
+            <template #default="scope">
+                <span v-if="scope.row.product_name">{{ scope.row.product_name }}</span>
+                <span class="status-danger" v-else>未设置</span>
+            </template>
+        </el-table-column>
+        <el-table-column label="数量" prop="count" width="100">
+            <template #default="scope">
+                <span>{{ scope.row.parent.count }}件</span>
+            </template>
+        </el-table-column>
+        <el-table-column label="订单金额" prop="order_amount" width="150">
+            <template #default="scope">
+                <span v-if="scope.row.parent.order_amount">¥{{ scope.row.parent.order_amount }}</span>
+                <span class="status-danger" v-else>未设置</span>
+            </template>
+        </el-table-column>
+        <el-table-column label="支付金额" prop="pay_amount" width="150">
+            <template #default="scope">
+                <span v-if="scope.row.parent.pay_amount">¥{{ scope.row.parent.pay_amount }}</span>
+                <span class="status-danger" v-else>未设置</span>
+            </template>
+        </el-table-column>
+        <el-table-column label="状态" prop="status" width="180">
+            <template #default="scope">
+                <div class="status-danger" v-if="scope.row.express_status==0"><sc-status-indicator type="danger"></sc-status-indicator> 待发货</div>
+                <div class="status-success" v-if="scope.row.express_status==1"><sc-status-indicator type="success"></sc-status-indicator> 待核销</div>
+                <div class="status-danger" v-if="scope.row.express_status==2"><sc-status-indicator type="danger"></sc-status-indicator> 已完成</div>
+                <div class="status-info" v-if="scope.row.express_status==3"><sc-status-indicator type="info"></sc-status-indicator> 已取消</div>
+                <div class="status-info" v-if="scope.row.express_status==4"><sc-status-indicator type="info"></sc-status-indicator> 退款审核</div>
+                <div class="status-info" v-if="scope.row.express_status==5"><sc-status-indicator type="info"></sc-status-indicator> 拒绝退款</div>
+                <div v-if="scope.row.status==5 && scope.row.remark">{{ scope.row.remark }}</div>
+            </template>
+        </el-table-column>
+        <el-table-column label="创建时间" prop="create_at" width="180"></el-table-column>
+        <el-table-column label="操作" width="200" align="right" fixed="right">
+            <template #default="scope">
+                <el-button-group>
+                    <el-button text type="warning" size="small" @click="table_log(scope.row)">订单记录</el-button>
+                    <el-button text type="warning" size="small" @click="table_express(scope.row)" v-if="scope.row.express_status==0">呼叫快递</el-button>
+                    <el-button text type="warning" size="small" v-if="scope.row.express_status==1" @click="table_print(scope.row)">打印面单</el-button>
+                    <el-button text type="success" size="small" @click="table_end(scope.row)" v-if="scope.row.express_status==1">手动核销</el-button>
+                    <el-button text type="success" size="small" @click="table_passwd(scope.row)" v-if="scope.row.express_status==0 && scope.row.service_type==2">更新地址</el-button>
+                </el-button-group>
+            </template>
+        </el-table-column>
+    </scTable>
+    <formMain ref="formMain" @success="handleSuccess"></formMain>
+    <addMain ref="addMain" @success="handleSuccess"></addMain>
+    <logMain ref="logMain" @success="handleSuccess"></logMain>
+</template>
+
+<script>
+import formMain from './form';
+import addMain from "@/views/manage/components/send";
+import logMain from '@/views/manage/order/components/log'
+export default {
+    components: {
+        formMain,addMain,logMain
+    },
+    data(){
+        return {
+            list: {
+                apiObj: this.$API.order.list
+            },
+            dataSelect:[],
+            dataSelectFull:[],
+            searchKey:{
+                ex_status:2
+            }
+        }
+    },
+    methods: {
+        table_passwd(row){
+            return this.$message.success("暂未开放");
+            this.$nextTick(() => {
+                this.$refs.formMain.open("edit").setData(row)
+            })
+        },
+        table_end(data){
+            return this.$message.success("暂未开放");
+            this.$confirm(`核销后该笔订单即为完成,如客户需退款只能通过来客后台进行操作,当前后台不支持核销后退款操作,确定要执行吗?`, '提示', {
+                type: 'warning'
+            }).then(async () => {
+                var loading = this.$loading();
+                var resp = await this.$API.order.end.post({"order_id":data.order_id});
+                loading.close();
+                if (resp.code !== 1) {
+                    return this.$message.error(resp.msg);
+                }
+                this.$message.success(resp.msg);
+                this.$refs.table.refresh()
+            }).catch(() => {
+
+            })
+        },
+        table_express(data){
+            return this.$message.success("暂未开放");
+            this.$confirm(`呼叫快递成功后,可进入【待核销】栏目进行打印快递面单,如已接通云打印可忽略`, '提示', {
+                type: 'warning'
+            }).then(async ()=>{
+                var loading = this.$loading();
+                var resp = await this.$API.merOrder.express.post({"id":data.id});
+                loading.close();
+                if (resp.code == 0) {
+                    return this.$message.warning(resp.msg);
+                }
+                this.$message.success(resp.msg);
+                this.$refs.table.refresh()
+            }).catch(()=>{})
+        },
+        table_log(data){
+            this.$nextTick(() => {
+                this.$refs.logMain.open("edit").setData(data)
+            })
+        },
+        refresh(){
+            this.$refs.table.refresh()
+        },
+        upData(data){
+            this.$refs.table.upData(data)
+        },
+        handleSuccess(){
+            this.$refs.table.refresh()
+        },
+        sortChange(event){
+            if (event.order) {
+                var data = {
+                    "field":event.prop,
+                    "order":event.order
+                }
+                this.$refs.table.upData(data)
+            } else {
+                this.$refs.table.reload(this.searchKey)
+            }
+            return ;
+        },
+        selectionChange(event){
+            this.dataSelect = [];
+            var arr = [];
+            var arrCompany = [];
+            event.forEach(function(val,index){
+                arr[index] = val.id;
+                arrCompany[index] = val;
+            });
+            this.dataSelectFull = arrCompany;
+            this.dataSelect = arr;
+            this.$emit("success",this.dataSelect);
+            this.$emit("successFull",this.dataSelectFull);
+        },
+    }
+}
+</script>
+
+<style>
+.desc{
+    color: #999;
+    font-size: 12px;
+}
+.flex-btn{
+    display: flex;
+    flex-wrap: wrap;
+    gap: 5px;
+}
+.flex-tags {
+    display: flex;
+    gap: 2px;
+    flex-wrap: wrap;
+}
+.flex-btn .el-button.is-text{
+    margin-left: 0;
+}
+.flex-tags-size{
+    font-size: 12px;
+}
+.flex-tags-size span{
+    display: block;
+    margin-bottom: 5px;
+    color: #999;
+}
+</style>

+ 50 - 0
src/views/store/refund/index.vue

@@ -0,0 +1,50 @@
+<template>
+    <el-container class="flex-column">
+        <div class="table-search">
+            <search @success="handleSuccess"></search>
+            <el-alert type="warning" show-icon title="栏目提醒" description="该栏目只处理服务中订单,已核销订单,请去抖音来客后台处理撤销核销/协助退款" :closable="false" style="margin-bottom: 10px;"></el-alert>
+            <optionBtn @success="handleSuccess" :dataSelect="dataSelect" :dataSelectFull="dataSelectFull" type="3"></optionBtn>
+        </div>
+        <el-main class="nopadding">
+            <div class="table-container">
+                <tablePage ref="tablePage" @success="tableHandle" @successFull="tableHandleFull" type="3"></tablePage>
+            </div>
+        </el-main>
+    </el-container>  
+</template>
+
+<script>
+import search from './components/search';
+import optionBtn from './components/option';
+import tablePage from './components/table';
+export default {
+    components: {
+        search,tablePage,optionBtn
+    },
+    data(){
+        return {
+            searchKey:{
+                ex_status:5
+            },
+            dataSelect:[],
+            dataSelectFull:[],
+        }
+    },
+    methods: {
+        tableHandle(data){
+            this.dataSelect = data;
+        },
+        tableHandleFull(data){
+            this.dataSelectFull = data;
+        },
+        handleSuccess(data){
+            this.$refs.tablePage.upData(data)
+        },
+        handleClick(name){
+            this.activeName = name;
+            this.searchKey.type = name;
+            this.$refs.tablePage.upData(this.searchKey)
+        }
+    }
+}
+</script>

+ 234 - 0
src/views/store/setting/index.vue

@@ -0,0 +1,234 @@
+<template>
+    <el-container>
+        <el-main v-loading="isLoading">
+            <el-card shadow="never" header="店铺设置" class="borderNone">
+                <div style="width: 50%;">
+                    <el-form ref="dialogForm" :model="formData" :rules="rules" label-width="100px" label-position="top">
+                        <fieldset>
+                            <legend><el-tag>店铺信息</el-tag></legend>
+                            <el-row :gutter="15">
+                                <el-col :span="12">
+                                    <el-form-item label="来客店铺名称" prop="store_name">
+                                        <el-input v-model="formData.store_name" clearable placeholder="来客店铺名称"></el-input>
+                                        <div class="el-form-item-msg"></div>
+                                    </el-form-item>
+                                </el-col>
+                                <el-col :span="12">
+                                    <el-form-item label="来客账户ID" prop="store_id">
+                                        <el-input disabled="true" v-model="formData.store_id" clearable placeholder="来客账户ID"></el-input>
+                                        <div class="el-form-item-msg"></div>
+                                    </el-form-item>
+                                </el-col>
+                                <el-col :span="6">
+                                    <el-form-item label="快递类型" prop="express_type">
+                                        <el-select v-model="formData.express_type" clearable placeholder="请选择" :style="{width: '100%'}">
+                                            <el-option :value="item.code" :label="item.name" v-for="item in expressType"></el-option>
+                                        </el-select>
+                                        <div class="el-form-item-msg"></div>
+                                    </el-form-item>
+                                </el-col>
+                                <el-col :span="6">
+                                    <el-form-item label="呼叫快递时间" prop="express_time">
+                                        <el-select v-model="formData.express_time" clearable placeholder="请选择" :style="{width: '100%'}">
+                                            <el-option :value="(item-1)" :label="(item-1)==0?'实时':(item-1)+'点后'" v-for="item in 20"></el-option>
+                                        </el-select>
+                                        <div class="el-form-item-msg"></div>
+                                    </el-form-item>
+                                </el-col>
+                                <el-col :span="6">
+                                    <el-form-item label="核销时机" prop="order_end">
+                                        <el-select v-model="formData.order_end" clearable placeholder="请选择" :style="{width: '100%'}">
+                                            <el-option :value="item.id" :label="item.name" v-for="item in orderEnd"></el-option>
+                                        </el-select>
+                                        <div class="el-form-item-msg"></div>
+                                    </el-form-item>
+                                </el-col>
+                                <el-col :span="6">
+                                    <el-form-item label="退款自动拦截快递" prop="is_reback">
+                                        <el-select v-model="formData.is_reback" clearable placeholder="请选择" :style="{width: '100%'}">
+                                            <el-option :value="item.id" :label="item.name" v-for="item in orderReback"></el-option>
+                                        </el-select>
+                                        <div class="el-form-item-msg"></div>
+                                    </el-form-item>
+                                </el-col>
+                                <el-col :span="6">
+                                    <el-form-item label="营业时间-开始" prop="service_at_start">
+                                        <el-time-select
+                                            v-model="formData.service_at_start"
+                                            :style="{ width: '100%' }"
+                                            start="00:15"
+                                            step="00:15"
+                                            end="23:55"
+                                            placeholder="营业时间-开始"
+                                        />
+                                    </el-form-item>
+                                </el-col>
+                                <el-col :span="6">
+                                    <el-form-item label="营业时间-结束" prop="service_at_end">
+                                        <el-time-select
+                                            v-model="formData.service_at_end"
+                                            :style="{ width: '100%' }"
+                                            start="00:15"
+                                            step="00:15"
+                                            end="23:55"
+                                            placeholder="营业时间-结束"
+                                        />
+                                    </el-form-item>
+                                </el-col>
+                                <el-col :span="6">
+                                    <el-form-item label="客服电话" prop="service_mobile">
+                                        <el-input v-model="formData.service_mobile" clearable placeholder="请输入"></el-input>
+                                        <div class="el-form-item-msg">在小程序选择门店中展现</div>
+                                    </el-form-item>
+                                </el-col>
+                                <el-col :span="6">
+                                    <el-form-item label="核销形式" prop="service_type">
+                                        <el-select v-model="formData.service_type" clearable placeholder="请选择" :style="{width: '100%'}">
+                                            <el-option :value="1" label="预约"></el-option>
+                                            <el-option :value="2" label="快递"></el-option>
+                                        </el-select>
+                                        <div class="el-form-item-msg">预约无需添加收货地址</div>
+                                    </el-form-item>
+                                </el-col>
+                            </el-row>
+                        </fieldset>
+                        <fieldset>
+                            <legend><el-tag>发货信息</el-tag></legend>
+                            <el-row :gutter="15">
+                                <el-col :span="12">
+                                    <el-form-item label="联系人" prop="express_name">
+                                        <el-input v-model="formData.express_name" clearable placeholder="请输入"></el-input>
+                                        <div class="el-form-item-msg">用于呼叫快递</div>
+                                    </el-form-item>
+                                </el-col>
+                                <el-col :span="12">
+                                    <el-form-item label="联系电话" prop="express_mobile">
+                                        <el-input v-model="formData.express_mobile" clearable placeholder="请输入"></el-input>
+                                        <div class="el-form-item-msg"></div>
+                                    </el-form-item>
+                                </el-col>
+                                <el-col :span="12">
+                                    <el-form-item label="物品名称" prop="express_goods">
+                                        <el-input v-model="formData.express_goods" clearable placeholder="请输入"></el-input>
+                                        <div class="el-form-item-msg"></div>
+                                    </el-form-item>
+                                </el-col>
+                                <el-col :span="12">
+                                    <el-form-item label="物品单位" prop="express_unit">
+                                        <el-input v-model="formData.express_unit" clearable placeholder="请输入"></el-input>
+                                        <div class="el-form-item-msg"></div>
+                                    </el-form-item>
+                                </el-col>
+                                <el-col :span="24">
+                                    <el-form-item label="发货地址" prop="express_address">
+                                        <el-input type="textarea" rows="5" v-model="formData.express_address" clearable placeholder="请输入"></el-input>
+                                        <div class="el-form-item-msg"></div>
+                                    </el-form-item>
+                                </el-col>
+                            </el-row>
+                        </fieldset>
+                    </el-form>
+                </div>
+            </el-card>
+        </el-main>
+        <el-footer>
+            <el-button type="primary" :loading="isSaveing" @click="submit">保存</el-button>
+        </el-footer>
+    </el-container>
+</template>
+
+<script>
+
+export default {
+    data() {
+        return {
+            isSaveing: false,
+            isLoading:false,
+            formData:{},
+            orderEnd:[{"id":1,"name":"订单提交后"},{"id":2,"name":"快递取件后"},{"id":3,"name":"快递签收后"}],
+            orderReback:[{"id":1,"name":"开启"},{"id":2,"name":"关闭"}],
+            expressType:[],
+            rules:{
+                express_type: [
+                    {required: true, message: '请选择'}
+                ],
+                is_auto: [
+                    {required: true, message: '请选择'}
+                ],
+                service_type: [
+                    {required: true, message: '请选择'}
+                ],
+                service_mobile: [
+                    {required: true, message: '请输入'}
+                ],
+                is_reback: [
+                    {required: true, message: '请选择'}
+                ],
+                store_name: [
+                    {required: true, message: '请输入'}
+                ],
+                service_at_start: [
+                    {required: true, message: '请输入'}
+                ],
+                service_at_end: [
+                    {required: true, message: '请输入'}
+                ],
+                express_name: [
+                    {required: true, message: '请输入'}
+                ],
+                express_mobile: [
+                    {required: true, message: '请输入'}
+                ],
+                express_goods: [
+                    {required: true, message: '请输入'}
+                ],
+                express_unit: [
+                    {required: true, message: '请输入'}
+                ],
+                express_address: [
+                    {required: true, message: '请输入'}
+                ],
+                express_time: [
+                    {required: true, message: '请选择'}
+                ],
+                order_end: [
+                    {required: true, message: '请选择'}
+                ],
+            }
+        }
+    },
+    created(){
+        this.getConfig()
+    },
+    methods:{
+        async getExpress(){
+            this.loading = true;
+            var resp = await this.$API.express.page.get();
+            this.loading = false;
+            this.expressType = resp.data;
+        },
+        async getConfig(){
+            this.isLoading = true;
+            var resp = await this.$API.storeShop.detail.get();
+            this.isLoading = false;
+            if (resp.code !== 1) {
+                return this.$message.error(resp.msg)
+            }
+            this.formData = resp.data;
+            this.getExpress()
+        },
+        async submit(){
+            var validate = await this.$refs.dialogForm.validate().catch(()=>{});
+            if(!validate){ return false }
+            this.isSaveing = true;
+            let submitData = JSON.parse(JSON.stringify(this.formData));
+            var resp = await this.$API.storeShop.save.post(submitData);
+            this.isSaveing = false;
+            if (resp.code == 0) {
+                return this.$message.error(resp.msg);
+            }
+            this.$message.success(resp.msg);
+        }
+    }
+}
+</script>