Explorar o código

修改问题 处理bug对接微信支付

yangg hai 11 meses
pai
achega
5d78cd434e

+ 2 - 2
.env

@@ -1,5 +1,5 @@
-VITE_API_URL=http://192.168.8.101:9998
+VITE_API_URL=http://192.168.8.110:9998
 #线下地址
-#http://192.168.8.104:9998
+#http://192.168.8.110:9998
 #线上地址
 #https://api.raycos.net

+ 1 - 0
package.json

@@ -46,6 +46,7 @@
     "print-js": "^1.6.0",
     "psl": "^1.9.0",
     "qrcode": "^1.5.3",
+    "qrcode.vue": "^3.4.1",
     "qrcodejs2": "^0.0.2",
     "qs": "^6.12.1",
     "sweetalert2": "^11.5.1",

+ 20 - 1
src/api/auth.js

@@ -165,4 +165,23 @@ export function getPackageRoleList(params) {
     loading: false,
     params
   })
-}
+}
+/* 绑定微信  */
+export function getOpenIdCode(orderId,params) {
+  return request({
+    url: `/admin/erp/pay/getOpenIdCode/${orderId}`,
+    method: 'post',
+    headers: { 'Content-Type': 'application/json' },
+    data: params
+  })
+}
+
+/* 微信支付*/
+export function getPayUrl(params) {
+  return request({
+    url: `/admin/erp/pay/getPayUrl`,
+    method: 'post',
+    headers: { 'Content-Type': 'application/json' },
+    data: params
+  })
+}

+ 0 - 1
src/components/layout/SidebarItem.vue

@@ -70,7 +70,6 @@ const hasOneShowingChild = (children: any[], item: any) => {
       return false;
     } else {
       onlyOneChild.value = child;
-      console.log("onlyOneChild:",onlyOneChild);
       return true;
     }
   });

+ 26 - 1
src/locales/zh.json

@@ -172,7 +172,32 @@
 
     "express":"物流公司",
 
-    
+    "companyDetails":"公司信息",
+    "currentPack":"当前套餐",
+    "end_use_time":"套餐到期时间",
+    "user_num":"可绑定账户数",
+    "companyName":"公司名称",
+    "credit_code":"统一社会信用代码",
+    "industry":"行业",
+    "company_user_name":"联系人",
+    "companyPhone":"联系人电话",
+    "companyEmail":"邮箱",
+    "postalCode":"邮编",
+    "website":"官网",
+    "companyAddress":"地址",
+    "companyLicense":"营业执照",
+
+    "nickname":"账户名称",
+    "loginName":"登录账号",
+    " profile":"头像",
+    "bindWeChat":"绑定微信",
+    "bindWeChatError":"获取微信绑定信息失败",
+    "uploadPro":"请上传头像",
+    "uploadNewPro":"请上传新的头像",
+
+    "pay_success":"支付成功",
+    "pay_info":"支付已取消",
+    "pay_error":"支付失败",
 
     "brand":"品牌",
     "weight":"重量",

+ 2 - 2
src/permission.js

@@ -5,7 +5,7 @@ import 'nprogress/nprogress.css' // Progress 进度条样式 */
 import { ElMessage } from 'element-plus'
 import Storage from '@/utils/storage'
 
-const whiteList = ['/login', '/boxed-signup']
+const whiteList = ['/login', '/boxed-signup','/platformLogin']
 
 let toFirstRoute = function getTopRoutePath(router, next) {
   const excludes = [
@@ -37,7 +37,7 @@ router.beforeEach(async (to, from, next) => {
  /*  next(true); */
   const refreshToken = Storage.getItem('admin_refresh_token')
   if (refreshToken) {
-    if ((to.path === '/login' || to.path === '/boxed-signup') && store.getters.addRouters.length) {
+    if ((to.path === '/login' || to.path === '/boxed-signup' || to.path ==='/platformLogin') && store.getters.addRouters.length) {
       return next(toFirstRoute(router))
       /* toFirstRoute(router, next) */
      /*  NProgress.done() */

+ 0 - 1
src/stores/modules/tagsView.js

@@ -80,7 +80,6 @@ const tagsView = {
       commit('DEL_VISITED_VIEWS', params.view)
       const latestView = [...state.visitedViews].slice(-1)[0]
       if (latestView) {
-        console.log(latestView);
         params.$router.push(latestView)
       } else {
         params.$router.push('/')

+ 0 - 4
src/stores/modules/user.js

@@ -32,7 +32,6 @@ export const mutations = {
      // 调试信息
    // const expires = new Date(jwt_decode(token).exp * 1000)
     Storage.setItem('admin_access_token', token)
-    console.log('SET_ACCESS_TOKEN mutation called with token:', token)
   },
   /**
    * 设置刷新令牌
@@ -41,7 +40,6 @@ export const mutations = {
    * @constructor
    */
   SET_REFRESH_TOKEN: (state,token) => {
-    console.log('SET_ACCESS_TOKEN mutation called')
    // const expires = new Date(jwt_decode(token).exp * 1000)
     Storage.setItem('admin_refresh_token', token)
   },
@@ -86,7 +84,6 @@ export const actions = {
       if (window.location.href.indexOf('/franchise/login') === -1) {
         API_Login.login(params).then(response => {
           const { access_token, refresh_token, ...user } = response
-          console.log('Committing SET_USER and SET_ACCESS_TOKEN') // 调试信息
           commit('SET_USER', user)
           commit('SET_ACCESS_TOKEN', access_token)
           commit('SET_REFRESH_TOKEN', refresh_token)
@@ -95,7 +92,6 @@ export const actions = {
       } else {
         API_Login.loginByFranchise(params).then(response => {
           const { access_token, refresh_token, ...user } = response
-          console.log(113);
           commit('SET_USER', user)
           commit('SET_ACCESS_TOKEN', access_token)
           commit('SET_REFRESH_TOKEN', refresh_token)

+ 5 - 7
src/utils/checkToken.js

@@ -1,7 +1,6 @@
 /**
  * Created by Andste on 2018/5/7.
  */
-
 import Storage from './storage'
 import { useStore } from 'vuex';
 import router from '@/router'
@@ -26,7 +25,7 @@ export default function checkToken(options) {
   // 刷新Token
   const refreshToken = Storage.getItem('admin_refresh_token')
   // 登录路径
-  let loginPath = Storage.getItem('admin_franchise') ? '/franchise/login' : '/login'
+  let loginPath = Storage.getItem('admin_franchise') ? '/platformLogin' : '/login'
   loginPath = router.resolve(loginPath).href
    // 获取 store 实例
    const store = useStore();
@@ -44,7 +43,10 @@ export default function checkToken(options) {
      * 如果refreshToken或者user没有
      * 说明登录已失效、或者cookie有问题,需要重新登录。
      */
+    const path = router.resolve(loginPath).hash;
+    const result = path.slice(path.indexOf('/'))
     if (!refreshToken || !user) {
+      if(result!=='/login'){
       store.dispatch('fedLogoutAction')
       ElMessageBox.alert('您的登录状态已失效,请重新登录!', '权限错误', {
         type: 'error',
@@ -52,6 +54,7 @@ export default function checkToken(options) {
           window.location.replace(loginPath)
         }
       })
+    }
       return
     }
     /**
@@ -66,7 +69,6 @@ export default function checkToken(options) {
        * 如果有刷新token锁,则进入循环检测。
        */
       if (!window.__refreshTokenLock__) {
-        // console.log(options.url + ' | 检测到accessToken失效,这个请求需要等待刷新token。')
         // 开始请求新的Token,并加锁。
         window.__refreshTokenLock__ = true
         const refreshTokenFunc = Storage.getItem('admin_franchise')
@@ -76,7 +78,6 @@ export default function checkToken(options) {
             useStore.dispatch('setAccessTokenAction', response.accessToken)
             useStore.dispatch('setRefreshTokenAction', response.refreshToken)
           window.__refreshTokenLock__ = null
-          // console.log(options.url + ' | 已拿到新的token。')
           resolve()
         }).catch(() => {
           window.__refreshTokenLock__ = undefined
@@ -84,14 +85,11 @@ export default function checkToken(options) {
           window.location.replace(loginPath)
         })
       } else {
-        // console.log('进入循环检测...')
         // 循环检测刷新token锁,当刷新锁变为null时,说明新的token已经取回。
         const checkLock = () => {
           setTimeout(() => {
             const __RTK__ = window.__refreshTokenLock__
-            // console.log(options.url + ' | 是否已拿到新的token:', __RTK__ === null)
             if (__RTK__ === undefined) {
-              // console.log('登录已失效了,不用再等待了...')
               useStore.dispatch('fedLogoutAction')
               window.location.replace(loginPath)
               return

+ 0 - 1
src/views/apps/applist.vue

@@ -99,7 +99,6 @@ const loginUser = ref({
 const fetchData = async () => {
   try {
     const response = await $axios.get('/api-endpoint');
-    console.log('API Response:', response.data);
   } catch (error) {
     console.error('API Error:', error);
   }

+ 2 - 4
src/views/auth/boxed-signin.vue

@@ -295,7 +295,8 @@ const currentFlag = computed(() => {
 });
 
 const typeLogin = () => {
-  router.push({ path: '/platformLogin' });
+  router.push({ path: '/platformLogin' })
+ /*  router.push({ path: '/platformLogin' }); */
 };
 
 /* 查询公司 */
@@ -348,7 +349,6 @@ const initCaptcha = (data) => {
 /** 更换图片验证码 */
 const changeValidcode = () => {
   validcodeImg.value = API_common.getValidateCodeUrl('LOGIN', uuid);
-  console.log(validcodeImg);
 };
 const MixinClone = (obj) => {
   return JSON.parse(JSON.stringify(obj));
@@ -368,13 +368,11 @@ const dispatchLoginAction = (params) => {
             // 使用 provide/inject 或其他方式在 Vue 3 中共享 WebSocket 实例
             app.provide('websocket', WS);
           } catch (error) {
-            console.log('websocket 实例化失败:', error);
           }
         }
         const forward = route.query.forward;
         let query = JSON.parse(JSON.stringify(route.query));
         delete query.forward;
-        console.log(params);
         if (params.type == 'com') {
           store.dispatch('toggleSuperMenu', 'compan');
         } else {

+ 2 - 1
src/views/auth/boxed-signup.vue

@@ -349,6 +349,7 @@ const stockRules = ref<any>({
 const handleAvatarSuccess: UploadProps['onSuccess'] = (response, uploadFile) => {
   API_Company.checkLicense({ image_url: response.url }).then((res) => {
     companyForm.value.name = res.enterprise_name;
+    companyForm.value.user_name=res.LR_name
     companyForm.value.credit_code = res.credit_code;
     companyForm.value.license_msg = res;
     companyForm.value.license = response.url;
@@ -365,7 +366,7 @@ const beforeAvatarUpload: UploadProps['beforeUpload'] = (rawFile) => {
 /* 身份证正面 */
 const handleFrontSuccess: UploadProps['onSuccess'] = (response, uploadFile) => {
   API_Company.checkIdCardOpposite({ image_url: response.url }, 'front').then((res) => {
-    if (res.name !== companyForm.value.name) {
+    if (res.name !== companyForm.value.user_name) {
       ElMessage.error('请上传法人身份证!');
       return;
     }

+ 172 - 73
src/views/companyMent/companyInfo.vue

@@ -1,79 +1,78 @@
 <template>
   <div class="bg-white dark:!bg-[#060818]">
     <el-tabs type="border-card" class="bg-gray-100 dark:bg-[#060818]">
-      <el-tab-pane label="公司信息" class="custom-tab-pane">
+      <el-tab-pane :label="$t('companyDetails')" class="custom-tab-pane">
         <el-form :model="companyForm" :rules="stockRules" ref="companyFormRef" label-width="140px">
           <el-row>
-            <el-col :span="6">
-              <el-form-item label="当前套餐:" prop="company_package_id">
+            <el-col :span="24" :md="6">
+              <el-form-item :label="$t('currentPack')+':'" prop="company_package_id">
                 <el-select v-model="companyForm.company_package_id" clearable placeholder="请选择套餐">
                   <el-option v-for="item in packageList" :key="item.id" :label="item.name" :value="item.id" />
                 </el-select>
               </el-form-item>
             </el-col>
-            <!-- user_num -->
-            <el-col :span="5">
-              <el-form-item label="套餐到期时间:" prop="name">
+            <el-col :span="24" :md="5">
+              <el-form-item :label="$t('end_use_time')+':'" prop="name">
                 {{ companyForm.end_use_time }}
               </el-form-item>
             </el-col>
-            <el-col :span="5">
-              <el-form-item label="可绑定账户数:" prop="name">
+            <el-col :span="24" :md="5">
+              <el-form-item :label="$t('user_num')+':'" prop="name">
                 {{ companyForm.user_num }}
               </el-form-item>
             </el-col>
-            <el-col :span="10">
-              <el-form-item label="公司名称:" prop="name">
-                <el-input v-model="companyForm.name" :minlength="2" :maxlength="20" clearable placeholder="请输入公司名称"></el-input>
+            <el-col :span="24" :md="10">
+              <el-form-item :label="$t('companyName')+':'" prop="name">
+                <el-input v-model="companyForm.name" :minlength="2" :maxlength="20" disabled clearable placeholder="请输入公司名称"></el-input>
               </el-form-item>
             </el-col>
-            <el-col :span="10">
-              <el-form-item label="统一社会信用代码:" prop="credit_code">
-                <el-input v-model="companyForm.credit_code" :minlength="2" :maxlength="20" clearable placeholder="请输入统一社会信用代码"></el-input>
+            <el-col :span="24" :md="10">
+              <el-form-item :label="$t('credit_code')+':'" prop="credit_code">
+                <el-input v-model="companyForm.credit_code" :minlength="2" :maxlength="20" disabled clearable placeholder="请输入统一社会信用代码"></el-input>
               </el-form-item>
             </el-col>
-            <el-col :span="10">
-              <el-form-item label="行业:" prop="industry">
-                <el-input v-model="companyForm.industry" :minlength="2" :maxlength="20" clearable placeholder="请输入行业"></el-input>
+            <el-col :span="24" :md="10">
+              <el-form-item :label="$t('industry')+':'" prop="industry">
+                <el-input v-model="companyForm.industry" :minlength="2" :maxlength="20" disabled clearable placeholder="请输入行业"></el-input>
               </el-form-item>
             </el-col>
-            <el-col :span="10">
-              <el-form-item label="联系人:" prop="user_name">
-                <el-input v-model="companyForm.user_name" :minlength="2" :maxlength="20" clearable placeholder="请输入联系人"></el-input>
+            <el-col :span="24" :md="10">
+              <el-form-item :label="$t('company_user_name')+':'" prop="user_name">
+                <el-input v-model="companyForm.user_name" :minlength="2" :maxlength="20" disabled clearable placeholder="请输入联系人"></el-input>
               </el-form-item>
             </el-col>
-            <el-col :span="10">
-              <el-form-item label="联系人电话:" prop="phone">
-                <el-input v-model="companyForm.phone" :minlength="2" :maxlength="20" clearable placeholder="请输入联系人电话"></el-input>
+            <el-col :span="24" :md="10">
+              <el-form-item :label="$t('companyPhone')+':'" prop="phone">
+                <el-input v-model="companyForm.phone" :minlength="2" :maxlength="20" disabled clearable placeholder="请输入联系人电话"></el-input>
               </el-form-item>
             </el-col>
-            <el-col :span="10">
-              <el-form-item label="邮箱:" prop="email">
-                <el-input v-model="companyForm.email" :minlength="2" :maxlength="20" clearable placeholder="请输入邮箱"></el-input>
+            <el-col :span="24" :md="10">
+              <el-form-item :label="$t('companyEmail')+':'" prop="email">
+                <el-input v-model="companyForm.email" :minlength="2" :maxlength="20" disabled clearable placeholder="请输入邮箱"></el-input>
               </el-form-item>
             </el-col>
-            <el-col :span="10">
-              <el-form-item label="邮编:" prop="postal_code">
-                <el-input v-model="companyForm.postal_code" :minlength="2" :maxlength="20" clearable placeholder="请输入邮箱"></el-input>
+            <el-col :span="24" :md="10">
+              <el-form-item :label="$t('postalCode')+':'" prop="postal_code">
+                <el-input v-model="companyForm.postal_code" :minlength="2" :maxlength="20" disabled clearable placeholder="请输入邮箱"></el-input>
               </el-form-item>
             </el-col>
-
-            <el-col :span="10">
-              <el-form-item label="官网:" prop="website">
-                <el-input v-model="companyForm.website" :minlength="2" :maxlength="20" clearable placeholder="请输入官网地址"></el-input>
+            <el-col :span="24" :md="10">
+              <el-form-item :label="$t('website')+':'" prop="website">
+                <el-input v-model="companyForm.website" :minlength="2" :maxlength="20" disabled clearable placeholder="请输入官网地址"></el-input>
               </el-form-item>
             </el-col>
-            <el-col :span="10">
-              <el-form-item label="地址:" prop="">
-                <el-cascader class="w-full" size="default" :options="options" clearable v-model="selectedOptions"> </el-cascader>
+            <el-col :span="24" :md="10">
+              <el-form-item :label="$t('companyAddress')+':'" prop="">
+                <el-cascader class="w-full" size="default" :options="options" disabled clearable v-model="selectedOptions"></el-cascader>
                 <span>
-                  <el-input class="!w-full mt-3" v-model="companyForm.address" placeholder="请输入"></el-input>
+                  <el-input class="!w-full mt-3" v-model="companyForm.address" disabled placeholder="请输入"></el-input>
                 </span>
               </el-form-item>
             </el-col>
-            <el-col :span="10">
-              <el-form-item label="营业执照:" prop="license">
+            <el-col :span="24" :md="10">
+              <el-form-item :label="$t('companyLicense')+':'" prop="license">
                 <el-upload
+                  disabled
                   class="avatar-uploader"
                   :action="uploadUrl"
                   :show-file-list="false"
@@ -87,42 +86,33 @@
             </el-col>
           </el-row>
         </el-form>
-        <div class="flex justify-center"><el-button type="primary" @click="submitWarehouseForm">保 存</el-button></div>
+        <div class="flex justify-center"><el-button type="primary" @click="submitWarehouseForm">{{$t('save')}}</el-button></div>
       </el-tab-pane>
-      <el-tab-pane label="个人信息" class="custom-tab-pane">
-        <el-form :model="infoForm" :rules="stockRules" ref="infoFormRef" label-width="140px">
+      <el-tab-pane :label="$t('info')" class="custom-tab-pane">
+        <el-form :model="infoForm" :rules="stockRules" ref="infoFormRef" label-width="100px">
           <el-row>
-            <el-col :span="16">
-              <el-form-item label="名称:" prop="nickname">
+            <el-col :span="24" :md="12" :lg="8">
+              <el-form-item :label="$t('nickname')+':'" prop="nickname">
                 {{ infoForm.nickname }}
-                <!-- <el-input v-model="infoForm.nickname" :minlength="2" disabled :maxlength="20" clearable placeholder="请输入公司名称"></el-input> -->
               </el-form-item>
             </el-col>
-            <el-col :span="16">
-              <el-form-item label="登录昵称:" prop="username">
+            <el-col :span="24" :md="12" :lg="8">
+              <el-form-item :label="$t('loginName')+':'" prop="username">
                 {{ infoForm.username }}
-                <!--  <el-input v-model="infoForm.username" :minlength="2" disabled :maxlength="20" clearable placeholder="请输入统一社会信用代码"></el-input> -->
               </el-form-item>
             </el-col>
-            <el-col :span="16">
-              <el-form-item label="手机号:" prop="phone">
+            <el-col :span="24" :md="12" :lg="8">
+              <el-form-item :label="$t('phone')+':'" prop="phone">
                 {{ infoForm.phone }}
-                <!--  <el-input v-model="infoForm.phone" :minlength="2" disabled :maxlength="20" clearable placeholder="请输入联系人电话"></el-input> -->
               </el-form-item>
             </el-col>
-            <el-col :span="16">
-              <el-form-item label="邮箱:" prop="email">
+            <el-col :span="24" :md="12" :lg="8">
+              <el-form-item :label="$t('companyEmail')+':'" prop="email">
                 {{ infoForm.email }}
-                <!--  <el-input v-model="infoForm.email" :minlength="2" disabled :maxlength="20" clearable placeholder="请输入邮箱"></el-input> -->
               </el-form-item>
             </el-col>
-            <!--  <el-col :span="16">
-              <el-form-item label="部门:" prop="dept_id">
-                {{ infoForm.dept_id }}
-              </el-form-item>
-            </el-col> -->
-            <el-col :span="16">
-              <el-form-item label="头像:" prop="face">
+            <el-col :span="24" :md="12" :lg="8">
+              <el-form-item :label="$t('profile')+':'" prop="face">
                 <el-upload
                   class="avatar-uploader"
                   :action="uploadUrl"
@@ -137,14 +127,25 @@
             </el-col>
           </el-row>
         </el-form>
-        <div class="flex justify-center"><el-button type="primary" @click="submitInfo">保 存</el-button></div>
+
+        <div class="flex justify-center">
+          <el-button type="primary" @click="paySubmit">支付测试</el-button>
+          <el-button type="primary" @click="bindWeChat">{{$t('bindWeChat')}}</el-button
+          ><!-- v-if="infoForm.openid && infoForm.openid==''" -->
+          <el-button type="primary" @click="submitInfo">{{$t('save')}}</el-button>
+        </div>
       </el-tab-pane>
     </el-tabs>
+    <el-dialog :title="$t('bindWeChat')" v-model="dialogVisibleWeChat" width="30%" center @close="addHandleCancle">
+      <div class="flex justify-center">
+        <qrcode-vue :value="qrCodeValue" :size="200" level="H"></qrcode-vue>
+      </div>
+    </el-dialog>
   </div>
 </template>
   
 <script lang="ts" setup>
-import { ref, onMounted } from 'vue';
+import { ref, onMounted, nextTick } from 'vue';
 import * as API_Company from '@/api/company';
 import * as API_Package from '@/api/package';
 import * as API_Auth from '@/api/auth';
@@ -153,6 +154,12 @@ import { ElMessageBox, FormInstance, ElMessage } from 'element-plus';
 import type { UploadProps } from 'element-plus';
 import { useStore } from 'vuex';
 import { submit } from '@/api/goodsInventoryLoss';
+import axios from 'axios';
+import QrcodeVue from 'qrcode.vue';
+import { useI18n } from 'vue-i18n';
+
+const { t } = useI18n();
+/* import QRCode from 'qrcodejs2'; */
 const store = useStore();
 const tableData = ref<any>({});
 
@@ -174,7 +181,6 @@ const selectedOptions = ref<any[]>([]);
 const loading = ref(false);
 
 const handleAvatarSuccess: UploadProps['onSuccess'] = (response, uploadFile) => {
-  console.log(response, uploadFile);
   companyForm.value.license = response.url; //URL.createObjectURL(uploadFile.raw!);
 };
 
@@ -185,6 +191,98 @@ const beforeAvatarUpload: UploadProps['beforeUpload'] = (rawFile) => {
   }
   return true;
 };
+/* 支付 */
+let ip = ref<any>(''); // 添加 ip 属性
+const payForm = ref<any>({
+  id: store.state.user.user.company_vo.id,
+  pay_type: 'wx',
+  ip: ip.value,
+  user_id: store.state.user.user.uid,
+});
+const paySubmit = () => {
+  API_Auth.getPayUrl(payForm.value).then((res) => {
+    console.log(res);
+    callWeChatPay(res);
+  });
+};
+declare const WeixinJSBridge: {
+  invoke(api: string, config: any, callback: (res: any) => void): void;
+};
+// 调用微信支付
+const callWeChatPay = (payParams: any) => {
+  // 确保WeixinJSBridge对象可用
+  if (typeof WeixinJSBridge == 'undefined') {
+    const onBridgeReadyWrapper = () => onBridgeReady(payParams); // 创建一个包装函数
+    if (document.addEventListener) {
+      document.addEventListener('WeixinJSBridgeReady', onBridgeReadyWrapper, false);
+    } else if ((document as any).attachEvent) {
+      (document as any).attachEvent('WeixinJSBridgeReady', onBridgeReadyWrapper);
+      (document as any).attachEvent('onWeixinJSBridgeReady', onBridgeReadyWrapper);
+    }
+  } else {
+    onBridgeReady(payParams);
+  }
+};
+
+// 微信支付桥接准备就绪
+const onBridgeReady = (payParams: any) => {
+  WeixinJSBridge.invoke(
+    'getBrandWCPayRequest',
+    {
+      appId: payParams.appId,
+      timeStamp: payParams.timeStamp,
+      nonceStr: payParams.nonceStr,
+      package: payParams.package,
+      signType: payParams.signType,
+      paySign: payParams.paySign,
+    },
+    (res: any) => {
+      if (res.err_msg == 'get_brand_wcpay_request:ok') {
+        // 支付成功
+        ElMessage.success(t('pay_success'));
+        // 可以在这里添加支付成功后的逻辑,比如刷新订单状态
+      } else if (res.err_msg == 'get_brand_wcpay_request:cancel') {
+        // 支付取消
+        ElMessage.info(t('pay_info'));
+      } else {
+        // 支付失败
+        ElMessage.error(t('pay_error'));
+      }
+    }
+  );
+};
+
+/* 打开绑定微信 */
+const dialogVisibleWeChat = ref(false);
+const qrCodeValue = ref('');
+const addHandleCancle = () => {
+  dialogVisibleWeChat.value = false;
+};
+
+/* 获取当前ip */
+
+const getIPAddress = async () => {
+  try {
+    const response = await axios.get('https://api.ipify.org?format=json');
+    ip.value = response.data.ip;
+  } catch (error) {
+    console.error('Error fetching IP address:', error);
+    ip.value = 'Unable to fetch IP';
+  }
+};
+/* 绑定微信 */
+const bindWeChat = () => {
+  API_Auth.getOpenIdCode(store.state.user.user.uid, { ip: ip.value })
+    .then((res) => {
+      dialogVisibleWeChat.value = true;
+      qrCodeValue.value = res;
+    })
+    .catch((error) => {
+      console.error('Error getting OpenID code:', error);
+      ElMessage.error(t('bindWeChatError'));
+    });
+};
+
 /* 个人信息详情 */
 const handleInfoSuccess: UploadProps['onSuccess'] = (response, uploadFile) => {
   infoForm.value.face = response.url; //URL.createObjectURL(uploadFile.raw!);
@@ -214,11 +312,11 @@ const submitWarehouseForm = () => {
       const params = { ...companyForm.value };
       params.province = selectedOptions.value.join(',');
       API_Company.editCompany(companyForm.value.id, params).then(() => {
-        ElMessage.success('修改成功!');
+        ElMessage.success(t('edit_success')+'!');
         GET_CompanyList();
       });
     } else {
-      ElMessage.error('表单填写有误,请核对!');
+      ElMessage.error(t('form_erroe')+'!');
       /*    store.dispatch('showMessage', { message: '表单填写有误,请核对!', type: 'error' }); */
       return false;
     }
@@ -227,7 +325,7 @@ const submitWarehouseForm = () => {
 
 const GET_CompanyList = () => {
   loading.value = true;
-  API_Company.getOne('1811346086001057794')
+  API_Company.getOne(store.state.user.user.company_vo.id)
     .then((response) => {
       loading.value = false;
       selectedOptions.value = response.province.split(',');
@@ -239,7 +337,6 @@ const GET_CompanyList = () => {
         return el;
       }); */
       companyForm.value = response;
-      console.log(companyForm.value);
     })
     .catch(() => {
       loading.value = false;
@@ -260,19 +357,20 @@ const GET_Info = () => {
   API_Auth.getAdministratorDetail(store.state.user.user.uid).then((res) => {
     infoForm.value = res;
     imgUrl.value = res.face;
+    console.log(res);
   });
 };
 const submitInfo = () => {
   if (infoForm.value.face == undefined) {
-    return ElMessage.error('请上传头像!');
+    return ElMessage.error(t('uploadPro')+'!');
   } else if (infoForm.value.face == imgUrl.value) {
-    return ElMessage.error('请上传新的头像!');
+    return ElMessage.error(t('uploadNewPro')+'!');
   }
   API_Auth.editAdministrator(store.state.user.user.uid, { face: infoForm.value.face }).then((res) => {
-    ElMessage.success('修改成功!');
+    ElMessage.success(t('edit_success')+'!');
     GET_Info();
-    store.dispatch('updateUserAction', res)
-/*     location.reload(); */
+    store.dispatch('updateUserAction', res);
+    /*     location.reload(); */
   });
 };
 
@@ -280,6 +378,7 @@ onMounted(() => {
   GET_CompanyList();
   GET_PackageList();
   GET_Info();
+  getIPAddress();
 });
 </script>
   

+ 3 - 5
src/views/goods/SKUList.vue

@@ -1,6 +1,6 @@
 <template>
   <div>
-    <en-table-layout :tableData="tableData.data" :loading="loading">
+    <en-table-layout :tableData="tableData.records" :loading="loading">
       <template #toolbar>
         <div class="inner-toolbar w-11/12 flex justify-between">
           <div class="toolbar-btns">
@@ -36,7 +36,7 @@
       </template>
       <template #pagination>
         <el-pagination
-          v-if="tableData.data && tableData.data.length"
+          v-if="tableData.records && tableData.records.length"
           @size-change="handlePageSizeChange"
           @current-change="handlePageCurrentChange"
           :current-page="tableData.page_no"
@@ -59,7 +59,7 @@
     >
       <el-form :model="skuForm" :rules="stockRules" ref="skuFormRef" label-width="140px">
         <el-row>
-          <!--     <el-col :span="10" v-if="!skuForm.id">
+        <!--<el-col :span="10" v-if="!skuForm.id">
               <el-form-item label="套餐:" prop="company_package_id">
                 <el-select v-model="skuForm.company_package_id" clearable placeholder="请选择套餐">
                   <el-option v-for="item in packageList" :key="item.id" :label="item.name" :value="item.id" />
@@ -300,7 +300,6 @@ const submitWarehouseForm = () => {
 
 const GET_GoodsList = () => {
   loading.value = true;
-  console.log(params);
   API_Goods.productList(params.value)
     .then((response) => {
       loading.value = false;
@@ -324,7 +323,6 @@ const handleDelGoods = (row) => {
 };
 const adminName = (val: string[]) => {
   let text = '';
-  console.log(val);
   if (val !== undefined) {
     text += codeToText[val[0]];
     text += codeToText[val[1]];

+ 69 - 30
src/views/stock/goodsUnderstockAdd.vue

@@ -1,7 +1,7 @@
 <template>
   <div class="bg-in-stock">
     <el-form ref="GoodsTransferFormRef" :model="GoodsTransferForm" label-width="120px" :rules="GoodsTransferFormRule" inline>
-      <h3>{{$t('transfer_order')}}</h3>
+      <h3>{{ $t('transfer_order') }}</h3>
       <el-form-item :label="$t('transfer_time')" prop="transfer_time" class="change-form-item">
         <span v-if="type === 'view'">{{ GoodsTransferForm.transfer_time }}</span>
         <el-date-picker
@@ -10,11 +10,36 @@
           value-format="YYYY-MM-DD HH:mm:ss"
           type="datetime"
           :disabled="type === 'view' || type === 'audit' || type === 'check'"
-          :placeholder="$t('change')+$t('date')"
+          :placeholder="$t('change') + $t('date')"
         >
         </el-date-picker>
       </el-form-item>
       <el-form-item prop="out_warehouse_id" :label="$t('out_warehouse')">
+        <span v-if="type === 'view'">{{ getWarehouse(GoodsTransferForm.out_warehouse_id) }}</span>
+        <el-select v-else @change="handleOutWarehouseChange" v-model="GoodsTransferForm.out_warehouse_id" clearable :disabled="type === 'view'">
+          <el-option
+            v-for="item in WarehouseList"
+            :key="item.id"
+            :label="item.name"
+            :value="item.id"
+            :disabled="item.id === GoodsTransferForm.in_warehouse_id"
+          />
+        </el-select>
+      </el-form-item>
+
+      <el-form-item prop="in_warehouse_id" :label="$t('to_warehouse')">
+        <span v-if="type === 'view'">{{ getWarehouse(GoodsTransferForm.in_warehouse_id) }}</span>
+        <el-select v-else @change="handleInWarehouseChange" v-model="GoodsTransferForm.in_warehouse_id" clearable :disabled="type === 'view'">
+          <el-option
+            v-for="item in WarehouseList"
+            :key="item.id"
+            :label="item.name"
+            :value="item.id"
+            :disabled="item.id === GoodsTransferForm.out_warehouse_id"
+          />
+        </el-select>
+      </el-form-item>
+      <!-- <el-form-item prop="out_warehouse_id" :label="$t('out_warehouse')">
         <span v-if="type === 'view'">{{ getWarehouse(GoodsTransferForm.out_warehouse_id) }}</span>
         <el-select v-else @change="cleanGoodsList" v-model="GoodsTransferForm.out_warehouse_id" :disabled="type === 'view'">
           <el-option v-for="item in WarehouseList" :key="item.id" :label="item.name" :value="item.id" />
@@ -25,7 +50,7 @@
         <el-select v-else v-model="GoodsTransferForm.in_warehouse_id" :disabled="type === 'view'">
           <el-option v-for="item in WarehouseList" :key="item.id" :label="item.name" :value="item.id" />
         </el-select>
-      </el-form-item>
+      </el-form-item> -->
       <el-form-item :label="$t('delivery_method')" prop="send_type">
         <span v-if="type === 'view'">{{ getdeliveryType(GoodsTransferForm.send_type) }}</span>
         <el-select v-else v-model="GoodsTransferForm.send_type" clearable :disabled="type === 'view'">
@@ -37,7 +62,7 @@
         <el-input v-else :disabled="type === 'view'" type="textarea" :rows="2" :placeholder="$t('place')" v-model="GoodsTransferForm.remark"> </el-input>
       </el-form-item>
       <div class="mx">
-        <h3>{{$t('goods_inventory')}}</h3>
+        <h3>{{ $t('goods_inventory') }}</h3>
         <el-button class="button" size="small" type="primary" v-if="type !== 'view'" @click="handleSelectWarehouseEntryBatch">选择</el-button>
       </div>
       <div style="display: block">
@@ -83,21 +108,21 @@
           </el-table-column>
           <el-table-column :label="$t('operate')" v-if="type !== 'view'">
             <template #default="scope">
-              <el-button size="small" type="danger" @click="GoodsTransferForm.product_list.splice(scope.$index, 1)">{{$t('delete')}}</el-button>
+              <el-button size="small" type="danger" @click="GoodsTransferForm.product_list.splice(scope.$index, 1)">{{ $t('delete') }}</el-button>
             </template>
           </el-table-column>
         </el-table>
       </div>
     </el-form>
     <div class="footer">
-      <el-button v-if="type !== 'view'" type="primary" @click="submitGoodsTransferForm">{{$t('save')}}</el-button>
+      <el-button v-if="type !== 'view'" type="primary" @click="submitGoodsTransferForm">{{ $t('save') }}</el-button>
       <!-- <el-button @click="printIng">{{$t('print')}}</el-button> -->
-      <el-button @click="roBack">{{$t('return')}}</el-button>
+      <el-button @click="roBack">{{ $t('return') }}</el-button>
     </div>
     <el-dialog :title="$t('transfer_goods')" v-model="goodsVisible" width="1000px" @close="closeGoosData">
       <div style="display: flex; align-items: center; justify-content: flex-end; padding: 10px 0">
-        <span>{{$t('search_goods')}}:</span><el-input v-model="params.keyWord" style="width: 200px; margin-right: 5px"></el-input>
-        <el-button @click="searchGoodEvent"> {{$t('search')}} </el-button>
+        <span>{{ $t('search_goods') }}:</span><el-input v-model="params.keyWord" style="width: 200px; margin-right: 5px"></el-input>
+        <el-button @click="searchGoodEvent"> {{ $t('search') }} </el-button>
       </div>
       <el-table :data="goodsData.records" border style="width: 100%" @selection-change="handleSelectionChange">
         <el-table-column type="selection" width="55" />
@@ -122,15 +147,15 @@
       >
       </el-pagination>
       <template #footer>
-        <el-button @click="closeGoosData">{{$t('cancel')}}</el-button>
-        <el-button type="primary" @click="submitGoosData()">{{$t('submit')}}</el-button>
+        <el-button @click="closeGoosData">{{ $t('cancel') }}</el-button>
+        <el-button type="primary" @click="submitGoosData()">{{ $t('submit') }}</el-button>
       </template>
     </el-dialog>
   </div>
 </template>
   
   <script lang="ts" setup>
-import { ref, onMounted, computed,reactive } from 'vue';
+import { ref, onMounted, computed, reactive } from 'vue';
 import { useStore } from 'vuex';
 import * as API_GoodsTransfer from '@/api/goodsTransfer';
 import * as API_BasicSetting from '@/api/basicSetting';
@@ -168,26 +193,40 @@ const GoodsTransferForm = ref<any>({
 const GoodsTransferFormRule = ref({
   transfer_time: {
     required: true,
-    message: t('change')+t('transfer_time'),
+    message: t('change') + t('transfer_time'),
     trigger: 'change',
   },
   out_warehouse_id: {
     required: true,
-    message: t('change')+t('out_warehouse'),
+    message: t('change') + t('out_warehouse'),
     trigger: 'change',
   },
   in_warehouse_id: {
     required: true,
-    message: t('change')+t('to_warehouse'),
+    message: t('change') + t('to_warehouse'),
     trigger: 'change',
   },
   send_type: {
     required: true,
-    message: t('change')+t('delivery_method'),
+    message: t('change') + t('delivery_method'),
     trigger: 'change',
   },
 });
 
+
+const handleOutWarehouseChange = (selectedId: string) => {
+  cleanGoodsList();
+  if (GoodsTransferForm.value.in_warehouse_id === selectedId) {
+    GoodsTransferForm.value.in_warehouse_id = '';
+  }
+};
+
+const handleInWarehouseChange = (selectedId: string) => {
+  if (GoodsTransferForm.value.out_warehouse_id === selectedId) {
+    GoodsTransferForm.value.out_warehouse_id = '';
+    cleanGoodsList();
+  }
+}
 const getdeliveryType = (value: string) => {
   const type = deliveryTypeList.value.find((type) => type.id === value);
   return type ? type.name : t('unknown');
@@ -233,7 +272,7 @@ const submitGoosData = () => {
     });
     goodsVisible.value = false;
   } else {
-    ElMessage.error(t('change')+t('goods_info')+'!');
+    ElMessage.error(t('change') + t('goods_info') + '!');
   }
 };
 /* 盘点商品分页 */
@@ -273,12 +312,12 @@ const roBack = () => {
     view: store.state.route,
     $router: store.state.router,
   }); */
- router.push({ name: 'goodsUnderstock' });
+  router.push({ name: 'goodsUnderstock' });
 };
 
 const handleSelectWarehouseEntryBatch = async () => {
   if (!GoodsTransferForm.value.out_warehouse_id) {
-    ElMessage.error(t('change')+t('out_warehouse')+'!');
+    ElMessage.error(t('change') + t('out_warehouse') + '!');
     return;
   }
   API_GoodsExchange.getGoodsInfo(params, GoodsTransferForm.value.out_warehouse_id, 'gt').then((res) => {
@@ -307,11 +346,11 @@ const submitGoodsTransferForm = () => {
     if (valid) {
       const params = { ...GoodsTransferForm.value };
       if (params.product_list.length === 0) {
-        ElMessage.error(t('change')+t('goods_info')+'!');
+        ElMessage.error(t('change') + t('goods_info') + '!');
         return;
       }
       if (params.in_warehouse_id === params.out_warehouse_id) {
-        ElMessage.error(t('out_warehouse')+t('to_warehouse')+t('consistent')+'!');
+        ElMessage.error(t('out_warehouse') + t('to_warehouse') + t('consistent') + '!');
         return;
       }
       params.product_list = params.product_list.map((item: any) => ({
@@ -323,8 +362,8 @@ const submitGoodsTransferForm = () => {
       }));
       if (id.value) {
         API_GoodsTransfer.editGoodsTransfer(id.value, params).then(() => {
-            ElMessage.success(t('edit_success')+'!');
-         /*  const { callback } = store.state.route.params;
+          ElMessage.success(t('edit_success') + '!');
+          /*  const { callback } = store.state.route.params;
           if (typeof callback === 'function') callback();
           store.dispatch('delCurrentViews', {
             view: store.state.route,
@@ -334,7 +373,7 @@ const submitGoodsTransferForm = () => {
         });
       } else {
         API_GoodsTransfer.addGoodsTransfer(params).then(() => {
-            ElMessage.success(t('add_success')+'!');
+          ElMessage.success(t('add_success') + '!');
           /* const { callback } = store.state.route.params;
           if (typeof callback === 'function') callback();
           store.dispatch('delCurrentViews', {
@@ -349,13 +388,13 @@ const submitGoodsTransferForm = () => {
 };
 
 const GET_DeptList = () => {
-  API_Setting.getDeptList({page_no:1,page_size:1000}).then((response) => {
+  API_Setting.getDeptList({ page_no: 1, page_size: 1000 }).then((response) => {
     deptList.value = response;
     deptListAll.value = response;
   });
 };
 
-const GET_WarehouseList = (value:any) => {
+const GET_WarehouseList = (value: any) => {
   API_BasicSetting.getWarehouseListAll().then((response) => {
     WarehouseList.value = response;
   });
@@ -380,7 +419,7 @@ const GET_ExpressList = () => {
 };
 
 onMounted(() => {
- /*  if (store.state.route.name === 'goodsTransferAdd') {
+  /*  if (store.state.route.name === 'goodsTransferAdd') {
     GoodsTransferForm.value.out_handled_by_id = user.value.uid;
     GoodsTransferForm.value.dept_id = user.value.dept_id;
   } else if (store.state.route.name === 'goodsUnderstockDetail') {
@@ -391,11 +430,11 @@ onMounted(() => {
     id.value = store.state.route.params.id;
     GET_GoodsTransferDetail();
   } */
- if(route.query.type==='view'){
-    type.value=route.query.type
+  if (route.query.type === 'view') {
+    type.value = route.query.type;
     id.value = route.query.id as string;
     GET_GoodsTransferDetail();
- }
+  }
   GET_DeptList();
   GET_DictDataInfo();
   GET_AdministratorList();

+ 0 - 1
src/views/templateManage/emailtemplate.vue

@@ -172,7 +172,6 @@ const handleCreated = (editor: IDomEditor) => {
 
 // 修改 onEditorContentChange 函数
 const onEditorContentChange = (editor: IDomEditor) => {
-  console.log('Editor content changed:', editor.getHtml());
 };
 
 const router = useRouter();

+ 0 - 2
vite.config.ts

@@ -6,7 +6,6 @@ import dotenv from 'dotenv';
 
 // 加载环境变量
 dotenv.config();
-console.log('Environment Variables:', import.meta.env);
 interface ImportMetaEnv {
     readonly VITE_API_URL: string; // 示例环境变量
 }
@@ -14,7 +13,6 @@ interface ImportMetaEnv {
 interface ImportMeta {
     readonly env: ImportMetaEnv;
 }
-console.log('Environment Variables:', import.meta.env);
 export default defineConfig({
     plugins: [
         vue(),

+ 5 - 0
yarn.lock

@@ -3062,6 +3062,11 @@ psl@^1.9.0:
   resolved "https://registry.npmmirror.com/psl/-/psl-1.9.0.tgz#d0df2a137f00794565fcaf3b2c00cd09f8d5a5a7"
   integrity sha512-E/ZsdU4HLs/68gYzgGTkMicWTLPdAftJLfJFlLUAAKZGkStNU72sZjT66SnMDVOfOWY/YAoiD7Jxa9iHvngcag==
 
+qrcode.vue@^3.4.1:
+  version "3.4.1"
+  resolved "https://registry.npmmirror.com/qrcode.vue/-/qrcode.vue-3.4.1.tgz#dd8141da9c4ea07ee56b111cd13eadf123af822a"
+  integrity sha512-wq/zHsifH4FJ1GXQi8/wNxD1KfQkckIpjK1KPTc/qwYU5/Bkd4me0w4xZSg6EXk6xLBkVDE0zxVagewv5EMAVA==
+
 qrcode@^1.5.3:
   version "1.5.3"
   resolved "https://registry.npmmirror.com/qrcode/-/qrcode-1.5.3.tgz#03afa80912c0dccf12bc93f615a535aad1066170"