Prechádzať zdrojové kódy

feat(djk): 新增订单确认页面和相关API接口

- 添加djkAppletOrderConfirm和addDJKOrder两个API接口定义
- 新增确认订单页面,包含商品信息展示、价格计算、积分抵扣等功能
- 更新页面路由配置,添加确认订单页面入口
- 优化支付成功/失败处理逻辑,支持参数传递跳转路径
- 修复用户店铺信息类型定义中的格式问题
- 移除支付方法中不必要的参数类型区分逻辑

refactor(user-store): 优化支付回调处理逻辑

- 移除getWxCommonPayment方法中的type参数
- 修改paySuccess和payError方法以支持动态路径参数
- 统一支付成功失败后的页面跳转逻辑

chore(utils): 添加布尔值转数字工具函数

- 新增boolToNumber函数用于将boolean值转换为number
- 更新自动导入声明文件以包含新工具函数
zhangtao 1 deň pred
rodič
commit
a7d9e25b98

+ 2 - 0
src/api/apiDefinitions.ts

@@ -106,4 +106,6 @@ export default {
   'djk.appletGoodsList':['GET', '/smqjh-pms/app-api/v1/goods/appletGoodsList'],
   'djk.appletShopInfo':['GET', '/smqjh-pms/app-api/v1/goods/appletShopInfo'],
   'djk.goodsInfo':['GET', '/smqjh-pms/app-api/v1/goods/goodsInfo'],
+  'djk.djkAppletOrderConfirm':['GET', '/smqjh-oms/api/v1/djkOrder/djkAppletOrderConfirm'],
+  'djk.addDJKOrder':['POST', '/smqjh-oms/api/v1/djkOrder/addDJKOrder'],
 };

+ 44 - 1
src/api/globals.d.ts

@@ -981,7 +981,7 @@ declare global {
       appletShopInfo<
         Config extends Alova2MethodConfig<apiResData<Api.DJKShopVO>> & {
           data: {
-           shopId:number
+            shopId: number
           }
         }
       >(
@@ -996,6 +996,49 @@ declare global {
       >(
         config: Config
       ): Alova2Method<apiResData<Api.PmsDjkGoods>, 'djk.goodsInfo', Config>;
+      djkAppletOrderConfirm<
+        Config extends Alova2MethodConfig<apiResData<{ price: number, points: number }>> & {
+          data: {
+            goodsId: number
+            channelId: number
+          }
+        }
+      >(
+        config: Config
+      ): Alova2Method<apiResData<{ price: number, points: number }>, 'djk.djkAppletOrderConfirm', Config>;
+      addDJKOrder<
+        Config extends Alova2MethodConfig<apiResData<string>> & {
+          data: {
+            channelId?: number;
+            /**
+             * 客户授权
+             */
+            customerAuthorization?: number;
+            /**
+             * 商品id
+             */
+            goodsId?: number;
+            /**
+             * 商品数量
+             */
+            goodsNum?: number;
+            /**
+             * phone
+             */
+            phone?: string;
+            /**
+             * 买家备注
+             */
+            remarks?: string;
+            /**
+             * 店铺id
+             */
+            shopId?: number;
+          }
+        }
+      >(
+        config: Config
+      ): Alova2Method<apiResData<string>, 'djk.djkAppletOrderConfirm', Config>;
 
     }
   }

+ 2 - 0
src/auto-imports.d.ts

@@ -16,6 +16,7 @@ declare global {
   const apiDefinitions: typeof import('./api/apiDefinitions')['default']
   const asyncComputed: typeof import('@vueuse/core')['asyncComputed']
   const autoResetRef: typeof import('@vueuse/core')['autoResetRef']
+  const boolToNumber: typeof import('./utils/index')['boolToNumber']
   const calculateCenterPointSpherical: typeof import('./utils/index')['calculateCenterPointSpherical']
   const clearCart: typeof import('./store/user')['clearCart']
   const computed: typeof import('vue')['computed']
@@ -398,6 +399,7 @@ declare module 'vue' {
     readonly apiDefinitions: UnwrapRef<typeof import('./api/apiDefinitions')['default']>
     readonly asyncComputed: UnwrapRef<typeof import('@vueuse/core')['asyncComputed']>
     readonly autoResetRef: UnwrapRef<typeof import('@vueuse/core')['autoResetRef']>
+    readonly boolToNumber: UnwrapRef<typeof import('./utils/index')['boolToNumber']>
     readonly calculateCenterPointSpherical: UnwrapRef<typeof import('./utils/index')['calculateCenterPointSpherical']>
     readonly computed: UnwrapRef<typeof import('vue')['computed']>
     readonly computedAsync: UnwrapRef<typeof import('@vueuse/core')['computedAsync']>

+ 8 - 0
src/pages.json

@@ -525,6 +525,14 @@
             "disableScroll": true
           }
         },
+        {
+          "path": "confirmOrder/index",
+          "name": "djk-confirmOrder",
+          "islogin": true,
+          "style": {
+            "navigationBarTitleText": "提交订单"
+          }
+        },
         {
           "path": "goodsinfo/index",
           "name": "djk-goods",

+ 10 - 16
src/store/user.ts

@@ -200,7 +200,7 @@ export const useUserStore = defineStore('user', {
      * @param type 0是下单,1是列表下单
      */
 
-    getWxCommonPayment(orderPay: wxpay, type: number) {
+    getWxCommonPayment(orderPay: wxpay) {
       uni.showLoading({ mask: true })
       return new Promise((resolve, reject) => {
         const orderInfo = {
@@ -216,16 +216,9 @@ export const useUserStore = defineStore('user', {
           orderInfo,
           ...orderInfo,
           success: (res) => {
-            if (!type) {
-              this.paySuccess()
-            }
             resolve(res)
           },
           fail: (e) => {
-            console.log(e, '失败')
-            if (!type) {
-              this.payError()
-            }
             reject(e)
           },
           complete() {
@@ -237,12 +230,13 @@ export const useUserStore = defineStore('user', {
     /**
      *
      * 支付成功统一跳转
+     *  @param name 订单列表
+     * @param idxPath 首页路径
+     *
      */
-    paySuccess() {
+    paySuccess(name: string, idxPath: string) {
       return new Promise((resolve) => {
-        const { paySuccessPath, payBackIndexPath } = storeToRefs(useSysStore())
-        paySuccessPath.value = 'xsb-order'
-        payBackIndexPath.value = 'subPack-xsb/commonTab/index'
+        useSysStore().setPaySuccessPath(name, idxPath)
         router.replace({ name: 'common-paySuccess' })
         setTimeout(() => {
           resolve(1)
@@ -252,12 +246,12 @@ export const useUserStore = defineStore('user', {
     /**
      *
      * 支付失败统一跳转
+     * @param name 订单列表
+     * @param idxPath 首页路径
      */
-    payError() {
+    payError(name: string, idxPath: string) {
       return new Promise((resolve) => {
-        const { paySuccessPath, payBackIndexPath } = storeToRefs(useSysStore())
-        paySuccessPath.value = 'xsb-order'
-        payBackIndexPath.value = 'subPack-xsb/commonTab/index'
+        useSysStore().setPaySuccessPath(name, idxPath)
         router.replace({ name: 'common-payError' })
         setTimeout(() => {
           resolve(1)

+ 199 - 0
src/subPack-djk/confirmOrder/index.vue

@@ -0,0 +1,199 @@
+<script setup lang="ts">
+definePage({
+  name: 'djk-confirmOrder',
+  islogin: true,
+  style: {
+    navigationBarTitleText: '提交订单',
+  },
+})
+const orderInfo = ref<Api.PmsDjkGoods>()
+const isPay = ref(false)
+const isAllow = ref(true)
+const phone = ref(useUserStore().userInfo.mobile)
+const isEdit = ref(false)
+const points = ref(0)
+const price = ref(0)
+onLoad((options: any) => {
+  console.log(options.order)
+  orderInfo.value = JSON.parse(options.order)
+  getCore()
+})
+async function getCore() {
+  const res = await Apis.djk.djkAppletOrderConfirm({ data: { goodsId: orderInfo.value?.id, channelId: useUserStore().userInfo.channelId } })
+  points.value = res.data.points
+  price.value = res.data.price
+}
+async function handlePay() {
+  if (!orderInfo.value) {
+    useGlobalToast().show({ msg: '网络异常!请联系客服' })
+    return
+  }
+  isPay.value = true
+  try {
+    const data = await Apis.djk.addDJKOrder({ data: { shopId: orderInfo.value.shopId, channelId: useUserStore().userInfo.channelId, phone: phone.value, goodsId: orderInfo.value.id, goodsNum: 1, customerAuthorization: boolToNumber(isAllow.value) } })
+    const res = await useUserStore().handleCommonPayMent(data.data)
+    if (res.payType !== 1) {
+      try {
+        await useUserStore().getWxCommonPayment(res)
+        await useUserStore().paySuccess('djk-homeTabbar', 'subPack-djk/commonTab/index')
+      }
+      catch {
+        useUserStore().payError('djk-homeTabbar', 'subPack-djk/commonTab/index')
+      }
+    }
+    else {
+      await useUserStore().paySuccess('djk-homeTabbar', 'subPack-djk/commonTab/index')
+    }
+  }
+  catch (error) {
+    console.log('error', error)
+    isPay.value = false
+  }
+}
+</script>
+
+<template>
+  <view v-if="orderInfo" class="page px20rpx py20rpx">
+    <view class="flex items-center rounded-16rpx bg-white p24rpx">
+      <image
+        :src="orderInfo.goodsImg?.split(',')[0]"
+        class="h160rpx w160rpx flex-shrink-0 rounded-16rpx"
+      />
+      <view class="ml20rpx flex-1">
+        <view class="text-32rpx font-semibold">
+          {{ orderInfo.goodsName }}
+        </view>
+        <view class="mt16rpx text-24rpx text-gray">
+          有效期{{ orderInfo.effectiveTime }}天·需提前{{ orderInfo.advanceBookingTime }}天预约
+        </view>
+        <view class="mt16rpx flex items-center justify-between">
+          <view class="text-36rpx text-#FF4D3A font-semibold">
+            <text class="text-20rpx">
+              ¥
+            </text> {{ orderInfo.price }}
+          </view>
+          <view class="text-24rpx text-gray">
+            x1
+          </view>
+        </view>
+      </view>
+    </view>
+    <view class="mt20rpx rounded-16rpx bg-white p24rpx">
+      <view class="flex items-center justify-between">
+        <view class="text-28rpx text-gray">
+          商品金额
+        </view>
+        <view class="text-28rpx font-semibold">
+          ¥{{ orderInfo.price }}
+        </view>
+      </view>
+      <view class="mt20rpx flex items-center justify-between">
+        <view class="text-28rpx text-gray">
+          积分{{ points ? `(${points})` : '' }}
+        </view>
+        <view class="text-28rpx font-semibold" :class="[points ? '' : 'text-gray']">
+          {{ points ? `¥${points / 100}` : '不可用' }}
+        </view>
+      </view>
+      <view class="my20rpx h2rpx w-full bg-#F0F0F0" />
+      <view class="mt20rpx flex items-center justify-between">
+        <view class="text-28rpx text-gray">
+          总计
+        </view>
+        <view class="text-28rpx font-semibold">
+          ¥{{ price }}
+        </view>
+      </view>
+    </view>
+    <view class="mt20rpx rounded-16rpx bg-white p24rpx">
+      <view class="flex items-center justify-between">
+        <view class="text-28rpx text-gray">
+          允许商户通过此号码致电沟通到店时间
+        </view>
+        <wd-checkbox v-model="isAllow" />
+      </view>
+      <view class="mt16rpx flex items-center text-28rpx">
+        <view v-if="!isEdit" class="mr10rpx">
+          {{ phone?.replace(/^(\d{3})\d{4}(\d{4})$/, '$1****$2') }}
+        </view>
+        <view v-else>
+          <input v-model="phone" type="number" :maxlength="11" @blur="isEdit = false">
+        </view>
+        <view v-if="!isEdit" class="flex items-center" @click="isEdit = true">
+          <view class="mr5rpx">
+            修改
+          </view>
+          <wd-icon name="arrow-right" size="18px" color="#000" />
+        </view>
+      </view>
+    </view>
+    <view class="mt20rpx rounded-16rpx bg-white p24rpx">
+      <view class="text-32rpx font-semibold">
+        购买须知
+      </view>
+      <view class="mt20rpx text-24rpx text-gray">
+        有效期
+      </view>
+      <view class="mt16rpx text-28rpx">
+        购买之日起{{ orderInfo.effectiveTime }}天有效
+      </view>
+      <view class="mt20rpx text-24rpx text-gray">
+        预约信息
+      </view>
+      <view class="mt16rpx text-28rpx">
+        请您提前{{ orderInfo.advanceBookingTime }}天预定
+      </view>
+      <view class="mt20rpx text-24rpx text-gray">
+        可用时间
+      </view>
+      <view class="mt16rpx text-28rpx">
+        {{ orderInfo.useStartTime }} 至 {{ orderInfo.useEndTime }}
+      </view>
+      <view class="mt20rpx text-24rpx text-gray">
+        消费流程
+      </view>
+      <view class="mt16rpx text-28rpx">
+        {{ orderInfo.usageProcess }}
+      </view>
+      <view class="mt20rpx text-24rpx text-gray">
+        购买人群
+      </view>
+      <view class="mt16rpx text-28rpx">
+        {{ orderInfo.buyNotice }}
+      </view>
+    </view>
+    <view class="h250rpx" />
+    <view class="ios footer fixed bottom-0 left-0 box-border w-full rounded-t-16rpx bg-white px24rpx">
+      <view class="box-border w-full flex items-center justify-between py20rpx">
+        <view class="flex items-center text-#FF4D3A">
+          <view class="font-semibold10 flex items-baseline text-36rpx">
+            <text class="text-24rpx">
+              ¥
+            </text> {{ price }}
+          </view>
+          <view class="ml20rpx text-22rpx">
+            共减¥ {{ points / 100 }}
+          </view>
+        </view>
+        <view class="w180rpx">
+          <wd-button size="large" :loading="isPay" loading-color="#9ED605" @click="handlePay">
+            立即支付
+          </wd-button>
+        </view>
+      </view>
+    </view>
+  </view>
+</template>
+
+<style scoped lang="scss">
+  .footer{
+    box-shadow: 0rpx -6rpx 12rpx 2rpx rgba(0,0,0,0.05);
+  }
+  .page{
+    :deep(){
+      .wd-button{
+        width: 180rpx !important;
+      }
+    }
+  }
+</style>

+ 5 - 1
src/subPack-djk/goodsinfo/index.vue

@@ -46,6 +46,10 @@ function handlePhone() {
     phoneNumber: String(goodsInfo.value?.tel),
   })
 }
+async function handlePay() {
+  await useUserStore().checkLogin()
+  router.push({ name: 'djk-confirmOrder', params: { order: JSON.stringify(goodsInfo.value) } })
+}
 </script>
 
 <template>
@@ -139,7 +143,7 @@ function handlePhone() {
             </view>
           </view>
           <view class="ml24rpx flex-1">
-            <wd-button block class="w-full">
+            <wd-button block class="w-full" @click="handlePay">
               立即购买
             </wd-button>
           </view>

+ 1 - 1
src/subPack-film/submit-order/index.vue

@@ -117,7 +117,7 @@ async function pay() {
     })
   }
   else {
-    await useUserStore().paySuccess()
+    await useUserStore().paySuccess('film-order', 'subPack-film/index/index')
   }
 }
 

+ 1 - 1
src/subPack-smqjh/components/xsb-orderList/xsb-orderList.vue

@@ -18,7 +18,7 @@ async function handleCancel(order: Api.xsbOrderList) {
 async function handlePay(orderNumber: string) {
   const res = await useUserStore().handleCommonPayMent?.(orderNumber)
   if (res?.payType !== 1 && res) {
-    await useUserStore().getWxCommonPayment(res, 1)
+    await useUserStore().getWxCommonPayment(res)
     _emit('refresh')
   }
   else {

+ 8 - 7
src/subPack-xsb/confirmOrder/index.vue

@@ -69,16 +69,17 @@ async function handlePay() {
     await useUserStore().clearCart(orderInfo.value.skuList)
     totalProduct.value = null
     console.log('进入微信支付', res)
-
     if (res.payType !== 1) {
-      console.log('进入微信支付')
-
-      await useUserStore().getWxCommonPayment(res, 0)
-      isPay.value = false
+      try {
+        await useUserStore().getWxCommonPayment(res)
+        await useUserStore().paySuccess('xsb-order', 'subPack-xsb/commonTab/index')
+      }
+      catch {
+        await useUserStore().payError('xsb-order', 'subPack-xsb/commonTab/index')
+      }
     }
     else {
-      await useUserStore().paySuccess()
-      isPay.value = false
+      await useUserStore().paySuccess('xsb-order', 'subPack-xsb/commonTab/index')
     }
   }
   catch {

+ 1 - 0
src/uni-pages.d.ts

@@ -49,6 +49,7 @@ interface NavigateToOptions {
        "/subPack-videoRights/videoRightsOrderInfo/videoRightsOrderInfo" |
        "/subPack-videoRights/videoRightsSubmitOrder/videoRightsSubmitOrder" |
        "/subPack-djk/commonTab/index" |
+       "/subPack-djk/confirmOrder/index" |
        "/subPack-djk/goodsinfo/index" |
        "/subPack-djk/shopinfo/index";
 }

+ 9 - 0
src/utils/index.ts

@@ -112,3 +112,12 @@ export enum OrderStatus {
    */
   OrderCompleted = 80,
 }
+
+/**
+ * 把true转为数字true为1,false是0
+ *
+ * @param value
+ */
+export function boolToNumber(value: boolean): number {
+  return value ? 1 : 0
+}